GDB是GNU開源組織發佈的一個強大的UNIX下程序調試工具。SylixOS中除Lite版本外,均可以實現GDB調試功能。 GDB能夠對C和C++程序進行調試,它使用戶能在程序運行時觀察程序的內部結構和內存的使用狀況。如下是GDB所提供的一些功能:數組
GDB由gdb-server和gdb-host組成。 目標板使用gdb-server來啓動已經編譯好的代碼,執行斷點、單步等調試動做,同時經過網絡、串口等反饋調試須要的信息給gdb-host。 宿主機上運行gdb-host,解析gdb-server傳來的信息,同時,發送斷點、單步等動做給目標板。網絡
在SylixOS中,gdb-server的主要通訊流程和網絡通訊框架,已經在Base中實現,代碼位置以下圖所示。 架構
這部分代碼邏輯中,已經完成和gdb-host的通訊邏輯。當在RealEvo-IDE中的Debug界面,進行單步,運行到指定行,全速運行等操做時,gdb-host實際經過對應架構的xxxx-sylixos-elf-gdb.exe工具與板卡內的gdb-server進行通訊。框架
在每一個具體架構中,都存在dbg目錄,該目錄下對應有xxxDbg.c和xxxGdb.c文件,以及xxx_gdb.h文件,以下圖所示。ide
xxx_gdb.h中主要實現與GDB相關的結構體變量定義和函數聲明。 好比,在AARCH64中,xxx_gdb.h 中對 GDB 相關結構體的定義以下程序清單所示:函數
/*************************************************************************** 最大寄存器數 ***************************************************************************/ #define GDB_MAX_REG_CNT 34 /*************************************************************************** 寄存器集合結構 ***************************************************************************/ typedef struct { INT GDBR_iRegCnt; /* 寄存器數量 */ struct { ULONG GDBRA_ulValue; /* 寄存器值 */ } regArr[GDB_MAX_REG_CNT]; /* 寄存器數組 */ } GDB_REG_SET;
在該結構體中須要定義gdb-server監控和傳輸的寄存器數量,以及爲每一個寄存器分配存儲的空間。監控和傳輸的寄存器數量,由GNU官方定義。好比在GNU提供的AARCH64 gdb說明中,其對org.gnu.gdb.aarch64.core的定義以下:工具
xxxGdb.c 中必須實現以下圖所示的接口。fetch
在xxxGdb.c中定義了兩個描述 xml 結構的全局變量,分別爲CoreXml和TargetXml的描述,這兩個描述類型均可以從GNU查詢到。
指針
須要實現接口中的archGdbCoreXml和archGdbTargetXml就是分別返回這兩個結構的函數實現。 archGdbRegsGet和archGdbRegsSet分別用於返回寄存器結構的狀態,以及對寄存器結構中的狀態值進行設置,經過這兩個函數,就能夠在IDE中監測和設置對應的寄存器值。 archGdbRegSetPc、archGdbRegGetPc和archGdbGetNextPc 是對PC指針的獲取和設置,其中archGdbRegSetPc和archGdbRegGetPc就是單獨對寄存器結構中的PC值進行設置和獲取。 archGdbGetNextPc是單步調試重點須要實現的邏輯。此段代碼邏輯中,須要針對異常分支、直接設置PC、函數返回等多種狀況下,Next PC的邏輯進行考慮和實現。調試
xxxDbg.c 中必須實現以下圖所示的接口。
archDbgAbInsert用於實現斷點插入的邏輯。斷點插入的實現思路是,在須要產生斷點的位置,替換一條斷點指令。這樣當程序運行到斷點處時,就會進入斷點異常,在斷點異常的處理流程中,向gdb-host發送寄存器狀態。 archDbgBpRemove 、archDbgBpPrefetch 和 archDbgBpAdjust 都是對斷點的通用處理,基本上各個架構實現的方式都類同。
此外,在RealEvo-IDE的安裝目錄「RealEvo\ide\tools\gdb」內須要根據具體的架構,預先建立一個gdbinit.txt文檔。 不然,在IDE中啓動gdb程序時,會出現異常。