<span id="7ztzv"></span>
<sub id="7ztzv"></sub>

<span id="7ztzv"></span><form id="7ztzv"></form>

<span id="7ztzv"></span>

        <address id="7ztzv"></address>

            原文地址:http://drops.wooyun.org/tips/6814

            0x00 Mona 2 前言 & 準備


            Mona 2是一種非常有用的插件,它由Corelan Team開發。起初是為Immunity Debugger寫的,現在它適用于WinDbg調試器。

            你將需要為WinDbg x86 和 WinDbg x64安裝一些工具:

            安裝Python 2.7 (從這里可下載到) 。

            x86 和 x64版本的工具分別安裝在不同的目錄里,如c:\python27(32) 和c:\python27。

            這里下載正確的zip包(請下載pykd-0.2.0.29-python-2.7.zip這個壓縮包),接著提取并運行vcredist_x86.exe 和 vcredist_x64.exe。

            從這里下載兩個exe程序(x86版和x64版),接著執行它們。

            從這里下載windbglib.py和mona.py,并將它們放置到WinDbg.exe所在的目錄中。

            enter image description here

            配置符號搜索路徑如下:

            通過 File→Symbol File Path

            輸入

            SRV*C:\windbgsymbols*http://msdl.microsoft.com/download/symbols
            

            3.保存工作區(File→Save Workspace).

            在WinDbg下運行mona.py

            用WinDbg運行mona.py的范例:

            1.使用如下命令加載pykd插件

            .load pykd.pyd
            

            2.運行mona使用命令如下:

            !py mona
            

            enter image description here

            更新mona 輸入如下:

            !py mona update
            

            enter image description here

            0x01 配置


            工作目錄

            在mona的工作目錄里,mona的多數函數將數據轉儲到已創建的文件中。我們可以具體指定某個工作目錄,這取決于使用的格式說明符%p (process name) 和 %i (process id)指定的進程名和id。

            例如,輸入:

            workingfolder "C:\mona_files\%p_%i"
            

            排除模塊

            你可以用如下操作排除指定模塊:

            !mona config -set excluded_modules "module1.dll,module2.dll"
            !mona config -add excluded_modules "module3.dll,module4.dll"
            

            作者

            你也可以設定作者:

            !mona config -set author Kiuhnm
            

            當產生與metasploit兼容的輸出內容時可以使用該信息。

            重點

            如果WinDbg和mona都沒有出錯,那么請試試以管理員身份運行WinDbg。

            0x02 Mona的手冊


            你可以在這里找到更多關于Mona的信息。

            范例

            該范例引用自Mona的手冊. 現在來說明如下代碼中我們控制的ECX的值:

            MOV   EAX, [ECX]
            CALL   [EAX+58h]
            

            我們想要使用那段代碼以jmp到我們的shellcode(即我們注入到進程中的代碼),它的地址位于ESP+4,因此我們需要調用如上調用的一些指令,如“ADD ESP, 4 | RET“。上面的代碼有許多間接的操作:

            (ECX = p1) → p2
            p2+58h → p3 → “ADD ESP,4 | RET”
            

            首先我們需要找到p3:

            !py mona config -set workingfolder c:\logs
            !py mona stackpivot -distance 4,4
            

            如上使用的命令可以讓你在stackpivots內的指定偏移范圍在mix~max之間找到等價于ADD ESP, X | RET代碼的指針,通過選項-distance min,max來指定偏移范圍。

            已發現指針/地址會被寫入到c:\logs\stackpivot.txt

            現在我們已經有我們的p3指針(許多p3指針!)了,我們還需找到p1:

            !py mona find -type file -s "c:\logs\stackpivot.txt" -x * -offset 58 -level 2 -offsetlevel 2
            

            下面來了解那些選項的含義:

            使用“-x *”選項意味著你要 “accept addresses in pages with any access level” (正如另一個范例所示, 用 “-x X”選項說明我們僅在可執行頁中定位).

            “-level 2”具體指定要間接操作的指令層級,它告知mona找出“a pointer (p1) to a pointer (p2)to a pointer (p3)”。 前兩個選項 (-type 和 -s)指定ps必須是指針,它被列出在文件“c:\logs\stackpivot.txt“里。

            使用“-offsetlevel 2” 和 “-offset 58”選項告知mona用偏移58h來進行增值操作時,第二個指針(p2)必須指向第三個指針(p3)。

            如果這個范例并不能讓你對其內容有較好的理解,請你不要擔心。這個范例僅向你展示了WinDbg中利用Mona插件可以實現的一些功能。當然,我也承認這個命令的語法不是非常易懂。

            范例

            使用findwild命令可以讓你找到帶有特殊形式的指令鏈。 細想如下范例:

            !mona findwild -s "push r32 # * # pop eax # inc eax # * # retn"
            

            選項”-s”指定鏈的形態:

            用 ‘#‘將指令分隔開

            r32 為任意32位寄存器

            可選參數為:

            ROP鏈

            Mona可以找到ROP gadgets并利用它們構造ROP鏈,但是我將不在這部分講解這方面的相關內容,因為這里我假設你并不知道ROP鏈的含義及關于ROP的概念。正如我曾說過的,如果這篇文章講述的內容讓你難以理解,那么請不要擔心。盡管學習該系列的下一部分文章吧。

            0x03 結構化異常處理(SEH)


            異常處理器以一種單鏈表的形式存在,它和每個線程有關。一般說來,鏈表的節點被分配在棧上。某一位于TEB (Thread Environment Block)的起始位置的指針指向鏈表頭,因此當代碼想要添加一個新的異常處理器時,某一新節點會被添加到鏈表頭并且在TEB里的指針所指向的位置會被改變,進而指向新節點。

            每個節點固有_EXCEPTION_REGISTRATION_RECORD類型并且會存儲處理器的地址及鏈表下個節點的一個指針。奇怪的是,鏈表上一節點的“next pointer”不是null但是它等價于0xffffffff。

            確切的定義如下:

            0:000> dt _EXCEPTION_REGISTRATION_RECORD
            ntdll!_EXCEPTION_REGISTRATION_RECORD
               +0x000 Next             : Ptr32 _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : Ptr32     _EXCEPTION_DISPOSITION
            

            TEB可被段選擇子fs訪問(始于 fs:[0]), 因此通常可看到代碼如下:

            mov    eax, dword ptr fs:[00000000h]      ; retrieve the head
            push   eax                                ; save the old head
            lea    eax, [ebp-10h]
            mov    dword ptr fs:[00000000h], eax      ; set the new head
            .
            .
            .
            mov    ecx, dword ptr [ebp-10h]           ; get the old head (NEXT field of the current head)
            mov    dword ptr fs:[00000000h], ecx      ; restore the old head
            

            編譯器通常會注冊單個全局句柄,它能意識到被程序執行過的區域(這依賴于某一全局變量)并且當它被調用時會有根據地作出行為。

            因為每個線程都有一個不同的TEB,因此操作系統會確保段被fs選擇,fs總會引用準確的TEB(即當前線程之一)。 通過讀取與TEB的Self區域相符的 fs:[18h]得到TEB的地址。

            列出TEB的信息如下:

            0:000> !teb
            TEB at 7efdd000
                ExceptionList:        003ef804          -----------------------
                StackBase:            003f0000
                StackLimit:           003ed000
                SubSystemTib:         00000000
                FiberData:            00001e00
                ArbitraryUserPointer: 00000000
                Self:                 7efdd000
                EnvironmentPointer:   00000000
                ClientId:             00001644 . 00000914
                RpcHandle:            00000000
                Tls Storage:          7efdd02c
                PEB Address:          7efde000
                LastErrorValue:       2
                LastStatusValue:      c0000034
                Count Owned Locks:    0
                HardErrorMode:        0
            

            現在我們可以證實fs引用TEB:

            0:000> dg fs
                                              P Si Gr Pr Lo
            Sel    Base     Limit     Type    l ze an es ng Flags
            ---- -------- -------- ---------- - -- -- -- -- --------
            0053 7efdd000 00000fff Data RW Ac 3 Bg By P  Nl 000004f3
            

            正如我們在之前講述過的, fs:18h含有TEB的地址:

            0:000> ? poi(fs:[18])
            Evaluate expression: 2130563072 = 7efdd000
            

            記住:poi會對某一指針進行解引用操作并且使用‘?’來對某一表達式進行求值操作。 我們看看ExceptionList 指向的結構體名:

            0:000> dt nt!_NT_TIB ExceptionList
            ntdll!_NT_TIB
               +0x000 ExceptionList : Ptr32 _EXCEPTION_REGISTRATION_RECORD
            

            正如我們已經說過的那樣,這意味著每個節點會是_EXCEPTION_REGISTRATION_RECORD的某一實例。使用!slist命令展示出整個鏈表的信息:

            0:000> !slist $teb _EXCEPTION_REGISTRATION_RECORD
            SLIST HEADER:
               +0x000 Alignment          : 3f0000003ef804
               +0x000 Next               : 3ef804
               +0x004 Depth              : 0
               +0x006 Sequence           : 3f
            
            SLIST CONTENTS:
            003ef804
               +0x000 Next             : 0x003ef850 _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : 0x6d5da0d5     _EXCEPTION_DISPOSITION  MSVCR120!_except_handler4+0
            003ef850
               +0x000 Next             : 0x003ef89c _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : 0x00271709     _EXCEPTION_DISPOSITION  +0
            003ef89c
               +0x000 Next             : 0xffffffff _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : 0x77e21985     _EXCEPTION_DISPOSITION  ntdll!_except_handler4+0
            ffffffff
               +0x000 Next             : ???? 
               +0x004 Handler          : ???? 
            Can't read memory at ffffffff, error 0
            

            記住$teb表示的是TEB的地址.

            以下使用了一種更簡潔的方法來展示異常處理鏈的信息:

            0:000> !exchain
            003ef804: MSVCR120!_except_handler4+0 (6d5da0d5)
              CRT scope  0, func:   MSVCR120!doexit+116 (6d613b3b)
            003ef850: exploitme3+1709 (00271709)
            003ef89c: ntdll!_except_handler4+0 (77e21985)
              CRT scope  0, filter: ntdll!__RtlUserThreadStart+2e (77e21c78)
                            func:   ntdll!__RtlUserThreadStart+63 (77e238cb)
            We can also examine the exception handler chain manually:
            0:000> dt 003ef804 _EXCEPTION_REGISTRATION_RECORD
            MSVCR120!_EXCEPTION_REGISTRATION_RECORD
               +0x000 Next             : 0x003ef850 _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : 0x6d5da0d5     _EXCEPTION_DISPOSITION  MSVCR120!_except_handler4+0
            0:000> dt 0x003ef850 _EXCEPTION_REGISTRATION_RECORD
            MSVCR120!_EXCEPTION_REGISTRATION_RECORD
               +0x000 Next             : 0x003ef89c _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : 0x00271709     _EXCEPTION_DISPOSITION  +0
            0:000> dt 0x003ef89c _EXCEPTION_REGISTRATION_RECORD
            MSVCR120!_EXCEPTION_REGISTRATION_RECORD
               +0x000 Next             : 0xffffffff _EXCEPTION_REGISTRATION_RECORD
               +0x004 Handler          : 0x77e21985     _EXCEPTION_DISPOSITION  ntdll!_except_handler4+0
            

            <span id="7ztzv"></span>
            <sub id="7ztzv"></sub>

            <span id="7ztzv"></span><form id="7ztzv"></form>

            <span id="7ztzv"></span>

                  <address id="7ztzv"></address>

                      亚洲欧美在线