或是直接就是b func
(gdb) b func
Breakpoint 1 at 0x8048458: file hello.c, line 10.
示例二:敲入b按兩次TAB鍵,你會(huì)看到所有b打頭的命令:
(gdb) b
backtrace break bt
(gdb)
示例三:只記得函數(shù)的前綴,可以這樣:
(gdb) b make_ <按TAB鍵>
(再按下一次TAB鍵,你會(huì)看到:)
make_a_section_from_file make_environ
make_abs_section make_function_type
make_blockvector make_pointer_type
make_cleanup make_reference_type
make_command make_symbol_completion_list
(gdb) b make_
GDB把所有make開頭的函數(shù)全部例出來(lái)給你查看。
示例四:調(diào)試C++的程序時(shí),有可以函數(shù)名一樣。如:
(gdb) b 'bubble( M-?
bubble(double,double) bubble(int,int)
(gdb) b 'bubble(
你可以查看到C++中的所有的重載函數(shù)及參數(shù)。(注:M-?和“按兩次TAB鍵”是一個(gè)意思)
要退出gdb時(shí),只用發(fā)quit或命令簡(jiǎn)稱q就行了。
GDB中運(yùn)行UNIX的shell程序
————————————
在gdb環(huán)境中,你可以執(zhí)行UNIX的shell的命令,使用gdb的shell命令來(lái)完成:
shell
調(diào)用UNIX的shell來(lái)執(zhí)行,環(huán)境變量SHELL中定義的UNIX的shell將會(huì)被用來(lái)執(zhí)行,如
果SHELL沒有定義,那就使用UNIX的標(biāo)準(zhǔn)shell:/bin/sh。(在Windows中使用
Command.com或cmd.exe)
還有一個(gè)gdb命令是make:
make
可以在gdb中執(zhí)行make命令來(lái)重新build自己的程序。這個(gè)命令等價(jià)于“shell make ”。
在GDB中運(yùn)行程序
————————
當(dāng)以gdb 方式啟動(dòng)gdb后,gdb會(huì)在PATH路徑和當(dāng)前目錄中搜索的源文件。如要確認(rèn)gdb是否讀到源文件,可使用l或list命令,看看gdb是否能列出源代碼。
在gdb中,運(yùn)行程序使用r或是run命令。程序的運(yùn)行,你有可能需要設(shè)置下面四方面的事。
1、程序運(yùn)行參數(shù)。
set args 可指定運(yùn)行時(shí)參數(shù)。(如:set args 10 20 30 40 50)
show args 命令可以查看設(shè)置好的運(yùn)行參數(shù)。
2、運(yùn)行環(huán)境。
path
可設(shè)定程序的運(yùn)行路徑。
show paths 查看程序的運(yùn)行路徑。
set environment varname [=value] 設(shè)置環(huán)境變量。如:set env USER=hchen
show environment [varname] 查看環(huán)境變量。
3、工作目錄。
cd
相當(dāng)于shell的cd命令。
pwd 顯示當(dāng)前的所在目錄。
4、程序的輸入輸出。
info terminal 顯示你程序用到的終端的模式。
使用重定向控制程序輸出。如:run > outfile
tty命令可以指寫輸入輸出的終端設(shè)備。如:tty /dev/ttyb
調(diào)試已運(yùn)行的程序
————————
兩種方法:
1、在UNIX下用ps查看正在運(yùn)行的程序的PID(進(jìn)程ID),然后用gdb PID格式掛接正在運(yùn)行的程序。
2、先用gdb 關(guān)聯(lián)上源代碼,并進(jìn)行g(shù)db,在gdb中用attach命令來(lái)掛接進(jìn)程的PID。并用detach來(lái)取消掛接的進(jìn)程。
暫停 / 恢復(fù)程序運(yùn)行
—————————
調(diào)試程序中,暫停程序運(yùn)行是必須的,GDB可以方便地暫停程序的運(yùn)行。你可以設(shè)置
程序的在哪行停住,在什么條件下停住,在收到什么信號(hào)時(shí)停往等等。以便于你查
看運(yùn)行時(shí)的變量,以及運(yùn)行時(shí)的流程。
當(dāng)進(jìn)程被gdb停住時(shí),你可以使用info program 來(lái)查看程序的是否在運(yùn)行,進(jìn)程號(hào),被
暫停的原因。
在gdb中,我們可以有以下幾種暫停方式:斷點(diǎn)(BreakPoint)、觀察點(diǎn)
(WatchPoint)、捕捉點(diǎn)(CatchPoint)、信號(hào)(Signals)、線程停止(Thread
Stops)。如果要恢復(fù)程序運(yùn)行,可以使用c或是continue命令。
一、設(shè)置斷點(diǎn)(BreakPoint)
我們用break命令來(lái)設(shè)置斷點(diǎn)。正面有幾點(diǎn)設(shè)置斷點(diǎn)的方法:
break
在進(jìn)入指定函數(shù)時(shí)停住。C++中可以使用class::function或function(type,type)格式來(lái)指定函數(shù)名。
break
在指定行號(hào)停住。
break +offset
break -offset
在當(dāng)前行號(hào)的前面或后面的offset行停住。offiset為自然數(shù)。
break filename:linenum
在源文件filename的linenum行處停住。
break filename:function
在源文件filename的function函數(shù)的入口處停住。
break *address
在程序運(yùn)行的內(nèi)存地址處停住。
break
break命令沒有參數(shù)時(shí),表示在下一條指令處停住。
break ... if
...可以是上述的參數(shù),condition表示條件,在條件成立時(shí)停住。比如在循環(huán)境體中,可以設(shè)置break if i=100,表示當(dāng)i為100時(shí)停住程序。
查看斷點(diǎn)時(shí),可使用info命令,如下所示:(注:n表示斷點(diǎn)號(hào))
info breakpoints [n]
info break [n]
二、設(shè)置觀察點(diǎn)(WatchPoint)
觀察點(diǎn)一般來(lái)觀察某個(gè)表達(dá)式(變量也是一種表達(dá)式)的值是否有變化了,如果有變化,馬上停住程序。我們有下面的幾種方法來(lái)設(shè)置觀察點(diǎn):
watch
為表達(dá)式(變量)expr設(shè)置一個(gè)觀察點(diǎn)。一量表達(dá)式值有變化時(shí),馬上停住程序。
rwatch
當(dāng)表達(dá)式(變量)expr被讀時(shí),停住程序。
awatch
當(dāng)表達(dá)式(變量)的值被讀或被寫時(shí),停住程序。
info watchpoints
列出當(dāng)前所設(shè)置了的所有觀察點(diǎn)。
三、設(shè)置捕捉點(diǎn)(CatchPoint)
你可設(shè)置捕捉點(diǎn)來(lái)補(bǔ)捉程序運(yùn)行時(shí)的一些事件。如:載入共享庫(kù)(動(dòng)態(tài)鏈接庫(kù))或是C++的異常。設(shè)置捕捉點(diǎn)的格式為:
catch
當(dāng)event發(fā)生時(shí),停住程序。event可以是下面的內(nèi)容:
1、throw 一個(gè)C++拋出的異常。(throw為關(guān)鍵字)
2、catch 一個(gè)C++捕捉到的異常。(catch為關(guān)鍵字)
3、exec 調(diào)用系統(tǒng)調(diào)用exec時(shí)。(exec為關(guān)鍵字,目前此功能只在HP-UX下有用)
4、fork 調(diào)用系統(tǒng)調(diào)用fork時(shí)。(fork為關(guān)鍵字,目前此功能只在HP-UX下有用)
5、vfork 調(diào)用系統(tǒng)調(diào)用vfork時(shí)。(vfork為關(guān)鍵字,目前此功能只在HP-UX下有用)
6、load 或 load 載入共享庫(kù)(動(dòng)態(tài)鏈接庫(kù))時(shí)。(load為關(guān)鍵字,目前此功能只在HP-UX下有用)
7、unload 或 unload 卸載共享庫(kù)(動(dòng)態(tài)鏈接庫(kù))時(shí)。(unload為關(guān)鍵字,目前此功能只在HP-UX下有用)
tcatch
只設(shè)置一次捕捉點(diǎn),當(dāng)程序停住以后,應(yīng)點(diǎn)被自動(dòng)刪除。
四、維護(hù)停止點(diǎn)
上面說(shuō)了如何設(shè)置程序的停止點(diǎn),GDB中的停止點(diǎn)也就是上述的三類。在GDB中,如
果你覺得已定義好的停止點(diǎn)沒有用了,你可以使用delete、clear、disable、
enable這幾個(gè)命令來(lái)進(jìn)行維護(hù)。
clear
清除所有的已定義的停止點(diǎn)。
clear
clear
清除所有設(shè)置在函數(shù)上的停止點(diǎn)。
clear
clear
清除所有設(shè)置在指定行上的停止點(diǎn)。
delete [breakpoints] [range...]
刪除指定的斷點(diǎn),breakpoints為斷點(diǎn)號(hào)。如果不指定斷點(diǎn)號(hào),則表示刪除所有的斷點(diǎn)。range 表示斷點(diǎn)號(hào)的范圍(如:3-7)。其簡(jiǎn)寫命令為d。
比刪除更好的一種方法是disable停止點(diǎn),disable了的停止點(diǎn),GDB不會(huì)刪除,當(dāng)你還需要時(shí),enable即可,就好像回收站一樣。
disable [breakpoints] [range...]
disable所指定的停止點(diǎn),breakpoints為停止點(diǎn)號(hào)。如果什么都不指定,表示disable所有的停止點(diǎn)。簡(jiǎn)寫命令是dis.
enable [breakpoints] [range...]
enable所指定的停止點(diǎn),breakpoints為停止點(diǎn)號(hào)。
enable [breakpoints] once range...
enable所指定的停止點(diǎn)一次,當(dāng)程序停止后,該停止點(diǎn)馬上被GDB自動(dòng)disable。
enable [breakpoints] delete range...
enable所指定的停止點(diǎn)一次,當(dāng)程序停止后,該停止點(diǎn)馬上被GDB自動(dòng)刪除。
五、停止條件維護(hù)
前面在說(shuō)到設(shè)置斷點(diǎn)時(shí),我們提到過(guò)可以設(shè)置一個(gè)條件,當(dāng)條件成立時(shí),程序自動(dòng)停
止,這是一個(gè)非常強(qiáng)大的功能,這里,我想專門說(shuō)說(shuō)這個(gè)條件的相關(guān)維護(hù)命令。一般
來(lái)說(shuō),為斷點(diǎn)設(shè)置一個(gè)條件,我們使用if關(guān)鍵詞,后面跟其斷點(diǎn)條件。并且,條件設(shè)
置好后,我們可以用condition命令來(lái)修改斷點(diǎn)的條件。(只有break和watch命令支
持if,catch目前暫不支持if)
condition
修改斷點(diǎn)號(hào)為bnum的停止條件為expression。
condition
清除斷點(diǎn)號(hào)為bnum的停止條件。
還有一個(gè)比較特殊的維護(hù)命令ignore,你可以指定程序運(yùn)行時(shí),忽略停止條件幾次。
ignore
表示忽略斷點(diǎn)號(hào)為bnum的停止條件count次。
六、為停止點(diǎn)設(shè)定運(yùn)行命令
我們可以使用GDB提供的command命令來(lái)設(shè)置停止點(diǎn)的運(yùn)行命令。也就是說(shuō),當(dāng)運(yùn)行
的程序在被停止住時(shí),我們可以讓其自動(dòng)運(yùn)行一些別的命令,這很有利行自動(dòng)化調(diào)
試。對(duì)基于GDB的自動(dòng)化調(diào)試是一個(gè)強(qiáng)大的支持。
commands [bnum]
... command-list ...
end
為斷點(diǎn)號(hào)bnum指寫一個(gè)命令列表。當(dāng)程序被該斷點(diǎn)停住時(shí),gdb會(huì)依次運(yùn)行命令列表中的命令。
例如:
break foo if x>0
commands
printf "x is %d\n",x
continue
end
斷點(diǎn)設(shè)置在函數(shù)foo中,斷點(diǎn)條件是x>0,如果程序被斷住后,也就是,一旦x的值在foo函數(shù)中大于0,GDB會(huì)自動(dòng)打印出x的值,并繼續(xù)運(yùn)行程序。
如果你要清除斷點(diǎn)上的命令序列,那么只要簡(jiǎn)單的執(zhí)行一下commands命令,并直接在打個(gè)end就行了。
七、斷點(diǎn)菜單
在C++中,可能會(huì)重復(fù)出現(xiàn)同一個(gè)名字的函數(shù)若干次(函數(shù)重載),在這種情況
下,break 不能告訴GDB要停在哪個(gè)函數(shù)的入口。當(dāng)然,你可以使用break 也就是把
函數(shù)的參數(shù)類型告訴GDB,以指定一個(gè)函數(shù)。否則的話,GDB會(huì)給你列出一個(gè)斷點(diǎn)菜
單供你選擇你所需要的斷點(diǎn)。你只要輸入你菜單列表中的編號(hào)就可以了。如:
(gdb) b String::after
[0] cancel
[1] all
[2] file:String.cc; line number:867
[3] file:String.cc; line number:860
[4] file:String.cc; line number:875
[5] file:String.cc; line number:853
[6] file:String.cc; line number:846
[7] file:String.cc; line number:735
> 2 4 6
Breakpoint 1 at 0xb26c: file String.cc, line 867.
Breakpoint 2 at 0xb344: file String.cc, line 875.
Breakpoint 3 at 0xafcc: file String.cc, line 846.
Multiple breakpoints were set.
Use the "delete" command to delete unwanted
breakpoints.
(gdb)
可見,GDB列出了所有after的重載函數(shù),你可以選一下列表編號(hào)就行了。
0表示放棄設(shè)置斷點(diǎn),1表示所有函數(shù)都設(shè)置斷點(diǎn)。
八、恢復(fù)程序運(yùn)行和單步調(diào)試
當(dāng)程序被停住了,你可以用continue命令恢復(fù)程序的運(yùn)行直到程序結(jié)束,或下一個(gè)斷點(diǎn)到來(lái)。也可以使用step或next命令單步跟蹤程序。
continue [ignore-count]
c [ignore-count]
fg [ignore-count]
恢復(fù)程序運(yùn)行,直到程序結(jié)束,或是下一個(gè)斷點(diǎn)到來(lái)。ignore-count表示忽略其后的斷點(diǎn)次數(shù)。continue,c,fg三個(gè)命令都是一樣的意思。
step
單步跟蹤,如果有函數(shù)調(diào)用,他會(huì)進(jìn)入該函數(shù)。進(jìn)入函數(shù)的前提是,此函數(shù)被編譯有
debug信息。很像VC等工具中的step in。后面可以加count也可以不加,不加表示
一條條地執(zhí)行,加表示執(zhí)行后面的count條指令,然后再停住。
next
同樣單步跟蹤,如果有函數(shù)調(diào)用,他不會(huì)進(jìn)入該函數(shù)。很像VC等工具中的step
over。后面可以加count也可以不加,不加表示一條條地執(zhí)行,加表示執(zhí)行后面的
count條指令,然后再停住。
set step-mode
set step-mode on
打開step-mode模式,于是,在進(jìn)行單步跟蹤時(shí),程序不會(huì)因?yàn)闆]有debug信息而不停住。這個(gè)參數(shù)有很利于查看機(jī)器碼。
set step-mod off
關(guān)閉step-mode模式。
finish
運(yùn)行程序,直到當(dāng)前函數(shù)完成返回。并打印函數(shù)返回時(shí)的堆棧地址和返回值及參數(shù)值等信息。
until 或 u
當(dāng)你厭倦了在一個(gè)循環(huán)體內(nèi)單步跟蹤時(shí),這個(gè)命令可以運(yùn)行程序直到退出循環(huán)體。
stepi 或 si
nexti 或 ni
單步跟蹤一條機(jī)器指令!一條程序代碼有可能由數(shù)條機(jī)器指令完成,stepi和nexti
可以單步執(zhí)行機(jī)器指令。與之一樣有相同功能的命令是 “display/i $pc” ,當(dāng)運(yùn)
行完這個(gè)命令后,單步跟蹤會(huì)在打出程序代碼的同時(shí)打出機(jī)器指令(也就是匯編代
碼)
九、信號(hào)(Signals)
信號(hào)是一種軟中斷,是一種處理異步事件的方法。一般來(lái)說(shuō),操作系統(tǒng)都支持許多
信號(hào)。尤其是UNIX,比較重要應(yīng)用程序一般都會(huì)處理信號(hào)。UNIX定義了許多信號(hào),
比如SIGINT表示中斷字符信號(hào),也就是Ctrl+C的信號(hào),SIGBUS表示硬件故障的信
號(hào);SIGCHLD表示子進(jìn)程狀態(tài)改變信號(hào); SIGKILL表示終止程序運(yùn)行的信號(hào),等等。
信號(hào)量編程是UNIX下非常重要的一種技術(shù)。
GDB有能力在你調(diào)試程序的時(shí)候處理任何一種信號(hào),你可以告訴GDB需要處理哪一種
信號(hào)。你可以要求GDB收到你所指定的信號(hào)時(shí),馬上停住正在運(yùn)行的程序,以供你進(jìn)
行調(diào)試。你可以用GDB的handle命令來(lái)完成這一功能。
handle
在GDB中定義一個(gè)信號(hào)處理。信號(hào)可以以SIG開頭或不以SIG開頭,可以用定義一個(gè)
要處理信號(hào)的范圍(如:SIGIO-SIGKILL,表示處理從SIGIO信號(hào)到SIGKILL的信號(hào),其
中包括SIGIO,SIGIOT,SIGKILL三個(gè)信號(hào)),也可以使用關(guān)鍵字all來(lái)標(biāo)明要處理所有
的信號(hào)。一旦被調(diào)試的程序接收到信號(hào),運(yùn)行程序馬上會(huì)被GDB停住,以供調(diào)試。其
可以是以下幾種關(guān)鍵字的一個(gè)或多個(gè)。
nostop
當(dāng)被調(diào)試的程序收到信號(hào)時(shí),GDB不會(huì)停住程序的運(yùn)行,但會(huì)打出消息告訴你收到這種信號(hào)。
stop
當(dāng)被調(diào)試的程序收到信號(hào)時(shí),GDB會(huì)停住你的程序。
print
當(dāng)被調(diào)試的程序收到信號(hào)時(shí),GDB會(huì)顯示出一條信息。
noprint
當(dāng)被調(diào)試的程序收到信號(hào)時(shí),GDB不會(huì)告訴你收到信號(hào)的信息。
pass
noignore
當(dāng)被調(diào)試的程序收到信號(hào)時(shí),GDB不處理信號(hào)。這表示,GDB會(huì)把這個(gè)信號(hào)交給被調(diào)試程序會(huì)處理。
nopass
ignore
當(dāng)被調(diào)試的程序收到信號(hào)時(shí),GDB不會(huì)讓被調(diào)試程序來(lái)處理這個(gè)信號(hào)。
info signals
info handle
查看有哪些信號(hào)在被GDB檢測(cè)中。
十、線程(Thread Stops)
如果你程序是多線程的話,你可以定義你的斷點(diǎn)是否在所有的線程上,或是在某個(gè)特定的線程。GDB很容易幫你完成這一工作。
break thread
break thread if ...
linespec指定了斷點(diǎn)設(shè)置在的源程序的行號(hào)。threadno指定了線程的ID,注意,這
個(gè)ID是GDB分配的,你可以通過(guò)“info threads”命令來(lái)查看正在運(yùn)行程序中的線程
信息。如果你不指定thread 則表示你的斷點(diǎn)設(shè)在所有線程上面。你還可以為某線
程指定斷點(diǎn)條件。如:
(gdb) break frik.c:13 thread 28 if bartab > lim
當(dāng)你的程序被GDB停住時(shí),所有的運(yùn)行線程都會(huì)被停住。這方便你你查看運(yùn)行程序
的總體情況。而在你恢復(fù)程序運(yùn)行時(shí),所有的線程也會(huì)被恢復(fù)運(yùn)行。那怕是主進(jìn)程
在被單步調(diào)試時(shí)。
查看棧信息
—————
當(dāng)程序被停住了,你需要做的第一件事就是查看程序是在哪里停住的。當(dāng)你的程序
調(diào)用了一個(gè)函數(shù),函數(shù)的地址,函數(shù)參數(shù),函數(shù)內(nèi)的局部變量都會(huì)被壓入
“棧”(Stack)中。你可以用GDB命令來(lái)查看當(dāng)前的棧中的信息。
下面是一些查看函數(shù)調(diào)用棧信息的GDB命令:
backtrace
bt
打印當(dāng)前的函數(shù)調(diào)用棧的所有信息。如:
(gdb) bt
#0 func (n=250) at tst.c:6
#1 0x08048524 in main (argc=1, argv=0xbffff674) at tst.c:30
#2 0x400409ed in __libc_start_main () from /lib/libc.so.6
從上可以看出函數(shù)的調(diào)用棧信息:__libc_start_main --> main() --> func()
backtrace
bt
n是一個(gè)正整數(shù),表示只打印棧頂上n層的棧信息。
backtrace <-n>
bt <-n>
-n表一個(gè)負(fù)整數(shù),表示只打印棧底下n層的棧信息。
如果你要查看某一層的信息,你需要在切換當(dāng)前的棧,一般來(lái)說(shuō),程序停止時(shí),最頂
層的棧就是當(dāng)前棧,如果你要查看棧下面層的詳細(xì)信息,首先要做的是切換當(dāng)前棧。
frame
f
n是一個(gè)從0開始的整數(shù),是棧中的層編號(hào)。比如:frame 0,表示棧頂,frame 1,表示棧的第二層。
up
表示向棧的上面移動(dòng)n層,可以不打n,表示向上移動(dòng)一層。
down
表示向棧的下面移動(dòng)n層,可以不打n,表示向下移動(dòng)一層。
上面的命令,都會(huì)打印出移動(dòng)到的棧層的信息。如果你不想讓其打出信息。你可以使用這三個(gè)命令:
select-frame 對(duì)應(yīng)于 frame 命令。
up-silently 對(duì)應(yīng)于 up 命令。
down-silently 對(duì)應(yīng)于 down 命令。
查看當(dāng)前棧層的信息,你可以用以下GDB命令:
frame 或 f
會(huì)打印出這些信息:棧的層編號(hào),當(dāng)前的函數(shù)名,函數(shù)參數(shù)值,函數(shù)所在文件及行號(hào),函數(shù)執(zhí)行到的語(yǔ)句。
info frame
info f
這個(gè)命令會(huì)打印出更為詳細(xì)的當(dāng)前棧層的信息,只不過(guò),大多數(shù)都是運(yùn)行時(shí)的內(nèi)內(nèi)
地址。比如:函數(shù)地址,調(diào)用函數(shù)的地址,被調(diào)用函數(shù)的地址,目前的函數(shù)是由什么
樣的程序語(yǔ)言寫成的、函數(shù)參數(shù)地址及值、局部變量的地址等等。如:
(gdb) info f
Stack level 0, frame at 0xbffff5d4:
eip = 0x804845d in func (tst.c:6); saved eip 0x8048524
called by frame at 0xbffff60c
source language c.
Arglist at 0xbffff5d4, args: n=250
Locals at 0xbffff5d4, Previous frame's sp is 0x0
Saved registers:
ebp at 0xbffff5d4, eip at 0xbffff5d8
info args
打印出當(dāng)前函數(shù)的參數(shù)名及其值。
info locals
打印出當(dāng)前函數(shù)中所有局部變量及其值。
info catch
打印出當(dāng)前的函數(shù)中的異常處理信息。
查看源程序
—————
一、顯示源代碼
GDB 可以打印出所調(diào)試程序的源代碼,當(dāng)然,在程序編譯時(shí)一定要加上-g的參數(shù),把
源程序信息編譯到執(zhí)行文件中。不然就看不到源程序了。當(dāng)程序停下來(lái)以后,
GDB會(huì)報(bào)告程序停在了那個(gè)文件的第幾行上。你可以用list命令來(lái)打印程序的源代
碼。還是來(lái)看一看查看源代碼的GDB命令吧。
list
顯示程序第linenum行的周圍的源程序。
list
顯示函數(shù)名為function的函數(shù)的源程序。
list
顯示當(dāng)前行后面的源程序。
list -
顯示當(dāng)前行前面的源程序。
一般是打印當(dāng)前行的上5行和下5行,如果顯示函數(shù)是是上2行下8行,默認(rèn)是10行,當(dāng)
然,你也可以定制顯示的范圍,使用下面命令可以設(shè)置一次顯示源程序的行數(shù)。
set listsize
設(shè)置一次顯示源代碼的行數(shù)。
show listsize
查看當(dāng)前l(fā)istsize的設(shè)置。
list命令還有下面的用法:
list ,
顯示從first行到last行之間的源代碼。
list ,
顯示從當(dāng)前行到last行之間的源代碼。
list +
往后顯示源代碼。
一般來(lái)說(shuō)在list后面可以跟以下這們的參數(shù):
行號(hào)。
<+offset> 當(dāng)前行號(hào)的正偏移量。
<-offset> 當(dāng)前行號(hào)的負(fù)偏移量。
哪個(gè)文件的哪一行。
函數(shù)名。
哪個(gè)文件中的哪個(gè)函數(shù)。
<*address> 程序運(yùn)行時(shí)的語(yǔ)句在內(nèi)存中的地址。
二、搜索源代碼
不僅如此,GDB還提供了源代碼搜索的命令:
forward-search
search
向前面搜索。
reverse-search
全部搜索。
其中,就是正則表達(dá)式,也主一個(gè)字符串的匹配模式,關(guān)于正則表達(dá)式,我就不在這里講了,還請(qǐng)各位查看相關(guān)資料。
三、指定源文件的路徑
某些時(shí)候,用-g編譯過(guò)后的執(zhí)行程序中只是包括了源文件的名字,沒有路徑名。GDB提供了可以讓你指定源文件的路徑的命令,以便GDB進(jìn)行搜索。
directory
dir
加一個(gè)源文件路徑到當(dāng)前路徑的前面。如果你要指定多個(gè)路徑,UNIX下你可以使用“:”,Windows下你可以使用“;”。
directory
清除所有的自定義的源文件搜索路徑信息。
show directories
顯示定義了的源文件搜索路徑。
四、源代碼的內(nèi)存
你可以使用info line命令來(lái)查看源代碼在內(nèi)存中的地址。info line后面可以跟
“行號(hào)”,“函數(shù)名”,“文件名:行號(hào)”,“文件名:函數(shù)名”,這個(gè)命令會(huì)打印出所指定的
源碼在運(yùn)行時(shí)的內(nèi)存地址,如:
(gdb) info line tst.c:func
Line 5 of "tst.c" starts at address 0x8048456 and ends at 0x804845d .
還有一個(gè)命令(disassemble)你可以查看源程序的當(dāng)前執(zhí)行時(shí)的機(jī)器碼,這個(gè)命令
會(huì)把目前內(nèi)存中的指令dump出來(lái)。如下面的示例表示查看函數(shù)func的匯編代碼。
(gdb) disassemble func
Dump of assembler code for function func:
0x8048450 : push %ebp
0x8048451 : mov %esp,%ebp
0x8048453 : sub $0x18,%esp
0x8048456 : movl $0x0,0xfffffffc(%ebp)
0x804845d : movl $0x1,0xfffffff8(%ebp)
0x8048464 : mov 0xfffffff8(%ebp),%eax
0x8048467 : cmp 0x8(%ebp),%eax
0x804846a : jle 0x8048470
0x804846c : jmp 0x8048480
0x804846e : mov %esi,%esi
0x8048470 : mov 0xfffffff8(%ebp),