Linux Kernel Hacking With KGDB in VMWARE在VMWARE中使用KGDB進行源碼級Linux核心調試 CopyRight By MikeFeng [環境] VMWARE 5.5 Windows XP SP2(可替換)虛擬機器Ubuntu 6.06 (被調試機) 虛擬機器Kubuntu 6.10 (調試機,可替換為其他linux作業系統)[工具] KGDB 2.4[核心] 2.6.15.5 + KGDB 2.6.15.5補丁[目的] 對Linux 2.6核心進行源碼級調試,就像windbg一樣。
1.準備工作
使用vmware安裝Ubuntu6.06和KUbuntu6.10(可替換為其他linux作業系統)。 在kgdb官方網站下載linux-2.6.15.5.tar.bz2和linux-2.6.15.5-kgdb-2.4.tar.bz2,將這些source移至/usr/src並且解包。因為Ubuntu 6.06的核心是2.6.15的,因此核心編譯成功性稍大一點,推薦在Ubuntu 6.06上進行編譯。 linux-2.6.15.5-kgdb-2.4.tar.bz2中含有對linux-2.6.15.5的kgdb補丁,推薦按照以下順序用patch命令打補丁(假設你裝的是32位的ubuntu):cd /usr/src/linux-2.6.15.5patch –p1 < ../linux-2.6.15.5-kgdb-2.4.tar.bz2/core-lite.patchpatch –p1 < ../linux-2.6.15.5-kgdb-2.4.tar.bz2/core.patchpatch –p1 < ../linux-2.6.15.5-kgdb-2.4.tar.bz2/i386-lite.patchpatch –p1 < ../linux-2.6.15.5-kgdb-2.4.tar.bz2/ i386.patchpatch –p1 < ../linux-2.6.15.5-kgdb-2.4.tar.bz2/ 8250.patch其他補丁可以不用打。
2.編譯核心
Make menuconfig,按照KGDB官方網站上的說明文檔配置必要的KGDB選項。注意將預設的串口1改為0。這個在make menuconfig的過程中不能更改,可以通過make oldconfig進行互動式配置更改,也可以在make menuconfig之後編輯kernel source目錄下產生的.config檔案,確保關於kgdb的配置如下(特別是最後一句)CONFIG_KGDB_8250_NOMODULE=yCONFIG_KGDB_8250=yCONFIG_KGDB_SIMPLE_SERIAL=yCONFIG_KGDB_BAUDRATE=115200CONFIG_KGDB_PORT_NUM=0然後就是編譯了。編譯能否成功除了看人品之外,還需要注意別用版本太高或者太低的gcc編譯器。據說4.1版本的gcc加入了堆疊溢位保護的功能,如果碰到堆棧什麼符號未定義之類的錯誤,那麼先確認自己的gcc版本是不是太高了。使用debian特有的命令進行編譯配置,大致流程如下。不推薦直接用make,配置起來麻煩。make-kpkg cleanfakeroot make-kpkg --initrd --append-to-version=-custom kernel_image kernel_headers 在--append-to-version= 後面你可以寫上任何字串來區別核心版本, 但是必須以" - "符號開始而且後面不包括任何空格. 如果在編譯過程中出現某些錯誤,那麼請在make menuconfig中不要將相關功能選中,確保通過編譯。每次編譯都要花較長時間,大概在半小時到一小時左右。其中大部分時間都花在核心模組檔案的產生上。
3.安裝核心 編譯完成之後,可以在/usr/src目錄中發現多了兩個.deb檔案,安裝可以用dpkg命令:dpkg -i linux-image-2.6.15.5-kgdb_10.00.Custom_i386.debdpkg -i linux-headers-2.6.15.5-kgdb_10.00.Custom_i386.deb安裝會自動將產生的核心vmlinuz和initrd.img拷貝至/boot/目錄中,並且更改grub設定。察看menu.lst(或者grub.conf)檔案可以看到在啟動項最後添加了兩項。將其中一項按照kgdb的官方說明文檔更改為如下所示:title Ubuntu, kernel 2.6.15.5-kgdbroot (hd0,0)kernel /boot/vmlinuz-2.6.15.5-kgdb root=/dev/sda1 ro kgdbwait kgdb8250=0, 115200initrd /boot/initrd.img-2.6.15.5-kgdbsavedefault boot其中關於root的配置因人而異,可以不是sda1。
4.配置虛擬機器
更改兩台機器的vmware配置,分別加上一個串口。注意被調試機要選this end is the client, the other end is a virtual machine,而調試機要選this end is the server,the other end is a virtual machine。可以用在被調試機上打命令cat /dev/ttyS0,在調試機上打echo
abc > /dev/ttyS0來測試設定是否生效。測試之間別忘了檢查下網路是否能相互連通,本地vmware NAT/DHCP之類的服務有沒有被禁用。通過測試之後就剩最後一步了。
5.聯機調試
啟動被調試機,根據提示按esc進行grub選擇。選擇剛才產生的新核心,等待Ok.booting the kernel的出現。在調試機上進行如下設定,確保串口通訊速率是115200,連接埠是0stty ispeed 115200 ospped 115200 < /dev/ttyS0確保調試機和被調試機的源碼和System.map一致,然後將目錄切換至源碼目錄,輸入gdb vmlinuz(gdb) target remote /dev/ttyS0等待斷點。如果收到的是error,那麼就是串口連接埠相關的配置沒有設定好,或者是gdb版本太低。檢查make menuconfig中的連接埠配置,檢查grub中的設定,檢查stty命令是否正確。如果收到的是類似於breakpoint () at gdbstub.c 1153之類的資訊,那麼恭喜你,你成功了。