黃荷潔,康 緋,舒 輝
(解放軍信息工程大學數(shù)學工程與先進計算國家重點實驗室,鄭州450000)
基于動態(tài)數(shù)據(jù)流分析的虛擬機保護破解技術(shù)
黃荷潔,康 緋,舒 輝
(解放軍信息工程大學數(shù)學工程與先進計算國家重點實驗室,鄭州450000)
由于虛擬機采用虛擬化技術(shù)和代碼混淆技術(shù),采用傳統(tǒng)的逆向分析方法還原被虛擬機保護的算法時存在較大困難。為此,提出一種基于動態(tài)數(shù)據(jù)流分析的虛擬機保護破解方法。以動態(tài)二進制插樁平臺Pin作為支撐,跟蹤記錄被虛擬機保護的算法在動態(tài)執(zhí)行過程中的數(shù)據(jù)流信息,對記錄的數(shù)據(jù)流信息進行整理分析,獲取虛擬機指令的解釋執(zhí)行軌跡,還原程序的控制流圖,根據(jù)軌跡信息對數(shù)據(jù)生成過程進行分層次、分階段還原,并由分析人員結(jié)合控制流圖和數(shù)據(jù)生成過程進行算法重構(gòu)。實驗結(jié)果證明,該方法能夠正確還原程序的控制流和數(shù)據(jù)生成過程,輔助分析人員完成被保護算法的重構(gòu)。
數(shù)據(jù)流分析;虛擬機保護;控制流還原;算法還原
軟件核心算法的逆向分析在網(wǎng)絡(luò)協(xié)議逆向、惡意代碼機理分析、協(xié)議特征提取等安全應(yīng)用中發(fā)揮著重要的作用。目前惡意軟件廣泛采用虛擬機保護等抗分析技術(shù)對核心算法進行保護,使得已有的逆向分析方法面臨新的挑戰(zhàn)。
虛擬機保護技術(shù)[1]是指將基于x86指令系統(tǒng)的可執(zhí)行代碼轉(zhuǎn)換為字節(jié)碼(Pcode)并加入虛擬機解釋器,程序運行時,由虛擬機解釋器對轉(zhuǎn)換后的Pcode進行解釋執(zhí)行。為增加逆向分析難度,虛擬機保護軟件通常采用指令集隨機化、虛假跳轉(zhuǎn)指令、垃圾指令、常數(shù)加密等方式對虛擬機解釋器進行高強混淆[2],使得一條匯編指令經(jīng)虛擬機處理后,會膨脹幾百甚至幾千倍。采用傳統(tǒng)的靜態(tài)分析與動態(tài)調(diào)試技術(shù)對虛擬機進行分析,得到的是虛擬機解釋器的邏輯,并不能獲取被保護代碼的語義信息;同時由于采用了混淆技術(shù),通過人工分析還原虛擬機指令與x86指令對應(yīng)關(guān)系,然后還原被保護算法的方式也很難奏效。因此深入研究虛擬機保護技術(shù),提出有效的自動化分析方法顯得意義重大。
在典型的虛擬機保護逆向分析研究成果中,文獻[3]提出通過動態(tài)數(shù)據(jù)流分析、污點追蹤和聚類分析等手段,獲取字節(jié)碼語法語義信息。這種方法只能還原部分Pcode的語義信息。Rolf Rolles提出通過逆向虛擬機結(jié)構(gòu),化簡被混淆指令,將虛擬機指令轉(zhuǎn)換中間語言,然后將中間語言編譯轉(zhuǎn)換為對應(yīng)的x86指令的方法來還原被保護的代碼[4]。這種方法要求虛擬機解釋器的結(jié)構(gòu)滿足一定條件,因此,并不具有通用性;同時通過指令化簡很難有效應(yīng)對虛擬機中使用高強度混淆代碼。文獻[5]提出通過識別被保護軟件的API調(diào)用,然后抽取出所有影響API參數(shù)的指令來近似表示程序的原始代碼。這種方法只能得到影響API參數(shù)的指令,因此,并不能有效還原被保護算法。
針對當前分析方法對于重構(gòu)被保護算法方面存在的不足,本文提出一種基于動態(tài)數(shù)據(jù)流分析[6-7]的虛擬機保護破解方法,利用動態(tài)二進制插樁[8]平臺Pin[9]將虛擬機解釋器動態(tài)執(zhí)行過程中的數(shù)據(jù)流信息記錄成二進制文件,并以這些文件作為分析基礎(chǔ),提取虛擬機指令的執(zhí)行軌跡,然后重構(gòu)被保護算法的控制流;采用改進的數(shù)據(jù)流分析[7,10]算法對被保護算法的輸出數(shù)據(jù)的生成過程進行分層次、分階段還原;最終由分析人員結(jié)合控制流和數(shù)據(jù)生成過程對被保護算法進行重構(gòu)。
首先定義虛擬機保護破解要解決的具體問題。
定義1 虛擬機保護破解
對于一個被虛擬機保護的函數(shù)F(x),對它進行破解是指通過還原被保護算法的控制流圖(Control Flow Graph,CFG)和函數(shù)輸入、輸出數(shù)據(jù)之間的運算關(guān)系(IOOR),最終重構(gòu)出被保護算法,得到F′(x),使得對于任意的輸入x,有F(x)=F′(x),即F(x)與F′(x)等價。
本文方法的基本原理是虛擬機解釋器對虛擬機代碼(VMCode)的解釋執(zhí)行軌跡包含著程序的控制流信息,虛擬機的執(zhí)行過程包含著數(shù)據(jù)的處理過程,通過對虛擬機執(zhí)行過程中的數(shù)據(jù)流信息進行整理分析,能夠得到被保護算法的CFG和IOOR,最終重構(gòu)出被保護算法。具體而言,在虛擬機指令未被混淆的情況下,x86指令被轉(zhuǎn)換為等價的Pcode,因此, x86指令代碼與VMCode的CFG相同,同時,對于同樣的輸入,VMCode與x86指令代碼的執(zhí)行軌跡一致。通過對VMCode的讀取過程進行提取和分析,能夠重構(gòu)原始x86指令代碼的控制流。由于虛擬機的本質(zhì)只是將原始x86指令的邏輯隱藏在Pcode的解釋執(zhí)行過程中。因此采用數(shù)據(jù)流分析技術(shù),能夠還原出被保護算法的輸入、輸出數(shù)據(jù)之間的運算關(guān)系。將數(shù)據(jù)的運算過程與控制流進行整合,就能重構(gòu)出被保護算法。
基于以上研究思路,將虛擬機保護破解過程分為3個階段:動態(tài)執(zhí)行軌跡記錄,控制流圖還原和數(shù)據(jù)生成過程還原階段。動態(tài)執(zhí)行軌跡記錄階段主要記錄每條指令的寄存器和訪存信息??刂屏鬟€原階段通過對訪存信息進行分析,識別出VMCode所在內(nèi)存區(qū)域,獲取VMCode的執(zhí)行軌跡信息,然后還原程序的CFG。數(shù)據(jù)生成過程還原階段通過對輸出數(shù)據(jù)進行分層次、分階段數(shù)據(jù)流追蹤,獲取其生成過程。
2.1 動態(tài)執(zhí)行軌跡記錄
對于基于數(shù)據(jù)流分析的虛擬機逆破解方法而言,獲取真實可靠的進程動態(tài)執(zhí)行信息是重要的基礎(chǔ)環(huán)節(jié)。為此,筆者編寫了基于動態(tài)分析平臺 Pin的指令流記錄插件,記錄用戶指定程序片段在執(zhí)行期間的數(shù)據(jù)流信息。由于虛擬機中加入了大量垃圾指令,因此實際執(zhí)行到的指令條數(shù)往往規(guī)模龐大,為了提高效率,采用緩存延遲寫入技術(shù)將執(zhí)行期的每條指令的寄存器值和內(nèi)存讀寫信息記錄為二進制文件,供后期分析使用。
2.2 控制流圖還原
控制流圖還原的基本思路是虛擬機執(zhí)行過程包含了對VMCode的讀取和解釋執(zhí)行,通過對每條指令的訪存信息進行整理篩選,就能得到VMCode所在內(nèi)存區(qū)域,根據(jù)VMCode的讀取軌跡能夠部分地還原CFG,通過多次運行,增大路徑覆蓋率,最終完整地還原被保護算法的CFG。
定義2 虛擬機輸入數(shù)據(jù)(VMInput)
獲取虛擬機指令區(qū)域(VMInsRgn)就是對VMInput進行整理篩選的過程。VMInput由3個部分組成:虛擬機指令,堆棧中的臨時數(shù)據(jù),可執(zhí)行模塊中的相關(guān)數(shù)據(jù)。VMInsRgn滿足如下3個條件:包含于可執(zhí)行模塊中;包含于或與虛擬機解釋器所在的PE文件的節(jié)相鄰;被IDA靜態(tài)分析識別為數(shù)據(jù)。按照上述條件對 VMInput進行篩選,最終得到VMInsRgn<InsStartAddr,InsSize>,其中,InsStartAddr是區(qū)域的起始地址;InsSize是區(qū)域大小。
在定位VMInsRgn后,將對此區(qū)域進行的讀操作視為虛擬機指令讀取,因此,對此區(qū)域的內(nèi)存讀取軌跡的集合就是虛擬機指令的執(zhí)行軌跡,記作traces,每一條執(zhí)行軌跡記作trace<StartAddr,EndAddr>,表示一串內(nèi)存空間連續(xù)的虛擬機指令被讀取, StartAddr,EndAddr分別表示虛擬機指令起始、結(jié)束地址。生成traces的具體算法如下:
Step 1 將當前trace的StartAddr、EndAddr置為無效,取第1條指令的內(nèi)存讀取信息Rc<Addr, Size>,其中,Addr表示內(nèi)存的起始地址;Size表示大小。
Step 2 如果Rc與VMInsRgn滿足InsStartAddr≤Addr<(InsStartAddr+InsSize),轉(zhuǎn) Step 3,否則轉(zhuǎn)Step 4。
Step 3 上次讀取的虛擬機指令區(qū)域Rb與Rc是否滿足AddrRb+SizeRb=AddrRc,滿足則轉(zhuǎn)Step 4;否則EndAddrtrace=AddrRb+SizeRb,并開始一條新的軌跡trace_new,同時StartAddrtrace_new=AddrRc。
Step 4 指令分析是否結(jié)束,結(jié)束則算法結(jié)束,否則讀取下一條指令訪存信息存入Rc,轉(zhuǎn)Step 2。
定義3 虛擬機基本塊
一條順序執(zhí)行的Pcode序列,且只有一個入口和一個出口,入口是其中的第1條Pcode,出口是最后一條Pcode,記作VMBB<StartAddr,EndAddr>,其中,StartAddr和EndAddr表示虛擬機基本塊的起始和結(jié)束地址。
為了能夠重構(gòu)虛擬機指令的控制流,首先需要將TRACES劃分基本塊。根據(jù)基本塊的定義,首先將traces拆分,將拆分結(jié)果作為虛擬機指令的基本塊。劃分基本塊的算法如下:
Step 1 將一條trace<StartAddr,EndAddr>看做一個由虛擬機指令構(gòu)成的內(nèi)存區(qū)域 U <StartAddr,EndAddr>;
Step 2 將U1,U2,…,Um拆分為 VMBB1, VMBB2,…,VMBBn,使其滿足如下條件:
(1)對于? VMBBi和 VMBBj,滿足VMBBi∩VMBBj=?
(2)對?VMBBi,?Uj使得滿足以下任意一個:
Step 3 拆分后的VMBB1,VMBB2,…,VMBBn為虛擬機指令的基本塊。
如圖1所示,3條執(zhí)行軌跡U1,U2和U3,經(jīng)過拆分后得到 4個基本塊 VMBB1,VMBB2,VMBB3, VMBB4。
圖1 軌跡拆分為基本塊的過程
順著虛擬機指令執(zhí)行軌跡,在連續(xù)執(zhí)行的VMBB之間繪制有向邊,可以得到被保護算法的部分CFG。圖1經(jīng)過重構(gòu)之后到控制流圖(圖2),可以看到存在B2→B2和B2→B3的邊,可以推斷出B2的尾部存在條件分支跳轉(zhuǎn)語句。通過輸入不同數(shù)據(jù)增加路徑覆蓋率,能夠得到較完整的CFG。
圖2 控制流圖
2.3 數(shù)據(jù)生成過程還原
為了獲取被保護算法的輸入、輸出數(shù)據(jù)之間的運算關(guān)系,需要對輸出數(shù)據(jù)進行數(shù)據(jù)流追蹤,追蹤過程應(yīng)該結(jié)合虛擬機自身特點以及控制流信息來優(yōu)化追蹤過程,例如:虛擬機通常采用常數(shù)加密、垃圾指令混淆,因此實際執(zhí)行到的指令規(guī)模非常龐大,對整個執(zhí)行過程進行數(shù)據(jù)流追蹤的方法并不適用;對于被保護算法中調(diào)用的子函數(shù),虛擬機并不會對其進行保護,如以下代碼所示,如果VMProtectedFunc函數(shù)是被保護的函數(shù),函數(shù)中調(diào)用了func1,那么func1是不會被保護的,因此,對算法重構(gòu)來說,子函數(shù)并不需要進行數(shù)據(jù)流分析,只需要獲取函數(shù)輸入、輸出之間的關(guān)系;對于控制流中的循環(huán)結(jié)構(gòu),只需要分析1次;對于條件跳轉(zhuǎn)的分析,則需要首先定位虛擬機解釋執(zhí)行軌跡的差異點,然后進行反向追蹤。因此本文對數(shù)據(jù)生成過程的分析以VMBB為單位,采用分層次、分階段的方式進行,即根據(jù)控制流圖還原階段對程序中控制結(jié)構(gòu)如條件跳轉(zhuǎn)、循環(huán)結(jié)構(gòu)以及函數(shù)調(diào)用的識別結(jié)果,將反向數(shù)據(jù)流跟蹤過程劃分階段,以VMBB為分析單位,獲取程序?qū)?shù)據(jù)的處理過程,生成數(shù)據(jù)流傳播樹TPT<Node,Edge>,其中, Node是TPT中所有節(jié)點的集合,包含了污點源和指令操作數(shù);Edge是TPT的邊的集合,記錄了所有節(jié)點的上下級和邏輯運算關(guān)系。
由于虛擬機解釋器被高強度混淆,因此首先需要對數(shù)據(jù)流分析算法進行改進。常數(shù)加密是虛擬機中大量使用的混淆手段。Themida[11]虛擬機解釋器代碼中常見的指令序列如下:
指令序列1:
指令序列2:
如果對指令序列1進行反向數(shù)據(jù)流追蹤,并假定eax為污點源。經(jīng)過反向數(shù)據(jù)流追蹤最終得到如圖3所示的數(shù)據(jù)流傳播樹。顯然由于算法中的常數(shù)加密,導致樹的節(jié)點個數(shù)增多,同時樹的高度也增加了。同理,如果指令序列2進行數(shù)據(jù)流追蹤,并假定ecx為污點源,由于數(shù)據(jù)流分析并不分析每條指令的語義信息,最終會導致ecx與edx寄存器錯誤的關(guān)聯(lián)。
圖3 數(shù)據(jù)流傳播樹
由于虛擬機執(zhí)行過程中指令規(guī)模龐大,為減少數(shù)據(jù)流傳播樹的節(jié)點個數(shù),降低樹的高度,方便傳播關(guān)系的分析,有必要對這些指令序列進行處理。對于上述例子,在對指令序列1中的mov edx,ecx進行分析時,如果能夠識別出ecx的值為常數(shù),就不再需要對ecx進行污點分析;同理,對指令序列2中的sub ecx,edx進行分析時,如果能識別出ecx是常數(shù),則不會將ecx與edx關(guān)聯(lián)。為了應(yīng)對常數(shù)加密,引入常量識別算法,該算法以x86指令基本塊為單位,識別同一基本塊中的某條指令在多次執(zhí)行過程中的值是否為固定值。具體算法流程如圖4所示。
圖4 常量識別算法流程
除了常數(shù)加密,虛擬機中大量使用堆棧來存取、傳遞臨時數(shù)據(jù),存在大量類似如下的指令序列:
如果對edi進行反向數(shù)據(jù)流追蹤,最終由于數(shù)據(jù)的移動使樹的高度增加。通過對傳送類指令(如mov,push,pop,xchg等)進行處理,當分析該類指令時,并不增加新的葉子節(jié)點,只替換其父節(jié)點,就能有效地降低樹高。
引入常量識別和傳送類指令優(yōu)化后,設(shè)計針對虛擬機的反向數(shù)據(jù)流跟蹤算法,該算法首先將用戶指定的內(nèi)存區(qū)域標記為污點源,然后逆著程序的執(zhí)行軌跡進行污點傳播分析,最終生成一張TPT。該算法能夠解決污點源由哪些數(shù)據(jù)、經(jīng)過哪些運算產(chǎn)生等問題,算法流程如圖5所示。
圖5 數(shù)據(jù)流追蹤算法流程
本文基于Pin設(shè)計并實現(xiàn)了虛擬機保護算法的破解系統(tǒng)。系統(tǒng)的工作流程如下:
(1)在Pin的監(jiān)控下運行測試程序,通過執(zhí)行軌跡記錄模塊記錄指令的數(shù)據(jù)流信息。
(2)控制流還原模塊識別出虛擬機指令所在區(qū)域,提取虛擬機指令執(zhí)行軌跡信息,然后劃分VMBB并還原CFG。
(3)數(shù)據(jù)生成過程還原模塊輔助分析人員完成對數(shù)據(jù)的生成過程的逆向分析,由分析人員結(jié)合控制流圖和數(shù)據(jù)的生成過程對被保護算法進行重構(gòu)。
為了驗證該算法還原技術(shù)的有效性,本文通過Themida提供的SDK方式對一段算法進行虛擬機加殼保護,采用該技術(shù)進行還原。測試環(huán)境如表1所示。
表1 測試環(huán)境
使用Themida SDK方式對代碼進行虛擬化保護,只需要對被保護的源代碼加上起始標志VM_START和結(jié)束標志VM_END這2個宏,編譯生成可執(zhí)行程序之后,運行Themida進行加殼。測試代碼如下:
編譯生成的程序經(jīng)過IDA反匯編,結(jié)果如下:
采用 Themida默認的虛擬機保護設(shè)置,即Processor Type:Mutable CISC processor;Multiprocessor: 1 CPU;Opcode Type:Metamorphic-Level2;Dynamic Opcode:20%Dynamic對代碼進行虛擬機保護。
通過以下代碼調(diào)用函數(shù),并對VM_test函數(shù)進行動態(tài)軌跡記錄。分析記錄結(jié)果獲取虛擬機輸入數(shù)據(jù),結(jié)合IDA分析得到0x4f1ad6~0x4f5216為虛擬機指令所在區(qū)域。
char data[]="VM_test";
VM_test(data,strlen(data),true);
通過IDA反匯編原始x86指令得到被保護算法的CFG如圖6所示。經(jīng)過控制流還原,得到虛擬機指令的CFG,如圖7所示。
圖6 x86指令的控制流圖
圖7 虛擬機指令的控制流圖
對比 x86指令和虛擬機指令的 CFG,得到VMBB與x86指令基本塊的對應(yīng)關(guān)系,如表2所示。
表2 寄存器信息二進制文件格式
對算法的運算過程進行逆向,首先確定要分析的數(shù)據(jù)為pdata指向的最終輸出數(shù)據(jù)。對輸出的數(shù)據(jù)的第一個字節(jié)進行反向數(shù)據(jù)流追蹤,以虛擬機基本塊為單位分析輸入輸出數(shù)據(jù),確定數(shù)據(jù)的生成過程在基本塊0x4f4ee3~0x4f5197,起始和結(jié)束執(zhí)行指令序列分別為1847260和1986050。通過對此執(zhí)行序列范圍以內(nèi)的指令進行反向數(shù)據(jù)流追蹤,得到數(shù)據(jù)流傳播樹,如圖8所示,可以看出,數(shù)據(jù)只是進行了簡單的異或,同理可以還原其他基本塊中對輸出數(shù)據(jù)的處理過程。
圖8 數(shù)據(jù)流傳播樹
通過輸入不同數(shù)據(jù)覆蓋更多路徑,對記錄的執(zhí)行軌跡信息進行分析,最終得到程序的控制流。對0x4f4e2c~0x4f4ee2的幾次不同解釋執(zhí)行過程進行比對,找到差異點,進行反向數(shù)據(jù)流追蹤,可以得到循環(huán)次數(shù)與VM_test的第2個參數(shù)有關(guān)。結(jié)合控制流和虛擬機基本塊的逆向分析,最終能夠?qū)崿F(xiàn)對被保護算法的重構(gòu)。
本文以動態(tài)數(shù)據(jù)流分析技術(shù)為基礎(chǔ),提出一種針對虛擬機保護的破解方法,論述了基本原理和實現(xiàn)過程,并通過實例測試加以驗證。測試結(jié)果表明,該方法能夠?qū)Ρ槐Wo算法的控制流圖和數(shù)據(jù)生成過程進行有效還原,輔助分析人員完成對被保護算法的重構(gòu),通過提高被保護代碼的執(zhí)行覆蓋率,最終實現(xiàn)被保護算法的完整還原。后續(xù)改進工作包括:分析不同指令集和保護強度的虛擬機,給出更有針對性的逆向分析方法,并設(shè)計相應(yīng)的還原算法,實現(xiàn)對被保護算法更自動化的還原。
[1] 段 鋼.加密與解密[M].3版.北京:電子工業(yè)出版社,2009.
[2] Collberg C,Nagra J.Surreptitious Software:Obfuscation, Watermarking,and Tamperproofing for Program Protection[M].[S.l.]:Addison-Wesley Professional,2009.
[3] Sharif M,Lanzi A,Giffin J.Automatic Reverse Engineering of Malware Emulators[C]//Proc.of 2009 IEEE Symposium on Security and Privacy.Berkeley,USA: IEEE Press,2009:94-109.
[4] Rolles R.Unpacking Virtualization Obfuscators[C]// Proc.of WOOT'09.Montreal,Canada:[s.n.],2009:1.
[5] Coogan K,Lu Gen,Debray S.Deobfuscatiion Virtualization-obfuscated Software:A Semantics-based Approa-ch [C]//Proc.of CCS'11.Chicago,USA:ACM Presss, 2011:275-284.
[6] 陳火旺,劉春林,譚慶平,等.程序設(shè)計語言編譯原理[M].3版.北京:國防工業(yè)出版社,2007.
[7] Newsome J,Song D.Dynamic Taint Analysis for Automatic Detection,Analysis,and Signature Generation of Exploits on Commodity Software[C]//Proc.of NDSS'05. San Diego,USA:[s.n.],2005.
[8] Nethercote N.Dynamic Binary Analysis and Instrumentation or Building Tools Is Easy[D].Cambridge,UK: University of Cambridge,2004.
[9] Luk Chi-Keung.Pin:Building Customized Program Analysis Tools with Dynamic Instrumentation[C]//Proc. of PLDI'05.Chicago,USA:[s.n.],2005:190-200.
[10] Clause J,Li Wanchun,Orso A.Dytan:A Generic Dynamic Taint Analysis Framework[C]//Proc.of International Symposium on Software Testing and Analysis. London,UK:[s.n.],2007:196-206.
[11] Oreans Technologies:Themida[EB/OL].[2009-05-06]. http://www.oreans.com/.
編輯 金胡考
Reverse Technology of Virtual Machine Protection Based on Dynamic Dataflow Analysis
HUANG He-jie,KANG Fei,SHU Hui
(State Key Laboratory of Mathematical Engineering and Advanced Computing, PLA Information Engineering University,Zhengzhou 450000,China)
Traditional reverse analysis methods are not very effective in the analysis of the algorithms protected by virtual machine because of virtualization technology and code obfuscation technology.Aiming at this problem,this paper presents a virtual machine protection reverse engineering technique based on dataflow analysis.It uses Pin platform to record the data flow information during the execution of the protected algorithms dynamically,analyses the record information,restores the track of the virtual machine instructions and the control flow graph of the protected algorithms, gets data generation process hierarchically by using the track information.Then the analyzer uses those information to reconstruct the protected algorithms.Experimental results show that the proposed method can correctly restore the program control flow and data generation process,and assist the analyzer to reconstruct the protected algorithms.
dataflow analysis;virtual machine protection;control flow reduction;algorithm reduction
1000-3428(2014)09-0059-07
A
TP309
10.3969/j.issn.1000-3428.2014.09.013
國家保密局科研基金資助項目(BMKY2013B03-1)。
黃荷潔(1989-),男,碩士研究生,主研方向:網(wǎng)絡(luò)與信息安全;康 緋,副教授;舒 輝,副教授、博士。
2013-09-11
2013-11-02E-mail:cssembly@gmail.com