天天看點

提權技術研究_Discuz!管理者複制 (一)Discuz!論壇加密方式 (二)使用Mysql-Front管理Mysql資料庫 (三)實施管理者複制(四)管理者密碼丢失解決方案(五)總結與探讨

<b>提權技術研究</b><b>_Discuz!</b><b>管理者複制</b>

<b>Simeon</b>

Crossday Discuz! Board 論壇系統(簡稱 Discuz! 論壇)是一個采用 PHP 和 MySQL 等其它多種資料庫建構的高效論壇解決方案。作為商業軟體産品, Discuz! 在代碼品質,運作效率,負載能力,安全等級,功能可操控性和權限嚴密性等方面有着良好的口碑。對于站長而言,利用 Discuz! 均能夠在最短的時間内,花費最低的費用,采用最少的人力,架設一個性能優異、功能全面、安全穩定的社群論壇平台。它能運作于Windows平台和Linux平台,目前已經有超過100萬的使用者。

使用Discuz!來建設論壇友善快捷,能夠滿足論壇功能需求,其安全性與同類相比是相對最高的,是以深受廣大使用者的喜愛,而在網絡攻防技術研究中最為核心的東西就是擷取使用者資料以及獲得系統的完全控制權限,本文主要針對Discuz!資料庫如何擷取管理者權限而展開研究的。在某些情況下,是完全可以擷取一個Webshell,在擷取Webshell的情況下,可以進一步擷取Mysql等有關資料庫連接配接的使用者和密碼等資訊,由于Discuz!特有的加密方式,即使通過SQL注入猜解擷取了Discuz!論壇管理者的密碼也無法破解,是以如何通過操作資料庫來獲得管理者權限就尤為有用。本文研究的技術可以應用在兩個方面:

(1)恢複論壇管理者的密碼。對于Discuz!論壇管理者來說,如果忘記密碼了,那麼對于整個論壇的管理将無從下手,是以隻能想辦法恢複。

(2)提升權限擷取使用者資料庫檔案。在得到Webshell的情況下,通過本文研究的技術可以輕易的檢視管理者資訊,修改論壇設定、備份資料庫等操作,還可以讓普通使用者具有管理者權限。

實驗環境:

(1)資料庫——Mysql5.1

(2)Mysql資料庫用戶端管理軟體——Mysql-Front

Discuz!6.X以及後面的7.0版本都采用md5多重加密,其加密函數有checkmd5和authcode,該函數在Discuz!預設安裝include目錄下的global.func.Php檔案中。先采用salt方式,随機獲得一個字元串,然後把明文密碼MD5之後,再與随機字元串連接配接起來之後,再次MD5。加密密碼為:md5(md5($newpw).$salt) 其中$salt為random,傳回的字元串$hash。這樣就極大的提高了使用者密碼的安全性。

<b>   function checkmd5($md5, $verified, $salt = '') {</b>

<b>       if(md5($md5.$salt) == $verified) {</b>

<b>              $result = !empty($salt) ? 1 : 2;</b>

<b>       } elseif(empty($salt)) {</b>

<b>              $result = $md5 == $verified ? 3 : ((strlen($verified) == 16 &amp;&amp; substr($md5, 8, 16) == $verified) ? 4 : 0);</b>

<b>       } else {</b>

<b>              $result = 0;</b>

<b>       }</b>

<b>       return $result;</b>

<b>}</b>

以上代碼主要度對密碼進行檢測,有三個參數:

 @param string $md5

 @param string $verified

 @param string $salt

傳回值為“0”表示失敗;為“1”采用“MD5 with salt”;為“2”采用“Dual MD5”; 為“3”表示是采用正常md5加密方式,為“4”采用“MD5-16”方式。

<b>function authcode($string, $operation = 'DECODE', $key = '', $expiry = 0) {</b>

<b> </b>

<b>      $ckey_length = 4;</b>

<b>      $key = md5($key ? $key : $GLOBALS['discuz_auth_key']);</b>

<b>      $keya = md5(substr($key, 0, 16));</b>

<b>      $keyb = md5(substr($key, 16, 16));</b>

<b>      $keyc = $ckey_length ? ($operation == 'DECODE' ? substr($string, 0, $ckey_length): substr(md5(microtime()), -$ckey_length)) : '';</b>

<b>      $cryptkey = $keya.md5($keya.$keyc);</b>

<b>      $key_length = strlen($cryptkey);</b>

<b>      $string = $operation == 'DECODE' ? base64_decode(substr($string, $ckey_length)) : sprintf('%010d', $expiry ? $expiry + time() : 0).substr(md5($string.$keyb), 0, 16).$string;</b>

<b>      $string_length = strlen($string);</b>

<b>      $result = '';</b>

<b>      $box = range(0, 255);</b>

<b>      $rndkey = array();</b>

<b>      for($i = 0; $i &lt;= 255; $i++) {</b>

<b>             $rndkey[$i] = ord($cryptkey[$i % $key_length]);</b>

<b>      }</b>

<b>      for($j = $i = 0; $i &lt; 256; $i++) {</b>

<b>             $j = ($j + $box[$i] + $rndkey[$i]) % 256;</b>

<b>             $tmp = $box[$i];</b>

<b>             $box[$i] = $box[$j];</b>

<b>             $box[$j] = $tmp;</b>

<b>      for($a = $j = $i = 0; $i &lt; $string_length; $i++) {</b>

<b>             $a = ($a + 1) % 256;</b>

<b>             $j = ($j + $box[$a]) % 256;</b>

<b>             $tmp = $box[$a];</b>

<b>             $box[$a] = $box[$j];</b>

<b>             $result .= chr(ord($string[$i]) ^ ($box[($box[$a] + $box[$j]) % 256]));</b>

<b>      if($operation == 'DECODE') {</b>

<b>             if((substr($result, 0, 10) == 0 || substr($result, 0, 10) - time() &gt; 0) &amp;&amp; substr($result, 10, 16) == substr(md5(substr($result, 26).$keyb), 0, 16)) {</b>

<b>                    return substr($result, 26);</b>

<b>             } else {</b>

<b>                    return '';</b>

<b>             }</b>

<b>      } else {</b>

<b>             return $keyc.str_replace('=', '', base64_encode($result));</b>

<b>      </b><b>}</b>

以上代碼主要用來加密或者解密使用者資訊,其中參數意義如下:

@param $string - 加密或解密的串

@param $operation - 加密還是解密

@param 密鑰

@return 傳回字元串

$ckey_length 随機密鑰長度 取值 0-32;加入随機密鑰,可以令密文無任何規律,即便是原文和密鑰完全相同,加密結果也會每次不同,增大破解難度。取值越大,密文變動規律越大,密文變化 = 16 的 $ckey_length 次方,當此值為 0 時,則不産生随機密鑰

圖1 設定MySQL-Front

說明:

     (2)本例中使用用戶端軟體來管理MySQL資料庫是因為友善快捷,當然熟悉MySQL指令的朋友也可以手工在指令提示符下執行資料庫操作。

在“打開登入資訊”視窗中選擇剛才設定的MySQL資料,然後打開即可,如圖2所示,在MySQL-Front中常用的四個按鈕為“對象浏覽器”、“資料浏覽器”、“SQL編輯器”和“圖表”。“對象浏覽器”主要用來浏覽有哪些表,而“資料浏覽器”主要用來檢視選中資料庫的表中的資料,“SQL編輯器”主要用來執行SQL語句,“圖表”主要用來與“對象浏覽器”進行切換,更多好用的功能和技巧需要自己去揣摩,就不再此贅述了。

圖2 打開MySQL資料庫

在實施管理者複制前,需要先在網站注冊一個使用者名,例如在本例中注冊普通使用者“cxb”,密碼為“test”,注冊成功使用該使用者進行登入,如圖3所示。

圖3 使用新增賬號登入注冊網站

在MySQL-Front中檢視已經注冊的使用者資訊,選中Discuz!論壇的使用者系統資料庫“*_members”,其中“*”為安裝設定的名稱,如圖4所示,在本例中為“antian_members”,該表儲存的是使用者注冊的資訊,使用“資料浏覽器”打開,可以看到該使用者注冊的一些詳細資訊。

圖4 檢視標明使用者的注冊詳細資訊

4.修改普通使用者為管理者使用者

在“antian_members”表中将使用者“cxb”的“adminid”值由“0”修改為“1”;将“groupid” 值由“12”修改為“1”,然後單擊“MySQL-Front”上面的釋出按鈕使修改生效,至此已經将普通使用者cxb變成管理者使用者,在登入的網頁中重新整理一下,再次檢視使用者個人資訊,如圖5所示,使用者“cxb”的使用者組已經更新為“Administrator”,可以行使管理者權限。

圖5 普通使用者組已經更新為管理者組

使用Mysql-Front打開myuc_members表後,單擊工具條下面的“資料浏覽器”

檢視myuc_members表中的資料,如圖6所示,先将admin的password值複制到本地進行備份,以待出現錯誤後進行恢複,将已知使用者的密碼值(password中的值)複制到admin中替代原來的值。

圖6修改管理者密碼為已知使用者密碼

   在Discuz!論壇中使用者的密碼不是普通的加密,而是經過變異的加密,是以還需要保證管理者的密碼與已知使用者的salt一緻,如圖7所示,将管理者與已經使用者的salt修改成一緻。

圖7 修改salt

   在Discuz!論壇中的登入子產品中單獨設定了安全提問,如圖8所示,一共有七個安全提問,使用者在注冊成功後在個人中心的“密碼和安全問題”中進行設定,每一個安全提問根據答案生成一串8位的加密字元,密碼不同安全字元串也不同。是以如果想要管理者使用者使用普通使用者的安全提問,則需要将管理者的“secques”設定成普通使用者的“secques”,反之,則将普通使用者的“secques”設定成管理者的“secques”,如圖9所示,将已知使用者的“secques”替換管理者的“secques”,然後使用普通使用者的安全提問替代管理者的安全提問進行登入。

圖8 安全提問

圖9 修改安全提問secques值

   至此有關discuz!論壇管理者與普通使用者身份之間的轉換已經完成,使用修改後的密碼和問題答案即可登入,登入後身份為管理者使用者,如圖10所示,可以對論壇系統進行管理。

圖10 登入背景進行管理

本文探讨了discuz!論壇的加密方法,通過實際的案例講解了如何通過操作MySQL資料庫來更改使用者身份,即通過修改普通使用者的adminid,groupid和secques以及password的值,可以使“普通使用者”變成“管理者”行使管理者權限;同時該方法也适用管理者丢失或者忘記了管理密碼,通過該方法可以重新設定密碼,并行使管理權限。

本文寫完後,又發現該管理者的密碼可以直接适用PasswordPro工具軟體進行破解,由于篇幅關系就不在本文中進行探讨,關于該論壇的安全問題還有很多話題,例如通過腳本來嗅探或者記錄使用者登入使用者名和密碼。在discuz!論壇資料庫中使用者密碼字段生成的是密文,網上有一些腳本可以直接用來記錄使用者登入的密碼。

完整全文:

<a href="http://www.antian365.com/viewthread.php?tid=5297&amp;extra=page%3D1">http://www.antian365.com/viewthread.php?tid=5297&amp;extra=page%3D1</a>

 本文轉自 simeon2005 51CTO部落格,原文連結:http://blog.51cto.com/simeon/245210