原創:struts2-045漏洞淺析
這是小弟寫的第一篇網文,文筆一般,請大家多包涵。近期發生了很多事,使我醒悟要回歸自我的同時,要作些改變,所以開始寫網文,且把這些網文分享至個人的微信公眾號(公眾號名:永記士多)和CSDN部落格(部落格賬號:rossrocket,暱稱:永記士多)。此微信公眾號和CSDN部落格現定位為:專門研究web應用的漏洞,效能,併發量,框架選擇等問題,技術涵蓋程式語言(java,php,python)、應用框架(sturts2,spring thinkphp,Laravel)、作業系統(主要是linux與windows),資料庫(mysql,oracle,db2,redis,mongodb等),web service(apache、nginx、lighttpd、tomcat、jboss、weblogic等)等等,力求不做人云亦云的技術人員,要實踐驗證真理,做web應用裡的“生活調查團”。
下面是這一次的小研究:struts2-045漏洞分析。這個是近期比較嚴重涉及面比較廣的一個漏洞,但這不是最新的漏洞,因為就在我分析的當天,另一個重大漏洞(struts2-046漏洞)被通報這了。以下為大家探討,struts2-045漏洞是一個怎樣的漏洞?黑客是怎麼利用這個漏洞進行攻擊。
1. 漏洞概述
首先看看該漏洞的相關通報:安恆資訊保安研究院WEBIN實驗室高階安全研究員nike.zheng發現著名J2EE框架——Struts2存在遠端程式碼執行的嚴重漏洞; 目前Struts2官方已經確認漏洞(漏洞編號S2-045,CVE編號:cve-2017-5638),並定級為高風險,影響版本範圍為Struts 2.3.5 – Struts 2.3.31和Struts 2.5 – Struts 2.5.10。Struts2作為老著名的老牌的mvc框架,這裡就不多說。這裡介紹一下其危險性。
1.1漏洞的危害性
有些網站把此漏洞定性為“strut2史上最大的漏洞”。是不是最大的漏洞的,不好說,但其危害性是巨大的,這是毋庸置疑的,因為這個漏洞能允許黑客遠端程式碼執行,相當於整臺伺服器已託管給黑客,黑客可以利用此漏洞獲取web應用的源程式,修改web應用內容,獲取資料庫密碼並盜取資料庫資訊,更改系統程式碼,更改資料庫密碼等等。以下我們做個POC測試:
(一).檢視資料在庫的地址與密碼
(1)先檢視當前目錄,從中我們可以知道使用tomcat的目錄,那麼就可以知道server.conf的:
(2)能過指令碼可以查詢server.xml和jdbc.properties的路徑分別為: F:\tmp\Apache Software Foundation\apache-tomcat-7.0.76\conf 和F:\tmp\Apache Software Foundation\apache-tomcat-7.0.76\webapps\ROOT\WEB-INF\classes。
(3)顯示jdbc.properties的內容,從而得到資料庫的地址與密碼:
(二)更改頁面程式碼
可以利用此漏洞修改任何的程式碼檔案,如我要更改首頁的頁面,要其顯示”Diaoyu Islands are Chinese”,可進行如下操作:
在瀏覽器輸入地址http://192.168.10.170:8080/index,顯示下資訊表示修改成功:
1.2漏洞的條件
此漏洞另一個危害性是其幾乎無條件性。只要使用了struts2框架的應用,所有的url請求都會被此漏洞利用,即使應用中沒有上傳功能或使用第三方外掛上傳檔案(如ueditor,kindeditor)也有此問題,除非修改了配置struts.multipart.parser為cos或pell。但這種情況非常少,因為大部分的struts2應用會使用apache的commons-fileupload為上傳檔案的解析器,而不配置struts.multipart.parser或配置為預設的jakarta,那麼大部分的應用都會存在此漏洞。
2. 原因分析
這樣的漏洞,我一開始以為是struts2應用中存在呼叫cmd或shell的程式碼需被黑客利用,但經過分析,發現struts2程式碼中不存在runtime.exe()或ProcessBuilder.start() 等語句。後來經過我一輪的分析與派查,才發現此漏洞的本質是Ognl表示式注入,與SQL流入有異曲同式之秒。下面深入分析此漏洞的原因。
2.1 Ognl簡述
既然此漏洞是一個Ognl漏洞,那麼先了解一下什麼是Ognl,是用來幹什麼的。先看看網上擷取的有關Ognl的描述。
這段話我們只要知道兩點就行了:1.Ognl是個一個表示式語言。2.可以用來獲取和設定java物件的屬性。其實針對此次漏洞我們可以理解Ognl有以下功能:通一定語法組裝的字串,經解釋後,可以獲取物件屬性或呼叫物件的方式(與struts2標籤庫有點相似)。這是一個非常容給黑客攻擊的特性來的。
2.2 Strtuts2程式碼分析
現在我們分析一下Struts2的在什麼情況下會呼叫Ognl表示式。下面的流程圖是程式碼執行的過程。
針對此流程圖,作以下分析:
a. 對序號(1)的方法,StrutsPrepareAndExecuteFilter的doFilter方法是Struts2框架的入口。所有web請求都會執行此方法後進入相應的Action類呼叫相應的方法。
b. 對序號(2)的方法,PrepareOperations的wrapRequest方法包裝出Struts2自己的request物件。
c. 對序號(4)的判斷,此判斷為關鍵,下面的POC例項中的第一個表示式就是為了些判斷為真,而呼叫JakartaMultiPartRequest類。
d. 對序號(6)的方法,調JakartaMultiPartRequest的parse方法對檔案解碼,而此方法捕獲序號(7)和序號(8)方法的異常,發現異常則呼叫序號(9)的方法。具體程式碼如下圖:
e. 對序號(8)的方法,JakartaMultiPartRequest的parse方法是一定會丟擲異常的,因為這是POC程式碼裡HEADER的內容根本不是“multipart/form-data”編碼的,而是一段Ognl表示式。所以是一定會走到序號(9)的。
f. 對序號(9)的方法,LocalizedTextUtil的findText是xwork框架上的工具庫方法。LocalizedTextUtil是xwork解決我們前端國際化問題的一個方案。其中findText是搜尋關鍵字的方法,裡面是一個複雜的演算法,但是其中有針對裡面的引數defautlMessage(e.getMessage())呼叫了Ognl表示式解釋方法進行解釋,而此引數defautlMessage是就是前端Heaher裡的Content-typre的值。
g. 對序號(16)的方法,OgnlTextParser的evaluate方法就是最終解釋Ognl表示式的語句。黑客就是向此處注入程式碼ProcessBuilder或Runtime的程式碼,從而呼叫cmd或shell命令,從而操制作業系統。
2.3 POC程式碼研究
以下網上的一段POC程式碼裡的一段header內容,即使沒有Ognl基礎也很容易看懂。
這個header內容只看Content-Type的內容,這Content-Type內容可以分為兩部分。第一部分不用多說只是為了本文中《2.2Strtuts2流程分析》的流程圖的序號(4)的判斷為真而已;第二部分就是Ognl注入的程式碼,就是黑客用來控制系統的程式碼,其實細看沒什麼大瞭解,大部人都可以看得懂,不需要學習Ognl。大家再看的模組(3),這就是執行cmd命令的地方,相當於在伺服器上執行了以下java程式碼:
2.修復方式
官方的解決方法是:升級到Apache Struts 2.3.32或2.5.10.1版。我們看看升級包怎麼解決這個問題。其實很簡單,就是更改類JakartaMultiPartRequest的buildErrorMessage(Throwable e, Object[] args)方法,改變呼叫LocalizedTextUtil.findText的呼叫的方式。原有的呼叫方式如下:
更改後的程式碼如下:
方案比簡解決,當e.getMessage()(這個值就是前端Header裡Content-type內容)不作為而LocalizedTextUtil.findText的defatulMessage引數而是作為args引數傳入。
附錄1
POC測試境(不是效能問題,不列硬體資訊)
1.攻擊端
作業系統 |
Fedora 25 64位(linux系統) |
指令碼直譯器 |
Python 2.7.12 |
2.伺服器端
作業系統 |
Windows 7 32位 |
Web service |
apache-tomcat-7.0.76 |
Struts2版本 |
2.3.15.1 |
Ognl版本 |
3.0.6 |
防毒軟體 |
360 |
附錄2:
相關知識
1. ProcessBuilder的redirectErrorStream 屬性
最初,此屬性為 false,意思是子程序的標準輸出和錯誤輸出被髮送給兩個獨立的流,這些流可以通過 Process.getInputStream() 和Process.getErrorStream() 方法來訪問。如果將值設定為 true,標準錯誤將與標準輸出合併。這使得關聯錯誤訊息和相應的輸出變得更容易。在此情況下,合併的資料可從 Process.getInputStream() 返回的流讀取,而從Process.getErrorStream() 返回的流讀取將直接到達檔案尾。
2. STRUTS2中的OGNL
相關推薦
原創:struts2-045漏洞淺析
這是小弟寫的第一篇網文,文筆一般,請大家多包涵。近期發生了很多事,使我醒悟要回歸自我的同時,要作些改變,所以開始寫網文,且把這些網文分享至個人的微信公眾號(公眾號名:永記士多)和CSDN部落格(部落格賬號:rossrocket,暱稱:永記士多)。此微信公眾號
Struts2-045漏洞處理時遇到的坑(升級Struts2.5需要特別注意的配置)
最近公司的ssh搭建老專案出現了問題,被人抓到了漏洞獲取了許可權,幸好是名白客沒有進行大肆破壞,找到原因是Struts2框架在之前就爆出的045漏洞,分享出自己在解決時遇到的坑。 關於檢測Struts2漏洞的方法: 關於045漏洞的危害: 幾乎無條件,所有url都
[原創]K8 Struts2 Exp 20170310 S2-045(Struts2綜合漏洞利用工具) [原創]Struts2奇葩環境任意檔案上傳工具(解決菜刀無法傳檔案或上傳亂碼等問題)
工具: K8 Struts2 Exploit組織: K8搞基大隊[K8team]作者: K8拉登哥哥部落格: http://qqhack8.blog.163.com釋出: 2014/7/31 10:24:56簡介: K8 Stru
[原創]K8 Struts2 Exp 20170310 S2-045(Struts2綜合漏洞利用工具)
上傳亂碼 mode color 平臺 功能 blog exp blank spa 工具: K8 Struts2 Exploit組織: K8搞基大隊[K8team]作者: K8拉登哥哥博客: http://qqhack8.blog.163.com發布: 2014/7/31 1
CCERT月報:Struts2漏洞已成高校網絡安全頑疾(轉)
排查 權限 允許 進行 bsp net 插件 人員 成功 Struts2漏洞已成高校網絡安全頑疾 建議學校加大信息系統巡查力度 9月教育網運行正常,未發現影響嚴重的安全事件。近期安全形勢較為嚴峻,學校要加大安全巡查的力度,對學校的信息系統進行排查,對於那些有嚴重安全隱
漏洞復現:Struts2 遠程代碼執行漏洞(S2-033)
res 3par alt param amp lan post pull struts docker pull medicean/vulapps:s_struts2_s2-033 docker run -d -p 80:8080 medicean/vulapps:s_str
Struts2.1.8 Ognl 漏洞淺析和解決方案
前面的話 工作了好幾點,一直都沒有認認真真的去寫過什麼東西,趁著最近這段時間有空,總結一下這幾年在工作中的一些經驗,尤其是Struts2 Ognl 漏洞,當年不知道影響了多少個網際網路企業。現在把他記錄下來,作為對幾年工作的一個回憶吧。 如果您是對S
原創:PHP利用session,實現用戶登錄後回到點擊的頁面(本文以TP為例)
con gop query php代碼 自帶 ttr strpos 手機 roo 1、以下內容純屬原創,請謹慎選擇: ①目的:用戶登錄超時,session過期,點擊後跳轉到登錄頁,登錄成功再跳轉到鼠標點擊的頁面。 ②流程:用戶登錄---session過期---點擊跳
原創:實現Solaris 與Windows 間的文件共享
when reading work existing pan after 重啟 所有者 相同 背景: 現行作業方式無法實現賬號權限的管控,並且每次訪問都需要創建新的連接。 Solaris訪問windows共享目錄通過以下命令 /usr/sfw/bin/smbclie
《Java從入門到放棄》入門篇:Struts2的基本訪問方式
java action struts Struts2是個什麽玩意呢?引用百度百科的介紹:Struts2是一個基於MVC設計模式的Web應用框架,它本質上相當於一個servlet,在MVC設計模式中,Struts2作為控制器(Controller)來建立模型與視圖的數據交互。介紹完畢···其核心原理
《Java從入門到放棄》入門篇:Struts2的基本數據傳遞方式
java struts action 把這個和JSP的數據傳遞方式對比一下,你就會發現·······真的可以少寫兩句代碼!!!struts2中常用的兩種數據傳遞方式如下:屬性匹配方式ModelDriven接口匹配方式(常用於自定義類型)個人比較喜歡使用第一種,為什麽呢?因為············
《Java從入門到放棄》入門篇:Struts2的常用基本標簽
java struts action s標簽庫 說起Struts2中的標簽,這真是個好東西,為什麽呢?因為··························就算你會這玩意,別人也可能會說,這玩意居然還有人學,用JSTL和EL表達式不就行了麽!還有一種情況。如果你不會,你可以理直氣狀的說:這是
《Java從入門到放棄》入門篇:Struts2的常用驗證方式
java struts action 感覺過了一個周末,人都懶得不要不要的,今天就來點簡單的內容吧 - -,各位看官如果欲求不滿的話,可以自行解決或再去寵幸其他“勃主”···struts2的驗證方式主要有四種方式:一、直接在功能方法中寫驗證代碼(不要扔雞蛋,這種辦法確實算一種)二、重寫valida
《Java從入門到放棄》入門篇:Struts2的常用驗證方式(二)
java struts action validate 數據驗證 前一回,我們講完了“直接在功能方法中寫驗證代碼”這種驗證方式,接下來,我們繼續搞定後續的三種方式。二、重寫validate方法(註意這個方法會驗證該類中所有的方法) 使用重寫驗證方法的好處就是,又可以少寫一句代碼了!!
原創:LNMP架構部署個人博客網站 禁止轉載復制
mcr sysv 返回 瀏覽器 you 首頁 gid 軟件程序 esp nginx編譯安裝步驟 ①. 檢查軟件安裝的系統環境 cat /etc/redhat-release uname -r
原創:Nginx反向代理實戰部署
image log nginx反向代理 request 1.8 反向代理 conf 負載 -1 均衡負載服務器 10.0.0.9 [[email protected] conf]# vim nginx.conf worker_processes 1;
struts2系列(二):struts2參數傳遞錯誤、struts2的輸入錯誤驗證
ide imp demo 瀏覽器 默認 success 數據 類型 index 一、struts2參數傳遞錯誤 1. 基本數據類型的傳遞最好使用包裝類,原因是struts 2.1之後使用基本數據類型如果參數為空會報錯2. 日期參數的傳遞最好定義一個區域的屬性(定義local
曉蓮說-何不原創:java 實現二維數組冒泡排序
java println 變量 冒泡排序 cnblogs 交換 public 自己 代碼 新手從業路-為自己回顧知識的同時,也希望和大家分享經驗: 話不多說,上代碼 public class 冒泡排序 { /** * @param admin
Struts2-052 漏洞復現
hal pty sha sta bject 程序 html message command s2-052漏洞復現 參考鏈接: http://www.freebuf.com/vuls/147017.html http://www.freebuf.com/vuls/1467
struts2框架學習筆記7:struts2標簽
put 取值 div private sub pan 不常用 筆記 textarea 三大標簽: 1.JSP:腳本,為了替代servlet,已過時 2.JSTL:標準標簽庫(core、format、sql、xml),還未淘汰的只有core庫 3.Struts2標簽庫:由S