[HCTF 2018]WarmUp PHP审计+任意文件读取

打开页面看到一个滑稽表情,f12发现提示source.php

 

 


进入该页面,发现是代码审计,代码如下:

 

<?php

    highlight_file(__FILE__); //打印代码

    class emmm //定义emmm类

    {

        public static function checkFile(&$page) //将传入参数赋值给$page

        {

            $whitelist = ["source"=>"source.php","hint"=>"hint.php"]; //申明白名单

            if (! isset($page) || !is_string($page)) { //若$page变量不存在或存在非法字符

                echo "you can't see it";

                return false; //返回false

            }

 

            if (in_array($page, $whitelist)) { $page在数组中

                return true; //返回true

            }

 

            $_page = mb_substr(

                $page,

                0,

                mb_strpos($page . '?', '?')

            );

            if (in_array($_page, $whitelist)) {

                return true;

            } //截取$page中?前部分,若没有截取整个$page

 

            $_page = urldecode($page); //url解码

            $_page = mb_substr(

                $_page,

                0,

                mb_strpos($_page . '?', '?')

            );

            if (in_array($_page, $whitelist)) {

                return true;

            }

            echo "you can't see it";

            return false;

        }

    }

//--------------------------------------------------------------------------------------------------------------

    if (! empty($_REQUEST['file'])

        && is_string($_REQUEST['file'])

        && emmm::checkFile($_REQUEST['file'])

    ) {

        include $_REQUEST['file'];

        exit;

    } else {

        echo "<br><img src=\"https://i.loli.net/2018/11/01/5bdb0d93dc794.jpg\" />";

}  ?> 
  • 非空
  • 类型为字符串
  • 能够通过checkFile()函数校验

看到其中$whitelist数组有两个值分别为source.phphint.php,进入hint.php页面:

 

  • 第一个if语句对变量进行检验,要求$page为字符串,否则返回false
  • 第二个if语句判断$page是否存在于$whitelist数组中,存在则返回true
  • 第三个if语句判断截取后的$page是否存在于$whitelist数组中,截取$page'?'前部分,存在则返回true
  • 第四if语句判断url解码并截取后的$page是否存在于$whitelist中,存在则返回true
    若以上四个if语句均未返回值,则返回false

有三个if语句可以返回true,第二个语句直接判断$page,不可用
第三个语句截取'?'前部分,由于?被后部分被解析为get方式提交的参数,也不可利用
第四个if语句中,先进行url解码再截取,因此我们可以将?经过两次url编码,在服务器端提取参数时解码一次,checkFile函数中解码一次,仍会解码为'?',仍可通过第四个if语句校验。('?'两次编码值为'%253f',构造url
http://***:***/source.php?file=source.php%253f../ffffllllaaaagggg
无返回值,由于我们不知道ffffllllaaaagggg文件的具体位置,只能依次增加../,最终在
http://***:***/source.php?file=source.php%253f../../../../../ffffllllaaaagggg中成功回显flag


 

posted @ 2020-04-20 15:04  Lee-404  阅读(710)  评论(0编辑  收藏  举报
Live2D