本文默認讀者已安裝所有必要工具,如果還不熟悉,建議先參考以下文章:
Ghidra 逆向實戰|STM32(ARM) MCU 韌體逆向工程 : 工具說明本實做將以 STM32H7A3 系列微控制器為範例,示範如何在 Ghidra 中進行無符號表(Symbol-less)韌體靜態分析,方法不分先後,依照實際需求與情況選擇適合的步驟進行。這些方法可協助使用者在缺乏符號表的情況下,仍能有效地進行韌體分析。
注意事項:
在韌體中,字串常數(如 ASCII 或 Unicode 格式)常見於除錯訊息、錯誤提示、人機介面標示等。若編譯時未移除這些資訊,便能在韌體中直接找到相關字串。
這些字串對逆向工程極為有用,不僅能協助判斷韌體所用的架構或函式庫,還能快速定位程式碼中調用這些字串的位置,是分析流程的重要切入點。
Window → Defined Strings 功能,快速檢視與搜尋所有字串常數,並追蹤其被調用的程式區段。
在韌體中,啟動入口(如 Reset_Handler)與 中斷向量表
是韌體執行的起點。這些區域通常包含初始化程式碼、系統設定與中斷處理程式等。而這些位置的程式碼通常會在韌體啟動時被執行,因此可以作為分析的起點。
不同架構中斷向量表的位置與格式可能有所不同,但通常會包含一系列的函式指標,指向各種中斷服務程式(ISR)或系統呼叫。在 ARM Cortex-M 架構中,中斷向量表規定位於韌體開頭(例如 STM32 通常從 0x08000000 開始,這是由於重定向和偏移),格式如下:
Offset 內容
0x00 初始堆疊指標(Initial Stack Pointer)
0x04 Reset_Handler(重設處理函式)
0x08 NMI_Handler(不可屏蔽中斷)
0x0C HardFault_Handler
0x10 MemManage_Handler
0x14 BusFault_Handler
0x18 UsageFault_Handler
... 其他中斷服務程式(ISR)指標
這些指標實際上是函式位址,Ghidra 可自動辨識並標註為函式。啟動時便是從 Reset_Handler 開始,追蹤其初始化流程與主程式流向。
附註:
Reset_Handler、SVC、PendSV、SysTick,因為這些 ISR
服務被用於 RTOS 的上下文切換、排程與任務。
在 Ghidra 逆向韌體時,標記 ISR(中斷服務函數)是分析的重要一步,以下以 STM32/ARM MCU 為例,說明實際操作流程:
Data → Pointer 或使用快捷鍵 'p' 進行手動標記(請注意 Initial Stack Pointer 是
uint 或 dword)。
Function → Create Function,讓 Ghidra
將該位址標記為一個函式。
Edit Function,輸入正確的函式名稱(如
Reset_Handler、SysTick_Handler 等),並可加上註解說明其用途。
Window → Function Graph 或
Window → Function Call Tree,分析其內部邏輯與呼叫關係。
Window → Symbol Tree 快速檢查所有已建立的函式,或用 Window → Defined Strings
搜尋相關字串輔助判斷。
SVC、PendSV、SysTick 這三個與 RTOS 核心功能高度相關的 ISR。
即便沒有符號表,依然可從程式流與常數變數中進行逆向工程判斷。韌體架構主要分為 裸機(Bare-metal) 與 RTOS(即時作業系統) 兩大類型。此判斷將直接影響後續的分析策略。
main() 函式,初始化後進入明顯的大型無限迴圈(如 while(1))。SVC、PendSV、SysTick)包含複雜控制流程,負責上下文切換與任務排程。0xE000ED04 (此位址為 ARM 架構專用的中斷控制暫存器 ICSR)觸發 PendSV
中斷,或強制「軟體內」觸發計時器等外設中斷。FreeRTOS、RTX、ThreadX 等關鍵字,可大概率判定 RTOS 類型。Kernel、Thread、task、Queue 等關鍵字,可判定存在
RTOS。0xE000ED04 (ICSR)(此位址為 ARM 架構專用的中斷控制暫存器)觸發
PendSV,或強制觸發計時器等外設中斷。這些多為 RTOS 系統調用與任務切換。(這種方法還能找出 RTOS 的部分函數位址)
SVC、PendSV、SysTick 等 ISR
的程式流。若這些中斷服務程式包含複雜控制流程(極可能是:上下文切換、排程、系統呼叫),多半為 RTOS 架構;若未使用或邏輯簡單,則偏向裸機。
FreeRTOS、RTX、ThreadX 等關鍵字。這些字串通常會以常數形式存在,若發現則高度懷疑採用對應
RTOS。此外,Kernel、Thread、task、Queue 這些關鍵字也可用來判斷是否存在
RTOS。
當完成基本架構分析後,利用 BinDiff 這類二進位比對工具,搭配官方 HAL 層範例程式碼 或已知韌體版本,建立「參考檔案」進行比對。
具體步驟如下:
BinExport 外掛 (BinDiff 通常是獨立工具)。File → Export Program,選擇 BinExport 格式,匯出兩個檔案。