Java程式碼審計篇 | ofcms系統審計思路講解 - 篇1 | 環境搭建、路由機制
目錄
-
1. 前言
-
2. 專案環境搭建
-
3. 專案路由機制
-
3.1. 1)先搜尋pom.xml檔案,看看使用了什麼框架
-
3.2. 2)確定是否是spring的路由機制
-
3.3. 3)確定自寫路由機制的特點
-
3.4. 4)從前端探索
-
3.5. 5)斷點除錯
-
3.6. 6)尋找路徑後的.json
-
3.7. 7)測試下結論
-
1. 前言
我發現很多文章包括教程,大概套路是:只說有漏洞的點,將有漏洞的點指出,然後分析程式碼;或者黑盒測試出漏洞之後,然後分析程式碼。
我認為這是在分析漏洞程式碼,而非程式碼審計。程式碼審計文章或教程應該是從0開始找到漏洞所在,包括思路!
所以這裡不管有沒有漏洞,我都會把審計過程寫出來,因此篇幅會很長,但我認為這樣對你會很有幫助。
知其然亦知所以然。
由於篇幅較長,因此我會分幾篇進行,本篇是整個系列的第1篇,講解兩個內容:
- 專案環境搭建
- 專案路由機制
文章中有錯誤點,或者思路上有什麼問題的,歡迎師傅們留言指出~
2. 專案環境搭建
專案地址:https://gitee.com/oufu/ofcms
版本:v1.1.2
下載地址:https://gitee.com/oufu/ofcms/archive/refs/tags/V1.1.2.zip
1)下載專案原始碼,解壓,使用idea開啟;修改資料庫連線資訊。
- 配置檔案位置:ofcms-V1.1.2/ofcms-admin/src/main/resources/dev/conf/db.properties
2)新建資料庫,預設資料庫名ofcms,並匯入sql檔案
- 專案sql檔案位置:ofcms-V1.1.2/ofcms-admin/src/main/resources/conf/sql/install.sql
- 開啟install.sql檔案,全選語句,點選左上角執行,完畢之後,檢視資料庫表是否完整
3)載入專案依賴後,配置tomcat:
注意專案名稱,否則無法訪問
4)啟動tomcat專案,預設彈出首頁,環境搭建成功。
3. 專案路由機制
在真正審計之前,最好是先確定下專案的路由機制,有了路由我們才能更好的瞭解前端功能是如何與後端功能函式搭配的,也是我們驗證漏洞的必要條件。
如何專案使用了某些框架,那麼專案路由機制和框架路由機制大機率是相同的;但是有些可能不同,比如本專案就是一個和使用框架不太相同的路由機制。(在這裡費了好長時間~)
在這裡,我們先分析下本專案的路由機制。
3.1. 1)先搜尋pom.xml檔案,看看使用了什麼框架
我們可以看到,該專案使用了 springframework,那該專案大機率使用的就是spring的路由機制。
3.2. 2)確定是否是spring的路由機制
搜尋@Mapping
、@Request
等spring的路由機制的常用註解,發現沒有!
那大機率,這裡就是自己寫的路由機制了。
3.3. 3)確定自寫路由機制的特點
這裡根據不同的專案會有不同的方式,而該專案在前面已經知道使用了springframework,那麼應該會有Controller
,尋找一下Controller
,因為在springframework中一般路由對映是寫在Controller
上面的。
透過搜尋幾個Controller
之後,發現:該專案的路由看似像透過@Action
註解完成的,但是類中的功能函式並沒有什麼註解。這裡會有一個疑問?透過註解中的路徑可以定位到類,但怎麼定位到功能函式呢?
這裡卡了很久。不行就換個思路,從前端嘗試探索。
- 這裡多說一下:
@Action
一般是Struts2中的路由註解,所以這裡我還懷疑了該專案使用了Struts2框架,但是搜尋struts2.xml
沒有搜到!
3.4. 4)從前端探索
登入後臺,之後隨便找個功能,點選一下,並抓包
路徑是這樣的~
接下來怎麼辦?我的方法是在後端搜尋該路徑,當然不要搜全路徑(搜尋的時候可以不斷的縮小路徑)
一路搜尋下來之後,到達了@Action
註解,點進去看一下。
剛才請求的路徑是這樣的:/ofcms_admin_war/admin/comn/service/del.json?sqlid=system.log.delete
,當前定位的類在admin目錄下,所以前面這段admin/comn/service
路徑對上了,但是後面的del.json
是什麼?
我們可以發現,該ComnController
類中存在del()
方法,難到del.json
對應就是這個方法嗎?
我們可以打斷點除錯看一下:
3.5. 5)斷點除錯
在del()方法處打個斷點,然後啟動除錯,重新點選該功能。
發現,確實停留到此處。
也就是說/ofcms_admin_war/admin/comn/service/del.json
對應的就是admin目錄下的存在@Action(path="/comn/service")
註解的類中的del()
方法。其實到這裡已經夠用了。
但是這裡稍微深入一下,為什麼路徑是del.json
?
3.6. 6)尋找路徑後的.json
這裡該如何找呢?我們可以在專案原始碼中搜尋.json
,而且找的應該是字串~因為這裡只是路徑中的字串,不是方法什麼的...
大概看一下,發現存在一個這樣的語句,看紅框位置,點進去看一下
這個類名字叫ActionHandler
,名字看起來就和@Action
註解有關。
再看下注釋:“請求字尾名處理”。看來我們尋找的沒錯了。
大概分析下程式碼:
public class ActionHandler extends Handler {
private String[] suffix = { ".html", ".jsp", ".json" };
public static final String exclusions = "static/";
public ActionHandler(String[] suffix) {
super();
this.suffix = suffix;
}
public ActionHandler() {
super();
}
@Override
public void handle(String target, HttpServletRequest request,
HttpServletResponse response, boolean[] isHandled) {
/**
* 不包括 suffix 、以及api 地址的直接返回
*/
//過慮靜態檔案
if(target.contains(exclusions)){
return;
}
target = isDisableAccess(target);
BaseController.setRequestParams();
next.handle(target, request, response, isHandled);
}
private String isDisableAccess(String target) {
for (int i = 0; i < suffix.length; i++) {
String suffi = getSuffix(target);
if (suffi.contains(suffix[i])) {
return target.replace(suffi, "");
}
}
return target;
}
public static String getSuffix(String fileName) {
if (fileName != null && fileName.contains(".")) {
return fileName.substring(fileName.lastIndexOf("."));
}
return "";
}
}
可以看到,請求的地址中字尾內容需要包含".html", ".jsp", ".json"。對,是包含,不是等於。
也就是說我們請求的地址可以是以上三種,也可以是".jsonaaa",當然這裡也沒什麼意義,只是分析下~
3.7. 7)測試下結論
將路徑修改為del.jsonaaa
,發現可以正常進入del()
方法,即我們的結論是正確的。