搜索 PHP代碼審計之旅

2021-03-02 合天智匯
本文轉自先知社區:https://xz.aliyun.com/t/7992前言:

之前做了很多web題都遇到過審計代碼的題目,命令執行、變量覆蓋等。但如果這些代碼是分布在一套源碼中(如CMS),需要我們去發現,去找到並會利用,就需要有一定的查找以及利用思路,這次測試的是BlueCMS1.6,重要不在於去復現這個CMS的漏洞,而在先了解一下整個審計思路還有過程是怎麼樣的,去鍛鍊自己的審計能力。由於我比較菜,所以有錯誤的地方也請師傅們指正。

何為白盒、黑盒、灰盒測試

審計代碼會經常遇到這三個名詞,這又代表是什麼意思那?

黑盒測試:已知產品的功能設計規格,可以進行測試證明每個實現了的功能是否符合要求。

白盒測試:已知產品的內部工作過程,可以進行測試證明每種內部操作是否符合設計規格要求,所有內部成分是否經過檢查。

 灰盒測試更像是白盒測試和黑盒測試的混合測試,現階段對灰盒測試沒有更明確的定義,但更多的時候,我們的測試做的就是灰盒測試,即既會做黑盒測試又會做白盒測試。

其他理解來也很簡單,就比如搭建一個網站,黑盒測試是在不知道網站源碼的情況下,對各個功能進行測試看看是否有問題,而白盒測試則是知道源碼,可以從代碼入手,看看代碼是否有問題,灰盒測試就是兩者混合起來進行測試(個人理解,如有錯誤請師傅指正),當然這些概念還有更深層的知識,這裡就不詳細介紹了。

白盒測試流程——BlueCMS1.6

由於初學代碼審計,通過BlueCMS1.6來進行練習,這裡重點寫一些白盒測試如何進行分析

0x00:了解目錄結構

看到這麼多,怎麼入手,思路是怎麼去做?直接去找SQL漏洞、RCE等估計有點困難,因為這也太多文件了,我看了很多大師傅們都是先了解一下整個目錄結構,這個目錄是作用於什麼的,包含有哪些文件,找到核心文件,再進行入手,會將審計範圍縮小一點而且會節省不少時間。

├── admin     後臺管理目錄├── install   網站的安裝目錄├── api       接口文件目錄├── data     系統處理數據相關目錄├── include  用來包含的全局文件└── template  模板

看到以下函數也需要注意:

1) 函數集文件,通常命名中包含functions或者common等關鍵字,這些文件裡面是一些公共的函數,提供給其他文件統一調用,所以大多數文件都會在文件頭部包含到它們,尋找這些文件一個非常好用的技巧就是去打開index.php或者一些功能性文件,在頭部一般都能找到。

2) 配置文件,通常命名裡面包括config這個關鍵字,配置文件包括Web程序運行必須的功能性配置選項以及資料庫等配置信息,從這個文件裡面可以了解程序的小部分功能,另外看這個文件的時候注意觀察配置文件中參數值是用單引號還是用的雙引號包起來,如果是雙引號,則很大可能會存在代碼執行漏洞。

當然不一樣的CMS,會有不同的目錄結構,但大多文件夾的名稱和對應的功能是不會有多大變化的,誰想在開發的時候整一堆亂起的文件名,到時自己測試都頭疼。


0x01:從首頁獲取信息

了解文件目錄後,就先從index.php文件入手,index.php一般是整個程序的入口,通過index文件可以知道程序的架構、運行流程、包含那些配置文件,包含哪些過濾文件以及包含那些安全過濾文件,了解程序的業務邏輯,所以從首頁入手是很有必要的。

但index.php這麼多行,都要看豈不是太累了,而且沒什麼用,因為index.php往往不需要獲取用戶輸入,那我們就看這個文件引入了哪些文件,逐層遞進。

引入了這兩個文件,我們上面提到過一定要注意含有common關鍵字的文件,打開common.inc.php觀察一下

在30多行發現了addslashes() 函數對全局數組POST,GET,COOKIES,REQUEST都進行了轉義處理,所以如果我們對包含該文件的文件進行SQL注入就要注意單引號、雙引號等會被轉義。

又觀察到會ban IP,可以了解這個文件主要是寫一些通用防護,其他文件引用即可使用

該文件包含了這幾個文件,如果到後面遇到看不懂的函數,可以通過跟蹤函數名在這些文件中搜索,就這樣先瀏覽一下大致的結構。

當然這裡寫的不全,只是列出一點,但起碼這個層次關係還是多少搞懂點了。include目錄下的文件都是通用,就是讓文件進行引用減少不需要的代碼,從而提高效率,接下來寫其他頁面就相當於單獨寫,當需要引用這些文件時,只需引入即可,所以只要知道這些通用文件,當你在查看其他文件時有不懂的函數溯源查看即可明白這些函數的用途,從而繼續審計。

0x02:挖掘漏洞跟蹤輸入變量

當看到一堆代碼時,會有那種不知所措的感覺,那就不妨想像一下一般網站出現漏洞的地方都是在哪裡?比如SQL注入、XSS、RCE等會發現有一個共同點,就是用戶可以進行輸入,有輸入的地方就可能存在漏洞,所以這樣就有的放矢,在繁多的代碼中,就先去找一下那些用戶可以控制輸入的代碼。

從根目錄開始,就按照順序來,先看ad_js.php

發現ad_id這個參數是可控的,再往下看發現SQL語句

ad_js.php包含有common.inc.php文件,所以我們輸入的單、雙引號會被轉義,但是這裡的sql語句中$ad_id是沒有單或雙引號包裹的,所以根本不需要去關注過濾,很明顯這裡就存在了sql注入漏洞,先拿小本本記錄一下,這個文件含有SQL注入漏洞。

再來查看ann.php,90多行,但我們只去找用戶可以進行輸入的地方

但是經過intval()函數的處理後,便沒辦法進行SQL注入了,那就換下一個文件

查看news_cat.php文件,發現變量沒單雙引號但因為intval()函數無法進行SQL注入

再來查看user.php文件中也可能存在SQL注入漏洞,查看一下

同樣也是沒單雙引號而且沒進行過濾,應該是可以的,看一下$id是如何傳參的

因為intval()函數的處理所以這個SQL注入沒辦法利用了

利用工具去尋找漏洞

審計PHP代碼常用的工具有Seay原始碼審計系統、rips等,工具有時也會發現一些我們漏掉的地方,所以有時手工和工具同時使用效率會更高,利用Seay原始碼審計系統工具發現這麼多漏洞,但要注意只是可能存在,有的不一定就是可以利用的。

還是去查找用戶能夠進行輸入的,畢竟一般漏洞都存在於輸入的地方,這個工具當你需要溯源的函數,只需全局搜索即可找到


查找危險函數

這裡列舉一些各個漏洞對應的危險函數,我們找漏洞無法就是RCE、SQL、文件包含等,那麼直接查找這些函數,觀察這些函數是否可以利用,不就可以判斷出是否存在對應的漏洞了,比如查詢一下unlink函數

看到了一個$_POST,進行查看一下內容

存在可以利用的變量$_POST['lit_pic'],追蹤一下該變量

發現除了這四個文件含有這個變量,其他文件沒有包含有這個變量,除了開頭包含文件的轉義處理以外,沒用其他過濾地方,那就可以通過利用這個變量進行網站根目錄下任意文件刪除的操作。

0x03:分析漏洞sql注入漏洞——UNION查詢注入

剛才在跟蹤輸入變量的時候,發現ad_js.php存在一個SQL注入漏洞,現在就來看如何利用這個漏洞

仔細觀察這段代碼,發現參數是沒有任何單雙引號,再去查找一下前面包含的這個SQL語句的getone函數,看看我們傳入的參數會不會因為這個函數而變化或轉義什麼的,追蹤getone函數,發現在mysql.class.php文件中,功能用於封裝為sql語句,並沒有什麼過濾等

這裡囉嗦一下,之所以ad_js.php能調用這個函數,因為包含了common.inc.php,而common.inc.php並非在開頭引入了這個文件,而是在62行才引入,所以有的引入不一定就在開頭,最好使用工具去查找。

接下來再回到ad_js.php,發現這段代碼

內容直接回顯,這不就是CTF常見的聯合查詢注入嗎?試一下

利用order by查詢出一共八列,接下來就聯合查詢

資料庫出來了,7是回顯位,這接下來按照聯合查詢的套路繼續走就可以了,這裡就不再詳細寫了

任意文件刪除漏洞

這裡就涉及到了灰盒測試

在上面提到了user.php文件中存在可控的參數,現在就來詳細的來看一下

發現lit_pic這個參數是可以通過POST來進行控制而且沒有包括其他的條件,但前面有一個BLUE_ROOT,需要去搞懂它所代表的意思,在文件開頭發現:

只是定義一個常量,並沒有過濾什麼的,所以是可以利用的,那接下來就去利用這個參數,但還有一個問題是在user.php文件下直接POST這個參數嗎?還是在來看看源碼吧,繼續查找發現這個參數是在提交編輯後的分類信息中的

那只需滿足該頁面下需要傳入的參數(填入必須的參數)即可

這裡我先創建一個實驗的文件text.txt

進行測試

再來看下text.txt,發現已經被刪除了


反射型XSS

有的時候工具檢測不出來不代表就沒有漏洞,有的也需要自己去手動查看,比如在guest_book.php便存在一個反射型的XSS漏洞,但是工具並沒有檢測出來

在頁面發現了用戶可以進行留言的地方

查看一下源碼發現有點東西的

page_id是通過POST直接傳入的,而且查看showmsg這個函數的定義也沒有對內容進行任何處理

所以這個漏洞是絕對可以利用的,傳入必要的參數即可引起反射型XSS

至於為什麼常規的<script>alert(/xss/)</script>不行,觀察代碼,要想我們的語句起作用,就需要把前面的<input>標籤給閉合掉,所以才加上了">

所以工具沒測出來的,並不代表就沒有漏洞,還是遵循那個原則,有用戶可以輸入的地方一定要看

總結:

當然還有很多其他的漏洞,這一篇主要是學習代碼審計的一些流程步驟,下一篇就專心來審計代碼。挖掘漏洞,利用漏洞!

參考博客

Somnus

實驗推薦

命令注入漏洞的代碼審計

https://www.hetianlab.com/expc.do?ec=ECIDf80c-799d-4bd5-979c-475ff391351a(通過代碼審計掌握挖掘命令注入漏洞的方法,了解命令注入漏洞產生的原因。)

相關焦點

  • XDCMS V1 代碼審計之旅
    3:訪問特定功能點,進行特定代碼審計,也就是說一個功能點看一段代碼(這裡如果出現了過濾函數,基本上可以在2中找到)審計之旅先打開首頁看看,看到有登陸框和註冊框,那就先從註冊框開始審計Seay全局搜索,查看代碼,蕪湖,沒有進行過濾,直接調用,舒服了(這裡默認後綴為.php)
  • PHP代碼審計四
    ,漏洞根據不同的代碼可以導致各種攻擊,如代碼注入、SQL注入、目錄遍歷等等<?規定要在數組搜索的值。array 必需。規定要搜索的數組。type可選。如果設置該參數為 true,則檢查搜索的數據與數組的值的類型是否相同。mixed array_search ( mixed $value , array $array [, bool $type = false ] )value 必需。
  • 代碼審計入門實戰
    變量表示待搜索的值,$haystack表示待搜索的數組。url=demo://%22;cat<f1agi3hEre.php;%23;hetianlab.com:80/總結一下filter_var函數的審計流程:快去合天網安實驗室搜索實驗--PHP代碼審計之filter_var函數
  • 二.PHP代碼審計涉及到的超全局變量
    · 出品|安全幫(www.secbang.com)概述:安全幫專注安全教育大牛繞過 針對零基礎小白【本章目的】掌握代碼審計中常用的代碼調試函數修改tets.php代碼,定義了一個名為test()的函數,賦值局部變量$xipu的值為simple,「echo $GLOBALS[『secbang』]」語句由於使用了$GLOBALS($GLOBALS['var']是外部的全局變量本身),故輸出的是test()函數之外定義的全局變量,即$secbang = "secbanger";,所以輸出secbanger。
  • 【代碼審計】PHP代碼審計之CTF系列(3)
    payload:http://127.0.0.1/ctf/1.php?file=http://127.0.0.1//ctf/1.php?file%3Dhttp%3A%2F%2F127.0.0.1%2F%26path%3D%253C%253Fphp%2520eval(%2524_POST%255B'x'%255D)%253B%253F%253E&path=a.php寫入一句話,直接菜刀列舉網站目錄即可。
  • ZZZPHP1.61 代碼審計-從SQL注入到Getshell
    近期有很多小夥伴在後臺留言想看關於代碼審計的文章,其實有關審計的文章網上資源是比較多的,但是從代碼審計開始到結束的這類文章卻少之甚少。
  • php代碼審計學習之函數缺陷
    > /e 模式修正符,是 preg_replace() 將 $replacement 當做php代碼來執行將GET請求傳過來的參數通過complexStrtolower函數執行,preg_replace函數存在e修正符\S*=${phpinfo()} 參考深入研究preg_replace
  • 代碼審計Day9 - str_replace函數過濾不當
    前言大家好,我們是紅日安全-代碼審計小組。最近我們小組正在做一個PHP代碼審計的項目,供大家學習交流,我們給這個項目起了一個名字叫 PHP-Audit-Labs 。具體代碼如下:用 phpstorm 加載整個項目文件,按住 Ctrl+Shift+F 鍵,搜索關鍵詞 old_thumb ,發現在 include/thumb.php
  • 【作者投稿】PHP代碼審計-sprintf函數中的安全問題
    測試代碼:<?php  $str = '788 1and 1=1';  echo sprintf('output is %d',$str);  ?對每個元素進行分隔) 必須,百分號%可選,美元符號$和單引號'可選,長度百分號為識別符,被認為是特定匹配模式的開始;後面的數字是從模式參數後面的第n個參數輸入數據;美元符號和後面的單引號是開啟padding模式(字符填充)的標識,緊跟在$'後面的是用來填充的字符;長度則為規定的輸入數據長度,如果數據足夠的話無效,如果數據不夠的話就使用$'後面的填充字符進行填充;最後的為數據類型 s表示字符串,d表示整數測試代碼
  • 代碼執行、命令執行漏洞-PHP
    php echo(escapeshellcmd($_GET['cmd']));?php preg_replace("/\[(.*)\]/e",'\\1',$_GET['str']); //從$_GET['str']變量裡搜索括號[]中間的內容作為第一組的結果,preg_replace()函數的第二個參數為'\\1'代表這裡用第一組結果填充,這裡可以直接執行代碼?
  • 如何使用PHP處理CSV文件?(代碼示例)
    源 / php中文網      源 / www.php.cn在PHP中我們可以使用fgetcsv()函數來解析CSV文件,它可以自動解析給定資源中的CSV欄位。為了使用fgetcsv()函數,我們需要先用fopen()函數打開文件進行讀取,然後用fclose()函數關閉文件來結束代碼。在兩者之間,我們使用一個循環,分別解析CSV每一行。
  • 代碼審計之PHPWIND
    圖1跟蹤代碼執行當本地上傳時會進入uploadAction函數,先進行了用戶驗證然後新建一個文件上傳的PwApplicationUpload類開始執行上傳具體代碼如下根據分析安裝成功後的目錄名為alias名稱,最後訪問a.php getshellhttp://192.168.86.232/phpwind/src/extensions/test211/a.php
  • PHP代碼安全
    }以上代碼如果沒有限制 pagesize 的範圍,惡意請求者請求把 pagesize 輸入 5000,10000 等甚至更大的數,會給資料庫帶來一定的壓力,localhost/api/articles?
  • PHP Document 代碼注釋規範
    首頁 > 語言 > 關鍵詞 > php最新資訊 > 正文 PHP Document 代碼注釋規範
  • PHP 實現中文分詞搜索功能
    應用場景打個比方,我們要搜索內容欄位有「中文分詞搜索功能」的文章,用 like 去查詢的話,可以匹配以下幾種:like '中文分%'like '%中文分詞搜索功能%'like '分詞搜索功能%'如果輸入 「中文搜索功能」,就無法匹配到對應的文章。
  • PHP 代碼規範簡潔之道
    之前整理過 PSR 的標準,也找過 php-cs-fixer 這樣的工具。這些都是規範代碼的重要手段。有統一的標準,配合上工具的檢查,形成統一的編碼約束不是什麼難題。沒有規範,不同的人甚至同一個人在空格、換行和命名上都有可能是十分隨意的。代碼一長,回使整個文件看起來無比雜亂。
  • 給PHP開發者講講PHP源碼(2)
    現在,在新標籤頁打開兩個連結,然後看看它們背後藏了什麼代碼。你會看到第一個連結帶你到了php_string.h文件,它包含了下面的代碼:PHP_FUNCTION(strpos);PHP_FUNCTION(stripos);PHP_FUNCTION(strrpos);PHP_FUNCTION(strripos);PHP_FUNCTION(strrchr);PHP_FUNCTION(substr);
  • PHP代碼20個實用技巧
    還可做得更多:為同樣文件查找多個目錄。能很容易的改變放置類文件的目錄,無須在代碼各處一一修改。可使用類似的函數加載文件,如html內容。為應用保留調試代碼  在開發環境中,我們列印資料庫查詢語句,轉存有問題的變量值,而一旦問題解決,我們注釋或刪除它們。然而,更好的做法是保留調試代碼。在開發環境中,你可以:
  • 通過PHP與Python代碼對比淺析語法差異
    php$n = 0;while ($n < 3) {    #累計次數,用於循環條件    $n = $n + 1;    #定義帳號和密碼    $uname = 'tangqingsong';    $pwd = '123123';    #接收參數    fwrite
  • PHP的語言層面的優化以及代碼優化技巧
    首頁 > 語言 > 關鍵詞 > php最新資訊 > 正文 PHP的語言層面的優化以及代碼優化技巧