Last Updated: 2010-07-01 07:30:23 UTC
by Bojan Zdrnja (Version: 1)
In this diary I will continue with the analysis of the PHP script that the RogueAV guys use on their frontend web servers. You can read the first diary at http://isc.sans.edu/diary.html?storyid=9085.
Now that we understand how the poisoning of search engines work, we can see some specifics about the PHP script that the attackers use. As I said in the first question, the script was obfuscated but it was still possible to understand what they are doing. The code snippets I will be showing in this and next diaries were actually "beautified" and made easier to read by me.
Infecting the whole site
Once the site has been compromised, the attackers install their script in any directory, preferably in a directory that is not accessible directly from the web since they will not need to access it directly.
The next step the attackers do is to infect all (and I mean all!) PHP files on the compromised web site. If it's a shared web site, and the permissions are not setup correctly, they will actually infect absolutely every web site hosted on that machine.
The infection consists of insertion of one line at the beginning of every PHP file, as seen below:
This line (which I deliberately shortened) contains a small PHP script that is just Base64 encoded. So, when any web page on the compromised web site is accessed, the attackers PHP script gets executed first! Below is the decoded script:
The decoded part shows what the attackers do:
- If the global msfn variable is not set and the ob_start function exists (it's a standard PHP function) the following code gets executed.
- The global variable is set to point to the master PHP script (the one we're talking about – called style.css.php in this example). Notice that it can be anywhere on the disk as long as the Apache process has access to it.
- If the file exists, it is included. This causes the master PHP script to execute and do main processing. I'll cover this execution process in subsequent diaries.
- If the master PHP script ran correctly, it will define functions gml and dgobh so the last line can execute. This is the part that actually displays the original web sites and, if needed, appends the links to search engines – I covered this in the previous diary.
This way the attackers made sure that their script will execute whenever another PHP script on the compromised web site is accessed. This allows them unlimited freedom in using different URLs for poisoning search engines but for redirecting users to the sites serving RogueAV (or any other malware). Cleaning a web site after such infection is not too difficult – all you have to do is remove the first line, but as with any infection or compromise I would recommend that you restore files off backups (you do make them, right?).
If you wonder how the attackers insert this line into every single PHP file, the answer is simple – a special function in the master PHP script takes care of this. It recursively traverses all directories, finds any PHP files and if it can modify them inserts the line at the beginning. Once the attackers installs the master PHP script (style.css.php), all he has to do is call the script with a proper parameter, as you can see in the screenshot below:
This interface is password protected, so you can't access it directly without authenticating first. For those curious, there is also a function that clears the whole site (parameter dgr=1, probably for remove) but access to it is, as well, password protected.
Scared of other attackers?
The master PHP script consists of dozens of functions that take care of various tasks. Today I will cover the first couple of lines that get executed as they are relatively interesting. You can see the PHP code below:
This code does something interesting. It takes the contents of $_GET, $_POST and $_COOKIE superglobals which contain request parameters and (of course) contents of the cookie. Then the code does a bit of shuffling with the content, converts it to all lower case and performs urldecode on it. This will normalize any content (for example, %61 will be converted to lower case a).
Finally, the code compares this content with any of the strings in line 12: 'base64','user_pass','substring(','or id=','eval(','nutch','_users','union all','mid('. If any of these matched, the script exits immediately!
This is interesting as it appears that the author of the script tried to implement a very simple intrusion detection system – notice how it contains SQL injection strings or parts of PHP code. This does not make a lot of sense (especially matching of SQL injection) since the master PHP script, for example, does not use a database at all so I wonder if this was part of another program that the author just reused.
And with this we come to the end of the second diary. In next diary I'll go through some advanced functions of the PHP script such as auto-update as well as the administrators interface. Of course, you are always welcome to contact us if you have any questions.