POC or STOP THE CALC POPPING VIDEOS
As a red teamer / penetration tester / bug bounty hunter, I get exposed to a wide range of software products while performing customer engagements. Often times we find systems running outdated or unpatched services with publicly disclosed vulnerabilities only to find a video popping a calculator. Unfortunately this means I can’t be lazy and just re-purpose an exploit, I get the pleasure of reproducing their research in an extremely short amount of time, CTF anyone???
Releasing POC’s for disclosed vulnerabilities is a pretty controversial topic. Seems like the most common view about POCs is they are the devil and allow any ole script-kiddie to take over the world. The problem with this view is that it fails to recognize that the entire problem goes away if organizations would just update, patch or isolate the vulnerable software from attackers.
If you knew that the lock on your door was shown to be broken, would it be your fault if someone burgled your home or the guy who detailed how to break the lock?
One of the typical arguments against releasing exploit POCs is that it puts those affected at unnecessary risk. However, I’ve seen that without that risk, many lack the motivation to patch/update. Now that I’ve got that out of the way, on to the exploits.
The first bug we are going to talk about is a Java deserialization bug in Code 42’s Crashplan server. I came across a Crashplan server while working a bug bounty on a internal customer network. After googling known vulnerabilities for the software, I found one remote code execution bug discovered in 2017. The team over at Radically Open Security put together a well written article that detailed the vulnerability and how they proved code execution on a test instance. The part that caught my attention was their mention that the exploit required the target box or network to have an open firewall so an attacker could reach a newly spawned network service on the vulnerable machine. Since my target was on an internal LAN, my hope was I may have such a target. Unfortunately for me, the article didn’t end with a nice link to a proof-of-concept which was actually a bit surprising with all the emphasis placed on “open-ness” on their website (maybe they forgot to upload it?).
Rather than re-hash their research, I’m just going to start where they left off and show you how to put together a working exploit for the vulnerability. To summarize the exploit, they found that they could instantiate any Java object (call the default constructor) that was in the classpath. To that end, they found a java class, org.apache.commons.ssl.rmi.DateRMI, that when instantiated creates a RMI server that can be exploited using ysoserial.
To get a better understanding of how to construct the necessary payload, I installed the server software and decompiled com.backup42.app.jar. After looking through the code a little bit, I found the functions that parse out the incoming message. One of the key pieces that was left out of the post was that in order to instantiate an arbitrary object, you first had to register the class by mapping it to an id. Once you mapped the id, then a second message is sent to create the object and the RMI server.
Since I needed to serialize the DateRMI object and a Code42 ClassMessage, I created a project in Netbeans, imported the two jars, and let Java handle the heavy lifting. To my delight, the RMI server was created on an arbitrary port as advertised. You can find the code on our github here.
With the RMI Server running we can execute arbitrary commands on the target using the following ysoserial command.
The second bug is also a Java deserialization bug, but this time it is a custom implementation in Adobe Coldfusion. Much like the first, I found an instance of the software while scanning boxes for bug bounty. After some light research, I found a recent article by ZDI with details about the bug and the obligatory calc pop. Googling for a POC only returned more exe popping videos…
My first step was to download a trial version of Cold Fusion 2018. Next I located the vulnerable code mentioned in the ZDI article, jnbcore.jar, and decompiled it with jd-gui. After reviewing the code a little bit, it became clear that this was a custom serialization library and there was going to be a nontrivial amount of reverse engineering to implement the binary protocol.
I’d like to say I did some really cool stuff from this point to write the exploit, but in actuality it was really tedious and I’m pretty sure I went about it the hard way. Since the protocol was super complex, I just decided to rip it all out and step through it in a debugger until I got it right. Too many hours later I had an exploit that instantiated the Java Runtime object and called exec on user supplied arguments. You can find a copy of the exploit on our Github here.