在我寫的《漏洞研究方法總結》里面總結了一些經驗,建立安全模型,源代碼、二進制代碼分析等的一些研究方法,但總體上還是人工去找漏洞,這對于研究的人員要求也比較高,F在大量的服務軟件出來,而基本上都存在著漏洞,完全靠人員去一個個的分析代碼測試顯然滿足不了需求,所以我們需要設計一個比較自動化能夠適合多數服務器的測試工具。原來也編寫過測試工具,利用測試工具輔助研究。但原來編寫的getiisfile還是具有很強的針對性,基本上只能用于WEB服務等的一些研究,也不夠自動化。
那我們如何設計一個比較通用的測試工具呢?不同的服務有不同的協議,而很多漏洞研究也是協議相關性很大,所以我們研究一個服務的漏洞,往往先研究其協議、熟悉其軟件等,然后研究其漏洞。這顯然是一個漫長的過程,所以我們的測試軟件不能走這套路子。如果我們的測試軟件里面也需要“掌握”每個服務的協議知識,那顯然就不能很好的做到通用,所以我們需要提煉一些服務的共性。仔細想想,現在的大多服務模型就是一個服務端,一個客戶端,兩者利用通信協議通信,所以服務的共性就是數據包的通信,具體每個數據包里面什么內容怎么解釋,那就是看每個服務采用的協議,我們的測試程序不能涉及到具體協議。再想想,像IIS的.htr的溢出包,就是請求”GET /aaa.htr HTTP/1.1 \r\n HOST:host”的”aaa.htr”這個域比較長 ,IIS的ipp的溢出包,就是請求“GET /a.printer HTTP/1.1 \r\n HOST:host”的”host”這個域比較長而又沒有超過一個范圍。很多服務的漏洞不就是包里面的某個域的數據過長或者數值不對的問題嗎?所以我們的漏洞測試工具的主要任務就是構造、自動發送這些某個域數據有問題的包。怎么構造這樣的包呢?我們可以采用腳本的方法,腳本指定怎么構造、構造什么樣的包。測試不同的服務,只要編寫針對這個服務的簡單腳本,這樣程序就能夠通用了。不同服務采用不同的協議,他們接收的包要有一定的協議要求,那怎么解決協議的問題呢。我們可以采用樣本包的辦法,就是腳本里面提供一個樣本包,構造包都在這個樣本包的基礎上,這樣就可以滿足包的協議要求,也可以避免測試每個服務我們需要掌握其協議的要求。
其實我們的設計主要兩點好的思路,一個就是腳本,這個使得我們的程序編寫好后比較通用,而又能夠比較靈活。再一個就是樣本包的解決辦法,這個屏蔽了具體協議,這樣我們的測試已經基本上是協議無關的了。比如我們要測試一個新的數據庫軟件的漏洞,不需要先分析好它的協議、包格式后才能開始了。
好了,現在基本設計方案已經明朗了,剩下的就是需要考慮腳本包含一些什么內容,以能夠更有效的進行測試。
我們可以把腳本提供的一些相關參數放一塊,組成一個節,這樣方便我們的程序讀取腳本參數,也方便我們自己編寫、閱讀腳本。還有就是最好支持注釋。
一、測試目標;
1、目標IP;
2、協議;這兒的協議當然是UDP,TCP、ICMP等;
3、端口;有些協議沒有端口的概念;
4、可能這些項通過樣本包直接提供。
二、樣本包;
1、樣本包提供的方式;為了更有效的進行測試,我們有必要通過多種途徑提供樣本包。如腳本里面直接提供樣本包,這個需要處理包的輸入問題,比如我們的腳本是以回車換行分隔各個腳本變量等,那么樣本包顯然需要處理回車換行等,還有0的問題,不可顯示字符的輸入,所以基本上需要一個16進制的輸入和直接字符輸入的混合輸入方法。通過一個樣本包數據文件提供樣本包。通過抓包提供樣本包。這個抓包提供樣本包,可以方便我們到具體應用環境測試,因為這個測試工具的測試效果顯然主要靠樣本包要能夠是有問題包的一個基準,所以樣本包越豐富,測試得也會越多。再一個可以第一項的測試目標也可以通過樣本包提供。
三、測試包組裝;
1、發包前固定發送的信息;這個像有些FTP的測試,可能需要認證,而是需要測試認證后的命令處理?梢悦看伟l包前固定發送認證內容,這樣就可以通過認證了。
2、樣本包的分隔符;用于把樣本包的各個域分隔出來,分隔符可以指定多個。比如請求“GET /a.htr?a=var1&b=var2 HTTP/1.1\r\nHOST:host\r\n\r\n”,分割符就可能有空格” ”、”?”、”=”、”&”、”\r”、”\n”、”:”等,當然也要處理16進制的輸入問題。
3、測試域范圍;包分隔后從第幾到第幾個域進行測試,或者從樣本包的哪個偏移到哪個偏移進行測試。
4、測試的類型;服務軟件處理一個包里面常見的錯誤一個是包字符串的處理錯誤,一個是一些數值的錯誤。
對于字符串測試:
5、添加的域前綴、后綴;比如測試CGI的問題,可能需要URL域后面要有固定串”.cgi”。
6、域串測試開始長度、結束長度、步長;
7、填充所用的字符;一般測試可能就用”a”填充,但如果要測試那個域的處理是否有格式串的問題,可能就需要填充”%s”、”%n”等這樣的串了。
對于數值測試:
8、數值字段單位(字節、字、雙字)、開始、結束、步長;
四、測試包發送;
1、 是否采用阻塞模式;
2、 每次發包是否重新連接;
3、 兩個包發送之間等待時間;
4、每個包發送次數;
五、返回信息處理;
1、 是否接收返回信息;
2、 返回信息是否記錄;
3、 返回信息特征串的搜索,報警處理;比如IIS返回”The remote procedure call failed”,就是RPC服務出現了錯誤,一般就是溢出或者有漏洞什么的了,可以進行報警或者LOG里面進行記錄。
4、 返回信息的分析處理,判斷服務有問題;這點可能一時還比較難。
比如:
getiisfile www.iis.com 80 "GET /" 1 a .ida
返回” 找不到 IDQ 文件 c:\inetpub\wwwroot\a.ida!
getiisfile www.iis.com 80 "GET /" 10 a .ida
返回”找不到 IDQ 文件 c:\inetpub\wwwroot\aaaaaaaaaa.ida!
getiisfile 61.132.55.67 80 "GET /" 239 a .ida
返回”c:\inetpub\wwwroot\aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
aaaaaaaaaaaaaaaaaaaaaaaaaaaaa.i?????r。系統找不到指定的路徑!
顯然此程序已經發生了錯誤,239個”a”的請求已經與1個、10個”a”的請求不一樣了,多了后面一個尾巴” ?????r”。其實是strncpy調用沒有串結尾的一個問題,這樣導致泄露了堆棧的內容。要根據返回信息自動判斷這些問題,可能算法就比較難做了,這種問題我們還是采用人工識別可能好做點。
六、LOG;
1、 測試狀態的LOG;方便測試停止后的繼續測試。
2、 每個測試的狀態、返回信息的LOG;
這樣我們可以構造發送各種包,顯然還不能算完,我們還得知道這些包的效果,服務軟件到底出問題沒有,F在判斷問題主要根據返回信息,這顯然不夠,這只能收集到很少部分信息,主要信息顯然都在服務器上,所以我們還需要有服務端運行的軟件配合檢測服務軟件的狀態。這個大致可以從下面一些方面入手:
一、 內存使用監視;這個可以用現有軟件或者寫軟件監視,可以判斷一些內存不釋放的漏洞。
二、 異常的監視;像一些溢出、數值非法導致的內存非法訪問等往往會導致一些異常,這個保護模式的CPU就會產生一個異常中斷,在WINDOWS下程序就會返回到NTDLL.DLL的引出函數”KiUserExceptionDispatcher”的入口,所以可以編寫軟件攔截這個入口或者在SOFT-ICE下設置這個斷點,再根據調用這個入口提供的數據結構,得到發生異常時的EIP等寄存器內容,判斷是否程序真正有問題。*NIX系統下可以采用可加載內核模塊(LKM)攔截系統的異常中斷,然后進行綜合判斷。如果寫程序,難點就主要在這個判斷是否程序錯誤、漏洞的算法,不過看來應該還比較樂觀,差不多出現異常就是有問題了。*NIX系統由于基本上沒有結構異常這個概念,所以一般程序發生錯誤基本上就會進程死掉等,所以很好判斷。內存交換出去了等異常WINDOWS自己識別了不會返回到這個入口,再就是WINDOWS結束一個線程等可能會進入這個入口,但基本上得到的發生異常的EIP是比較固定的,所以很好排除。但WINDOWS編程有結構異常的概念,所以如果不攔截異常,很多程序的錯誤可能就不會暴露出來。
三、 服務進程狀態的監視;像很多服務程序出現問題后,系統可能會殺死服務進程,IIS5等系統會自動重新啟動此服務進程,*NIX等系統可能會產生進程DUMP的操作,所以我們都可以根據這些信息判斷服務軟件是否產生了錯誤。
文章來源于領測軟件測試網 http://www.kjueaiud.com/