GDB是在Linux命令列下對C/C++的程式進行除錯常用的一個命令,現將平時記錄在本子上的筆記整理如下:
一、斷點
斷點型別有breakpoints, watchpoints, catchpoints.
1).breakpoints: 普通斷點,程式執行到該點時暫停(此時此行尚未執行),是gdb中最常用的斷點,相關命令為:
break [函式名,行數或者指令地址] [condi] :在指定地方加上斷點
例:
(gdb) set $counter = 0
(gdb) break 26 if ++$counter == 99
在第26行設定斷點,每次觸發斷點的時候執行判斷條件,僅在判斷條件為真的時候使程式在斷點處停止。在迴圈的debug中很好用。
類似的命令還有condition等。
rbreak RE :在所有符合正規表示式RE的函式上加上斷點
2).watchpoints: 也稱為data breakpoints,在表示式值變化時停止執行的斷點。
watch expr[thread threadnum] 表示式可以是變數值,地址(如*(int *)0x12345678)或數學表示式。
3).catchpoints: 程式事件斷點,如c++異常
catch event :event可以是 throw或catch事件
檢視斷點:
info breakpoint[n] : 列印所有(或者第n個)斷點資訊,同 info break
info watchpoints[n] : 同上
刪除斷點:
delete [斷點號] [range...] :range是斷點號,空格分割
clear location :location是函式名,行數等
enable/disable :使能/使失效斷點,不刪除
其他:
為斷點號bnum寫一個命令列表,程式執行到斷點時gdb會依次執行列表中的命令:
commands [bnums]
...command list...
end
二、單步除錯
1)基本命令:
step:執行下一步(即step into,進入呼叫的函式體內)
next:同上,但是不進入函式體
finish:往下執行直至當前棧幀(下面解釋)中的函式返回
continue:往下執行直至遇到斷點
列印資訊:
print/x data:以x(十六進位制)格式列印資料data的值(或者縮寫為p/x data);
輸出格式有x、d、u、o、t(二進位制,two,因為b已經用來表示byte)、a(address)、c(char)、f(float)、s(string)、r(raw)
檢視資料型別: ptype data;
列印陣列: p *array@len
2)棧幀(stack frame)是在棧中為引數、返回地址和區域性變數保留的一塊記憶體區,必要時在過程呼叫中使用,相關命令:
frame[args]:從一個棧幀移動到另一個,並列印選擇的棧幀。args可以是棧幀號或其地址。
info frame []:檢視棧幀的詳細資訊
backtrace:向後追蹤棧幀(呼叫)
3)底層資訊:
檢視彙編:disassemble [option] [range]
接收一個引數時,列印該地址周圍的函式的彙編,接收兩個引數時,表示需要dump的範圍
檢視記憶體:x /nfu addr
n:重複數。預設為1,表示要顯示多少記憶體(以單元u為基數)
f:顯示格式。同print,預設為x, i表示機器指令
u:單元大小。分別可以是b(byte)、h(halfwords,=2byte)、w(words,=4byte)和g(gaint words,=8byte);預設為w
暫存器:
$pc:程式計數器,值為下一條指令的地址
$ps:程式狀態暫存器
$sp:stack pointer棧指標
$fp:frame pointer 指向當前棧幀的指標
三、變更執行
1)修改變數
print i=num,賦值並列印變數i
set i=num,僅賦值
2)修改記憶體
用'{...}'結構來生成地址。如:
set {int}0x83040 = 4; //將4儲存到地址0x83040中
3)跳轉
jump [location]
location可以是行號或者地址。注意jump命令僅僅改變$pc的值,而不改變當前棧幀、堆疊指標或上下文,效果相當於set $pc = {int}location
4)中斷
signal sig //立即將訊號sig發給程式
5)其他
return:使(函式)返回