Sunday, November 15, 2015

vBulletin 5.1.x #rce walk-through

I saw this vBulletin rce exploit on pastebin written in python by Mauritania Attacker. Thought it was interesting and worth talking thru.

First, let's understand that vBulletin is software used to build website forums. Per wiki, some of the bigger ones are and

Next let's understand the exploit. Per the name it's rce (Remote Code Execution) which essentially means you'll be able to run the code you want against the web server remotely (from your laptop if you want for example). It does not appear to require any authentication, so you don't need a username/password, you simply need to know a website/url and that's it. Unauthenticated RCE is perhaps the scariest category of exploit. 0day also is bad because that likely means it was being used and exploited before anybody told the vBulletin developers and thus before they had a chance to patch it and before website owners had a chance to apply a fix.

Now the exploit linked above is written in python. The script simply lets you type in a website ( site = input('Target : ') ) and it'll perform an initial harmless test (mad = inject(site)) to validate if the site is vulnerable to the rce exploit or not. We'll dig a bit deeper into that test in a bit down below. Next, if the test is successful, and the website is vulnerable, it prompts the user for the shell commands you want to run against the web server ( userinput = input("AnonGhost@Target :") ). Then it runs them (bash(site, userinput)). That's it, that's how scarey and how simple this vulnerability is.

So first, the test.

import requests, re, sys
url = ghost + '/ajax/api/hook/decodeArguments?'
r = requests.get( url,
     params = 'arguments=O:12:"vB_dB_Result":2:{s:5:"%00*%00db";O:11:"vB_Database":1:{s:9:"functions";a:1:{s:11:"free_result";s:6:"system";}}s:12:"%00*%00recordset";s:14:"echo Th3Falcon";}', timeout= 50 )

The test is going to exploit a vulnerability in the ajax API calls (Ajax API DecodeArguments) in /core/vb/api/, in the file hook.php, in the function decodeArguments. That function takes 1 parameter which is actually a serialized version of a bunch of arguments in json notation. The code inside hook.php is going to end up de-serializing those arguments from json into objects. Unfortunately the way it was originally written it wasn't properly serializing or deserializing (see below).

If we look at the json in the url parameters above closer (with some nicer indentation and highlighting) we can see that it's a serialized version of the class vB_dB_Result.

     s:14:echo Th3Falcon;

Reading the json above can be a bit tricky. Here's some useful information for reading json...
- O is "object", then the length of the class name, then the class name, then the object size (# of properties it has)
- s is "string", then the length (# of characters), and then the string's value, closed by a semicolon (;);
- a is an "array", then the length (# of key/value pairs), and then 2 string for each for both the key and the value.
- %00 is the null byte (single character).

The key things from the exploit code and jason above in red is that it appears the attacker can control both a bash command that gets run plus it's parameters. So he can run "system('echo Th3Falcon')". uh-oh. Why can he run that?

It appears that in the decodeArguments method...

public function decodeArguments($arguments)
   if ($args = @unserialize($arguments))

... the way the unserialize/serialize methods work make is possible for the user to control these values. From what I've read, the fix is to change it to json_decode/json_encode to prevent this attack. json_decode is smarter and knows where there are unserialize functions that shouldn't be allowed to be controlled by user input. If you're running the old code and still using the unserialize/serialize combo, then the attacker with input from the url ends up controlling both the bash command and the parameter which ends up being a really bad combination.

function free_result($queryresult)
   $this->sql = '';
   return @$this->functions['free_result']($queryresult);

It still may be tough to see with the naked eye how this is working, so let's break it down with some pretty colors.



@system('echo Th3Falcon');

Which means your web server is now going to be owned because I'm sure the attacker as higher ambitions that simply running an echo.

More about neonprimetime

Top Blogs of all-time
  1. pagerank botnet sql injection walk-thru
  2. ali.txt php injection walk-thru
  3. apache struts2 rce walk-thru

Copyright © 2015, this post cannot be reproduced or retransmitted in any form without reference to the original post.

No comments:

Post a Comment