ctf show web 入门46
这道题目是上一题的升级版过滤条件变得更加苛刻了。我们来分析一下新增的限制以及应对方案。代码审计与变化相比之前正则过滤 preg_match 新增了以下内容[0-9]禁止使用任何数字。这意味着 $IFS$9 这种绕过方式失效了。\$禁止使用美元符号 $。这意味着 ${IFS} 变量绕过空格的方式失效了。*禁止使用通配符。这意味着 fl这种模糊匹配失效了。依然存在的限制禁止分号 ;、关键词 cat、flag 以及 空格。末尾依然有 /dev/null 21 屏蔽回显。既然数字、$ 和 * 都被封死了我们需要寻找更原始的 Shell 特性。A. 绕过空格 (禁止 $ 和数字)由于不能用 ${IFS}我们可以使用以下方式输入重定向最推荐。读写重定向。%09URL 编码的 Tab 键。B. 绕过关键词 flag (禁止 *)由于不能使用 *我们可以使用 ?。? 在 Linux Shell 中代表匹配任意单个字符。flag.php 可以写成 fla?.php 或 fl??.php。C. 绕过关键词 cat继续使用替代命令tac, nl, more, less, head, tail, sort, uniq 等。D. 截断重定向 /dev/null由于分号 ; 被过滤依然使用|| (逻辑或)%0a (换行符)第一步列目录首先要看看文件名虽然不能用数字但 ls 不需要参数?cls||或者?cls%0a第二步读取flag构造的payload为?ctac%09fla?.php%0a或者?ctac%09fla?.php||为什么限制数字但 %0a %09 却能成功这是一个关于解析顺序的误解。核心原理URL 解码发生在正则检查之前在 Web 服务器如 Apache/Nginx接收到你的请求后PHP 会在脚本运行之前自动对 GET/POST 参数进行 URL 解码。你的操作你在浏览器地址栏输入 ?cls%0a。服务器处理PHP 收到请求立刻将 %0a 解码为真正的 换行符Hex: 0x0A。变量赋值此时变量 $c 的内容实际上是 ls 后面跟着一个不可见的“回车换行”。正则检查preg_match(“/[0-9]/”, $c) 检查的是解码后的字符。%0a 在解码后是一个控制字符换行它不是字符 0 或 9。正则匹配的是字面上的数字字符ASCII 48-57而换行符的 ASCII 码是 10。结论%0a 只是换行符在传输过程中的“皮囊”。一旦进入 PHP 内部它就变成了换行符不再包含数字 0。为什么 || 可以绕过重定向限制要理解这个需要先看清楚题目中 system 拼接后的完整命令结构。命令拼接的真相题目代码system($c. /dev/null 21);如果你传入 cls||最终在服务器终端执行的命令是ls || /dev/null 21Shell 的逻辑运算符原理在 Linux Shell 中|| 是一个**逻辑或OR**运算符它遵循“短路逻辑”命令A || 命令B只有当 命令A 执行失败返回非零值时才会执行 命令B。执行命令 A首先执行 ls。判断结果ls 成功执行找到了文件返回状态码为 0代表成功。短路效应因为 命令A 已经成功了根据 OR 的逻辑整个表达式已经成立Shell 会直接跳过后面的 命令B。结果后面的 /dev/null 21也就是负责把结果丢进黑洞的命令被忽略了。ls 的输出直接流向了标准输出最后被 PHP 捕获并显示在网页上。
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2607043.html
如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!