TeamT5 Security 培訓後筆記 — Windows Reversing

第一部曲

Wei zen Liu
Dennisliuu 筆記空間
12 min readFeb 12, 2021

--

由於培訓內容實在太扎實太精彩了,在結束之後我打算開始重新讀重新實作,並且延伸一點內容之後,打成一篇文章。由於每天的內容很多,因此決定弄成一個系列文,這是整個培訓的第一天。一開始當然就先基本介紹 TeamT5 有多猛,然後正式步入第一天的內容 — Windows reversing

Windows PE Structure

什麼是 PE ? Portable Executable 是一種在 Windows 上的檔案格式,用於 *.exe, *.obj, *.dll 的文件格式,主要使用在32位元和64位元的 Windows 上。PE 文件格式封裝了 Windows 作業系統加載執行程式時所必需的一些訊息:

其中,MS-DOS header 有兩個重要成員:e_magic, e_lfanew.

e_magic 是主要是用來存放 MS-DOS Header 的簽章,所有兼容於 DOS 格式的 PE 檔其值皆會被設為0x5A4D,也就是 ASCII 的 MZ

e_lfanew則是 4-byte signature 的一個偏移量,該偏移量表示PE Header的偏移位置,它位於PE檔0x3C的位置,所以我們可以透過這個偏移值 (0x3C) 來找到PE檔內的PE Header。

MS-DOS header 與 MS-DOS stub 只存在 image file。因此在 MS-DOS 下運行該應用程式,默認的 Stub 會印出 “This program cannot be run in DOS mode”。

PE 格式是由 Unix 的 COFF 格式修改來的,其格式如下:

COFF File Header (Object and Image) 是在 object file 一開始前,規範一組格式,格式內容可以參見這裡,這邊列幾個特別可以注意一下的。如 Machine offset=0 會表示該程式在哪個系統架構下執行,如 0x8664 為 x64 系統、0x5064 為 RISC-V 64-bit 等。 而 TimeDateStamp offset=4 則紀錄了 compile time (unix time)。後續會提及 CFF Explorer 並手動修改。

再進入 PE 分析工具前,以下先列出一些有趣的 Windows API。

Win32 API

想要了解 Windows 系統架構和底層技術,可以讀 Windows Internals Book

API Function 名稱結尾的 A 和 W 代表 string 被處理的方式,ANSI (narrow, 8-bit)、Unicode (wide, 16-bit)。Function 名稱結尾可能有 Ex,通常是比較新的 API call,避免改了一個 API 導致向下不兼容。

重點 API:

Memory APIs (Kernel32)

  • VirtualAlloc: 分配一塊記憶體,可以注意這塊記憶體的權限 (RWX)
  • VirtualProtect: 可以變更一塊記憶體的權限 (如:修改記憶體 RW 變成 RWX)
  • WriteProcessMemory: 可以將記憶體寫入目標 process,一般程式少用,可作 shellcode injection

Library APIs (Kernel32)

  • LoadLibrary: 有時候惡意程式不會直接 call 某些 function,而是用 LoadLibrary 動態載入
  • GetProcAddress: 從目標 dll 取出 exported function 和 variable 來避免被掃出有使用可能有惡意的 API

Service APIs (Kernel32) 需有系統管理員權限

  • OpenSCManager (A/W)
  • StartService (A/W)
  • (Open/Control/Delete) Service
  • SetServiceStatus

Kernel APIs (Kernel32)

  • Sleep: Anti-dynamic-analysis or anti-sandbox
  • IsDebuggerPresent/CheckRemoteDebuggerPresent: 檢查有沒有使用 debugger

Crypto APIs (advapi32)

  • CryptGetProvParam
  • CryptAcquireContext (A/W)
  • 可以注意加密方法:如 PROV_RSA_FULL, PROV_RSA_AES,
  • Crypt (Encrypt/Decrypt)
  • Crypt (Derive/Import)Key

Filesystem APIs (Kernel32)

  • (Read/Create/Delete) File (Ex)
  • (Create/Delete) Directory (A/W)
  • Find(First/Next) File (A/W)
  • Used to enumerate directories
  • GetTempPath (A/W)
  • Return a temporary file to r/w

Process APIs (Kernel32)

  • CreateToolhelp32Snapshot
  • Used to get all running processes
  • CreateProcess (A/W)
  • TerminateProcess
  • CreateRemoteThread (Ex)
  • Can be used to start previously injected shellcode.
  • CreateThread

Registry APIs (advapi32)

  • Reg (Open/Create/Delete) Key (Ex) (A/W)
  • Reg (Get/CreateKey/DeleteKey/Delete) Value (Ex) (A/W)
  • Retrieve information about the environment.

Network APIs (WinINet)

  • InternetOpen (A/W)
  • InternetOpenUrl (A/W)
  • InternetConnect (A/W)
  • InternetReadFile (Ex) (A/W)
  • HttpOpenRequest (A/W)

Network APIs (winsock2)

  • WSAStartup/WSaCleanup
  • accept/connect/recv/send
  • gethostname/gethostbyname/getaddrinfo
  • Can be used to retrieve local IP/device name

PE Inspection

靜態惡意程式的分析,可以先從觀察 PE header 開始,透過某些特徵快速辨別是否為惡意程式,有鑒於每個檔案都直接使用 xxd, objdump 太麻煩,因此可以先用以下這些工具快速檢測:

pestudio

pestudio 為一個整合型的工具,內建基本的分析規則,並結合 virustotal 快速掃瞄,紅色、橘色代表值得注意的地方。而在 libraries 及 imports 的分類中,可以觀察程式所引用的函數,但若 import 為 0 表示動態載入,一般人不會這麼做,因此也是值得觀察的地方。另一個可以觀察的地方是 strings,可以掃描出程式中的 strings。有趣的是,通常執行在 linux/unix 上的 malware,strings 經常可以直接找出 C2 (Command and Control)。

注意,倘若檔案為 Read-only 則有很高機會是 marwale,因為一般程式不會只有讀取,而沒有任何與使用者的互動。

CFF Explorer

另一個 Explorer suite 中的 CFF Explorer,其功能包含可以看 header/import/export/read/write 等,還可以在 “Option Header” 的 “DllCharacteristics”,透過將 “DLL can move” 選項取消來 disable ASLR,並幫助進行靜態分析。

Detect it easy

最後一個也是很多人用的:Detect it easy,簡稱為 DIE。其功能也是很方便,可以看各種資訊,包含加殼,原始碼,甚至有修改的功能。此外也提供可以看 Entropy,如果兩個程式的 entropy 很像,那可能代表兩個程式內容雷同,甚至表示有相同的惡意程式藏在其中。而若 entropy 很高,則可能代表被加密或加殼過。

Disassembler & Decompiler tools

Hex-rays IDA Pro

貴(可以自行尋找綠色版),但功能強大,也能裝很多的擴充:

  • F5 顯示 pseudocode
  • X 跳到 xref
  • N 重新命名
  • Y 設定 type
  • G 跳到指定位子
  • Shift + F12 顯示String
  • 可以開雙視窗 右鍵選 Sync with …
  • 可以讓ASM跟虛擬碼對照著看,而且自動滑動

Ghidra

由美國 NSA 開源,雖使用 JDK,但有很多小巧思,減少 JDK 可能的漏洞

Cutter

原本是要做 radare2 的介面,最後自己幹出功能,背後跟 Ghidra 同一套 decompiler,好看!

  • Install: brew install gettext && brew install --cask cutter

Debugging in Windows

通常為了逃避正常靜態分析軟體如 IDA Pro,可以根據 import address table 得知呼叫過程或是把斷點下在GetProcessAddress 的 API import,就可以不用去管如何動態產生某些被 import 的東西,直接抓結果即可。

透過開啟 Process explorer 或 Process hacker,可以觀察有很多 services 如 svchost 一直執行,windows 中這些可能都跟其他程式一起共享資源,因此不建議直接關掉,可能會造成多個程式一起被終止。

Registry,登入檔,幾個有趣的點如:

  • Computer\HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows\CurrentVersion\Run
  • HKEY\LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Run

以上皆為開機時會自動啟動的點,除開機外,另一個有趣的觀察點為 Hardware vendor。假如使用虛擬機時,Registry 為記錄為 VBOX 或 VMWare 根據不同 VM 環境,也就是說,當 malware 發現這些 key 時,可能自動轉為 sleep 狀態,以避免被發現。

  • Computer\HKEY_LOCAL_MACHINE\HARDWARE\ACPI\DSDT\VBOX__

在 windows 上進行動態分析,有許多有 GUI 的工具。如 x64dbg,現代版的 OllyDbg,能在 32/64 位元上執行,並能自行增加 plug-in,甚至建立斷點 (bp) 或顯示 stack 中資料 (logstack)。Windbg 由微軟設計,更能在 kernel-level 上去做動態分析,但學習曲線較高。最後是 radare2,開源工具,雖然功能強大、能結合許多功能工具等,但學習曲線非常高。後面範例會用到 x64dbg。

x64dbg 快捷鍵:

  • F7 下一步 (Function 會進入)
  • F8 下一步 (Function 會直接執行完不進入)
  • F9 Run 到斷點或是程式執行完
  • F2 設置斷點
  • 指令 bp Sleep就可以把 Sleep 下斷點
  • ScyllaHide 反反反編譯程式

由於第一天內容實在太扎實了,所以決定拆成三部分,最下面有連結可以看~

--

--

Wei zen Liu
Dennisliuu 筆記空間

Front-end developer / Mobile application developer, Study in NTUT. Skills: Html / SCSS / Javascript(es6) / gulp.js / Vue.js / Git / bash / linux / C / C++ /