1. 程式人生 > >0day 第10章--10.3:覆蓋虛擬函式突破GS

0day 第10章--10.3:覆蓋虛擬函式突破GS

實驗環境:winxp sp3 vs2010
實驗要求:程式要求禁用優化、release版本

實驗原理:程式只有在函式返回時才檢查Security Cookie,如果在函式檢查之前劫持程式流程,就能實現緩衝區溢位了!因此可以利用C++中的虛擬函式!(為什麼?見0day第6章攻擊C++虛擬函式)

[C++虛擬函式原理]
{虛表指標->虛表->函式地址,call函式地址}

總結一下入的坑:
(1) 原理搞不懂
通過傳參,覆蓋的是虛表指標中的內容,即虛表,而不是將虛表中的內容覆蓋成shellcode地址(第6章才是這樣!),因此還需要經過一次呼叫。
實驗資料:傳入的引數地址:0x00402108;
buf的地址:0x0012FE9C;
虛表指標:0x0012FF78(0x004021D8)
虛表:0x004021D8(0x004010A0)
Call 0x004010A0
這裡buf地址和虛表指標相差了0x0012FF78-0x0012FE9C=220個位元組,因此我們需要填充220個位元組;
將虛表指標中的內容,即虛表覆蓋為引數地址。這樣我們傳入的引數地址前4個位元組必須是指向shellcode;

這裡我們沒有直接將前4個位元組覆蓋為shellcode地址,而是用到了pop pop ret指令作為跳板!
① 為什麼不用jmp esp作跳板地址?
因為所有的暫存器都不能調到0x00402108或者0x0012FE9C
0x00402108地址不在堆疊中,所以跳不過去

② 為什麼不把前4個位元組覆蓋為shellcode地址?
因為shellcode地址有字串“\x00”,會被截斷!

執行完pop pop ret指令後,程式會直接跳轉到0x0012FEC執行shellcode!
為什麼???

(2) pop pop ret指令找不到
用網上編寫的也就是書中第3章的查詢指令的c程式碼,vs各種報錯。。。
用Immunity Debugger的mona外掛從ntdll.dll、kernel32.dll、user.dll等各種dll中查詢依然找不到。。。
最後終於利用findjmp.exe在ntdll.dll中找到了!
但是一開始用的是pop esi pop ebp ret指令一直報錯。。。網上查資料發現利用的pop pop ret不能影響程式的流程,而pop ebp會破壞堆疊導致平衡破壞,影響程式流程。
① 用錯誤的pop指令0x7C9333A1
在這裡插入圖片描述


在這裡插入圖片描述
果然是因為破壞了ebp嗎?值得商榷?????????
7C99333A1指令和右面的FC一起被解析成mov eax,dword ptr ds:[0xfc7c9333]了,於是報訪問內容錯誤!
在這裡插入圖片描述
在這裡插入圖片描述
②正確的分析在後面,此處略。

(3) 程式pop pop ret後會調到buf的初始位置,而不是buf中去掉跳板地址的後4個位元組處
而這樣就把pop pop ret跳板地址當作指令執行了,這樣沒關係嗎??
事實證明沒有關係!

分析程式:
最終程式:
在這裡插入圖片描述
OD載入執行,在字串OK處下斷,找到傳入的引數地址0x00402108
在這裡插入圖片描述
F7進入,單步,執行到strcpy結束處,發現buf的地址為0x0012FE9C
在這裡插入圖片描述


此時觀察右下角堆疊圖,這時虛表指標為0x0012FF78,而我們已經將它的內容覆蓋為引數地址0x00402108
在這裡插入圖片描述
F7繼續,果然程式call [0x00402108中的內容]=0x7C973F65
在這裡插入圖片描述
繼續單步進入,此時0x0012FE9C距離棧頂3個位元組,因此2次pop後,將執行0x0012FE9C中的內容
在這裡插入圖片描述
單步繼續,程式果然執行0x0012FF9C中的內容了!
在這裡插入圖片描述
F9執行,果然出現彈框了!
在這裡插入圖片描述