Web_XCTF/BUUCTF_WriteUp | warmup
题目
分析
F12 查看源码,发现注释 <!--source.php-->
,作为参数接入 url 提交,得到 php 代码:
稍做分析:
<?php
highlight_file(__FILE__); // 对当前文件进行 PHP 语法高亮显示
class emmm // 构造类emmm
{
public static function checkFile(&$page) // 建立公有静态函数checkFile,参数引用变量page
{
// whitelist数组source的元素赋为字符串source.php,hint的元素赋为字符串hint.php
$whitelist = ["source"=>"source.php","hint"=>"hint.php"];
// 如果page变量未设置或page变量不是字符串
if (! isset($page) || !is_string($page)) {
echo "you can't see it"; // 输出you can't see it
return false; // 返回false
}
// 如果page变量的值在数组whitelist中
if (in_array($page, $whitelist)) {
return true; // 返回true
}
// 将page字符串中第一个“?”前的子串赋给_page
$_page = mb_substr(
$page, // 原字符串
0, // 开始位置下标
mb_strpos($page . '?', '?') // 在page变量字符串后连接“?”,返回“?”在字符串page中第一次出现的位置,作为mb_substr函数的提取长度
);
// 如果_page变量的值在数组whitelist中
if (in_array($_page, $whitelist)) {
return true; // 返回true
}
$_page = urldecode($page); // 对page变量的值进行url解码赋给_page变量
// 将_page字符串中第一个“?”前的子串赋给_page
$_page = mb_substr(
$_page,
0,
mb_strpos($_page . '?', '?')
);
// 如果_page变量的值在数组whitelist中
if (in_array($_page, $whitelist)) {
return true; // 返回true
}
echo "you can't see it"; // 输出you can't see it
return false; // 返回false
}
}
if (! empty($_REQUEST['file']) // 如果以get或post请求得到file值
&& is_string($_REQUEST['file']) // 且以get或post请求得到的file值是字符串
&& emmm::checkFile($_REQUEST['file']) // 且向emmm类中的checkFile函数传递由get或post表单得到的file参数并返回true
) {
include $_REQUEST['file']; // 包含file的值
exit; // 退出脚本
} else { // 否则
// 输出滑稽图片
echo "<br><img src=\"https://i.loli.net/2018/11/01/5bdb0d93dc794.jpg\" />";
}
?>
看到 include 函数,猜测是文件包含漏洞。包含条件是 file 值存在且为字符串,同时 file 值限定为以下四种可能:
- source.php
- xxx?source.php(xxx为任意长度不带 “?” 符号的字符串)
- hint.php
- xxx?hint.php(xxx为任意长度不带 “?” 符号的字符串)
这种情况或许可以通过对 “?” 符号后的字符串进行一些操作。
先看看 hint.php 文件:
ffffllllaaaagggg 可能是 flag 的文件名。
PHP 文档对 include 函数的文件查找路线解释为:“被包含文件先按参数给出的路径寻找,如果没有给出目录(只有文件名)时则按照 include_path 指定的目录寻找。如果在 include_path 下没找到该文件则 include 最后才在调用脚本文件所在的目录和当前工作目录下寻找。如果最后仍未找到文件则 include 结构会发出一条 E_WARNING”
根据 file 的要求和 flag 文件名构造 url,在第五级父目录找到 flag:
payload:?file=source.php?../../../../../ffffllllaaaagggg
,其中 source.php 仅用于通过函数 checkFile 的过滤,更换为 hint.php 同样可通过。
Flag
XCTF:flag{25e7bce6005c4e0c983fb97297ac6e5a}
BUUCTF:flag{427773f9-b1a6-49b1-8402-97ad11968d2d}
参考
PHP 代码审计-CTF Wiki
PHP 教程-菜鸟教程
php class类的用法详细总结-左正-博客园
PHP之static静态变量详解-心雨星空-博客园
PHP中private、public、protected的区别详解-周伯通之草堂-博客园
php中引用符号(&)的使用详细介绍-梦入烟城-CSDN
mb_strpos (Encoding)-PHP 中文开发手册-开发者手册-腾讯云开发者社区
php 中 \$_GET、\$_POST 和 $_REQUEST 的区别?
PHP 类与对象 —— 范围解析操作符(::)-终毅衝-CSDN
PHP_ include-Manual
Linux基础命令之cd返回上级目录/返回根目录/进目录/返回上一次目录/返回指定目录-Soinice-CSDN