功能
一般來說,GDB主要幫助你完成下面四個方面的功能:
1、啟動你的程式,可以按照你的自定義的要求隨心所欲的運行程式。
2、可讓被調試的程式在你所指定的調置的
斷點處停住。(斷點可以是
條件表達式)
3、當程式被停住時,可以檢查此時你的程式中所發生的事。
4、你可以改變你的程式,將一個BUG產生的影響修正從而測試其他BUG。
版本發布
2009年12月29日,程式調試工具 GDB 7.0.1 發布,新版本修正了7.0版本的一些嚴重的堆疊溢出bug,這些bug可能導致 GDB 調試進程中斷,修正了在 FreeBSD 和 IRⅨ 系統下無法編譯的問題,增加了對 Thumb2調試的支持,還有其他一些小bug的修復。
2010年03月19日,GDB 7.1 發布,
詳細改進內容:多程式調試的支持;
位置獨立的執行檔(派)調試的支持;
新的目標(包括一個模擬器):Xilinx MicroBlaze和瑞薩RX;
Python支持增強;
c++支持擴展;
新tracepoint功能;
過程記錄的改進;
遠程協定擴展。
2010年09月06日 ,GDB 7.2 發布,
該版本改進記錄:
⒉ C++ 改進,支持參數依賴查找ADL,靜態常量類成員和改進了用戶自定義操作符的支持
⒊ Python 調試的改進,包括
斷點、符號、符號表、程式空間、執行緒等可通過命令行進行操作
⒋ Furthermore,enhancements were made for tracepoints and for GDBserver.在跟蹤點和GDB程式上有了改善。
⒌ 支持 ARM Symbian 平台
⒍ 其他方面的改進和bug修復。
2011年08月26日,GDB 7.3a 發布,
變化:
1。GDB可以理解執行緒的名字。
2。這個命令”執行緒名稱”(指定一個名稱)和“執行緒找到[REGEXP]”(匹配名稱、目標ID,或者額外的信息)被添加。
3。Python腳本支持大大增強。
4。在c++的支持,異常處理是提高,模板參數放在範圍在一個實例化時調試。
5。執行緒調試的核心轉儲在GNU / Linux成為可能。
6。最初支持C語言版本的OpenCL。
7。許多其他改進。
檔案清單
List
(gdb) list line1,line2
查看原始碼
list lineNum 在lineNum的前後原始碼顯示出來
list + 列出當前行的後面代碼行
list - 列出當前行的前面代碼行
list function
set listsize count
設定顯示代碼的行數
show listsize
顯示列印代碼的行數
list first,last
顯示從first到last的原始碼行
執行程式
要想運行準備調試的程式,可使用run命令,在它後面可以跟隨發給該程式的任何參數,包括標準輸入和標準輸出說明符(<;和>;)和shell通配符(*、?、[、])在內。如果你使用不帶參數的run命令,gdb就再次使用你給予前一條run命令的參數,這是很有用的。利用set args 命令就可以修改傳送給程式的參數,而使用show args 命令就可以查看其
預設參數的列表。
(gdb) file a.out //載入被調試的可執行程式檔案。
(gdb)set args –b –x
(gdb) show args
(gdb)r //執行程式
Backtrace 命令產生一張列表,包含著從最近的過程開始的所有有效過程和調用這些過程的參數。
顯示數據
利用print 命令可以檢查各個變數的值。
(gdb) print p (p為變數名)
print 是gdb的一個功能很強的命令,利用它可以顯示被調試的語言中任何有效的
表達式。表達式除了包含你程式中的變數外,還可以包含以下內容:
對程式中函式的調用
(gdb) print find_entry(1,0)
數據結構和其他複雜對象
(gdb) print *table_start
={e=reference=’\000’,location=0x0,next=0x0}
值的歷史成分
(gdb)print (為歷史記錄變數,在以後可以直接引用的值)
人為數組提供了一種去
顯示存儲器塊(數組節或動態分配的存儲區)內容的方法。早期的
調試程式沒有很好的方法將任意的
指針換成一個數組。就像對待參數一樣,讓我們查看記憶體中在變數h後面的10個整數,一個
動態數組的語法如下所示:
base@length
因此,要想顯示在h後面的10個元素,可以使用h@10:
(gdb)print h@10
=(-1,345,23,-234,0,0,0,98,345,10)
(gdb) whatis p
type = int *
斷點
break命令(可以簡寫為b)可以用來在調試的程式中設定
斷點,該命令有如下四種形式:
break line-number 使程式恰好在執行給定行之前停止。
break function-name 使程式恰好在進入指定的函式之前停止。
break line-or-function if condition 如果condition(條件)是真,程式到達指定行或函式時停止。
break routine-name 在指定例程的入口處設定斷點
如果該程式是由很多原檔案構成的,你可以在各個原檔案中設定
斷點,而不是在當前的原檔案中設定斷點,其方法如下:
(gdb) break filename:line-number
(gdb) break filename:function-name
要想設定一個條件斷點,可以利用break if命令,如下所示:
(gdb) break line-or-function if expr
例:
(gdb) break 46 if testsize==100
從斷點繼續運行:continue 命令
斷點管理
1.顯示當前gdb的斷點信息:
(gdb) info break
他會以如下的形式顯示所有的斷點信息:
Num Type Disp Enb Address What
1 breakpoint keep y 0x000028bc in init_random at qsort2.c:155
2 breakpoint keep y 0x0000291c in init_organ at qsort2.c:168
刪除指定的某個斷點:
(gdb) delete breakpoint 1
該命令將會刪除編號為1的
斷點,如果不帶編號參數,將刪除所有的斷點
(gdb) delete breakpoint
禁止使用某個斷點
(gdb) disable breakpoint 1
該命令將禁止斷點1,同時斷點信息的 (Enb)域將變為 n
允許使用某個斷點
(gdb) enable breakpoint 1
該命令將允許斷點1,同時斷點信息的 (Enb)域將變為 y
清除源檔案中某一代碼行上的所有斷點
(gdb)clear number
註:number 為源檔案的某個代碼行的行號
2.設定條件斷點
例子:
#include <stdio.h>int main(void){ int i = 0; int sum = 0; for (i = 1; i <= 200; i++) { sum += i; } printf("%d\n", sum); return 0;}
gdb可以設定條件斷點,也就是只有在條件滿足時,斷點才會被觸發,命令是“break … if cond”。以上面程式為例:
(gdb) startTemporary breakpoint 1 at 0x4004cc: file a.c, line 5.Starting program: /data2/home/nanxiao/aTemporary breakpoint 1, main () at a.c:55 int i = 0;(gdb) b 10 if i==101Breakpoint 2 at 0x4004e3: file a.c, line 10.(gdb) rStarting program: /data2/home/nanxiao/aBreakpoint 2, main () at a.c:1010 sum += i;(gdb) p sum$1 = 5050
可以看到設定斷點只在i的值為101時觸發,此時列印sum的值為5050。
變數檢查賦值
ptype:比whatis的功能更強,他可以提供一個結構的定義
set variable = value:將值賦予變數
print variable = value or p variable = value : 除了顯示一個變數的值外,還可以用來賦值
單步執行
next 不進入的單步執行
step 進入的單步執行如果已經進入了某函式,而想退出該函式返回到它的調用函式中,可使用命令finish
函式調用
call name 調用和執行一個函式
(gdb) call gen_and_sork(1234,1,0)
(gdb) call printf(“abcd”)
=4
finish 結束執行當前函式,顯示其返回值(如果有的話)
機器語言工具
有一組專用的gdb變數可以用來檢查和修改計算機的
通用暫存器,gdb提供了目 前每一台計算機中實際使用的4個暫存器的標準名字:
$pc :程式計數器
$fp :幀指針(當前堆疊幀)
$sp :棧指針
$ps :處理器狀態
信號
gdb通常可以捕捉到傳送給它的大多數信號,通過捕捉信號,它就可決定對於正在運行的進程要做些什麼工作。例如,按CTRL-C將中斷信號傳送給gdb,通常就會終止gdb。但是你或許不想中斷gdb,真正的目的是要中斷gdb正在運行的程式,因此,gdb要抓住該信號並停止它正在運行的程式,這樣就可以執行某些調試操作。
Handle命令可
控制信號的處理,他有兩個參數,一個是信號名,另一個是接受到信號時該作什麼。幾種可能的參數是:
nostop 接收到信號時,不要將它傳送給程式,也不要停止程式。
stop 接受到信號時停止程式的執行,從而允許
程式調試;顯示一條表示已接受到信號的訊息(禁止使用訊息除外)
print 接受到信號時顯示一條訊息
noprint 接受到信號時不要顯示訊息(而且隱含著不停止程式運行)
pass 將信號傳送給程式,從而允許你的程式去處理它、停止運行或採取別的動作。
nopass 停止程式運行,但不要將信號傳送給程式。
例如,假定你截獲SIGPIPE信號,以防止正在調試的程式接受到該信號,而且只要該信號一到達,就要求該程式停止,並通知你。要完成這一任務,可利用如下命令:
(gdb) handle SIGPIPE stop print
請注意,UNⅨ的信號名總是採用大寫字母!你可以用信號編號替代信號名如果你的程式要執行任何信號處理操作,就需要能夠測試其信號處理程式,為此,就需要一種能將信號傳送給程式的簡便方法,這就是signal命令的任務。該命令的參數是一個數字或者一個名字,如SIGINT。假定你的程式已將一個專用的SIGINT(鍵盤輸入,或CTRL-C;信號2)信號處理程式設定成採取某個清理動作,要想測試該信號處理程式,你可以設定一個
斷點並使用如下命令:
(gdb) signal 2
continuing with signal SIGINT⑵
該程式繼續執行,但是立即傳輸該信號,而且處理程式開始運行。
GDB使用
GDB是一個強大的命令行調試工具。大家知道命令行的強大就是在於,其可以形成執行序列,形成腳本。UNⅨ下的軟體全是命令行的,這給程式開發提代供了極大的便利,命令行軟體的優勢在於,它們可以非常容易的集成在一起,使用幾個簡單的已有工具的命令,就可以做出一個非常強大的功能。
於是UNⅨ下的軟體比Windows下的軟體更能有機地結合,各自發揮各自的長處,組合成更為強勁的功能。而Windows下的圖形軟體基本上是各自為營,互相不能調用,很不利於各種軟體的相互集成。在這裡並不是要和Windows做個什麼比較,所謂“寸有所長,尺有所短”,圖形化工具還有時不如命令行的地方。