版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報或認(rèn)領(lǐng)
文檔簡介
C++調(diào)試HUAWEI業(yè)務(wù)與軟件產(chǎn)品線研發(fā)培訓(xùn)組(2006.04)目錄調(diào)試的意義gdb概述一個例子啟動gdb查看源碼使用斷點(diǎn)查看棧查看運(yùn)行時數(shù)據(jù)修改運(yùn)行時數(shù)據(jù)小結(jié)調(diào)試的意義----什么是調(diào)試調(diào)試的定義:調(diào)試是在軟件開發(fā)的編碼階段對軟件功能正確的驗(yàn)證,和對已發(fā)現(xiàn)的問題進(jìn)行分析定位,直到最后的解決,是一個“發(fā)現(xiàn)問題->定位問題->解決問題->驗(yàn)證問題->發(fā)現(xiàn)問題”這樣的一個閉環(huán)過程。調(diào)試的意義----開發(fā)過程中的作用(1)窺探程序內(nèi)部機(jī)制(2)發(fā)現(xiàn)問題,解決問題的重要輔助手段(3)有效的調(diào)試方法能夠快速定位出軟件中存在的問題。(4)調(diào)試是軟件開發(fā)必不可少的一環(huán)。打個比方,軟件和人一樣也有生命周期,調(diào)試類似于對人的教育:使其不斷改進(jìn),發(fā)現(xiàn)并改正錯誤的習(xí)慣,最終成長為有用的人才。gdb概述(1)----簡介GDB是GNU開源組織發(fā)布的一個強(qiáng)大的Unix/Linux下的程序調(diào)試工具;是一個命令行程序;功能強(qiáng)大;gdb概述(2)----主要功能1、啟動你的程序,可以按照你的自定義的要求隨心所欲的運(yùn)行程序;2、可讓被調(diào)試的程序在你所指定的調(diào)置的斷點(diǎn)處停住;3、當(dāng)程序被停住時,可以檢查此時你的程序中所發(fā)生的事;4、動態(tài)的改變你程序的執(zhí)行環(huán)境。一個例子啟動gdb需使用-g來編譯程序:1、gdb<program>program也就是你的執(zhí)行文件,一般在當(dāng)然目錄下。
2、gdb<program>core
用gdb同時調(diào)試一個運(yùn)行程序和core文件,core是程序非法執(zhí)行后coredump后產(chǎn)生的文件。查看源碼----listlist<linenum>
顯示程序第linenum行的周圍的源程序。
list<function>
顯示函數(shù)名為function的函數(shù)的源程序。
list
顯示當(dāng)前行后面的源程序。
list-
顯示當(dāng)前行前面的源程序。list<first>,<last>
顯示從first行到last行之間的源代碼。
list,<last>
顯示從當(dāng)前行到last行之間的源代碼。list+
往后顯示源代碼使用斷點(diǎn)----設(shè)置斷點(diǎn)(1)break<function>
在進(jìn)入指定函數(shù)時停住。C++中可以使用class::function或function(type,type)格式來指定函數(shù)名。
break<linenum>
在指定行號停住。
break+offsetbreak-offset
在當(dāng)前行號的前面或后面的offset行停住。offiset為自然數(shù)。
breakfilename:linenum
在源文件filename的linenum行處停住。
breakfilename:function
在源文件filename的function函數(shù)的入口處停住。使用斷點(diǎn)----設(shè)置斷點(diǎn)(2)break*address
在程序運(yùn)行的內(nèi)存地址處停住。
breakbreak命令沒有參數(shù)時,表示在下一條指令處停住。
break...if<condition>...可以是上述的參數(shù),condition表示條件,在條件成立時停住。比如在循環(huán)境體中,可以設(shè)置breakifi=100,表示當(dāng)i為100時停住程序。查看斷點(diǎn)時,可使用info命令,如下所示:(注:n表示斷點(diǎn)號)
infobreakpoints[n]infobreak[n]使用斷點(diǎn)----設(shè)置觀察點(diǎn)
觀察點(diǎn)一般來觀察某個表達(dá)式的值是否有變化了,如果有變化,馬上停住程序。
watch<expr>
為表達(dá)式(變量)expr設(shè)置一個觀察點(diǎn)。一量表達(dá)式值有變化時,馬上停住程序。
rwatch<expr>
當(dāng)表達(dá)式(變量)expr被讀時,停住程序。
awatch<expr>
當(dāng)表達(dá)式(變量)的值被讀或被寫時,停住程序。
infowatchpoints
列出當(dāng)前所設(shè)置了的所有觀察點(diǎn)。使用斷點(diǎn)----設(shè)置捕捉點(diǎn)可設(shè)置捕捉點(diǎn)來補(bǔ)捉程序運(yùn)行時的一些事件。如:載入共享庫(動態(tài)鏈接庫)或是C++的異常。設(shè)置捕捉點(diǎn)的格式為:catch<event>當(dāng)event發(fā)生時,停住程序。event可以是下面的內(nèi)容:
1、throw一個C++拋出的異常。
2、catch一個C++捕捉到的異常。
tcatch<event>
只設(shè)置一次捕捉點(diǎn),當(dāng)程序停住以后,應(yīng)點(diǎn)被自動刪除。使用斷點(diǎn)----去除斷點(diǎn)(1)有三種辦法:clear,delete,disableclear
清除所有的已定義的停止點(diǎn)。
clear<function>clear<filename:function>
清除所有設(shè)置在函數(shù)上的停止點(diǎn)。
clear<linenum>clear<filename:linenum>
清除所有設(shè)置在指定行上的停止點(diǎn)。
使用斷點(diǎn)----去除斷點(diǎn)(2)delete[breakpoints][range...]
刪除指定的斷點(diǎn),breakpoints為斷點(diǎn)號。如果不指定斷點(diǎn)號,則表示刪除所有的斷點(diǎn)。range表示斷點(diǎn)號的范圍(如:3-7)。其簡寫命令為d。使用斷點(diǎn)----去除斷點(diǎn)(3)disable[breakpoints][range...]disable所指定的停止點(diǎn),breakpoints為停止點(diǎn)號。如果什么都不指定,表示disable所有的停止點(diǎn)。簡寫命令是dis.enable[breakpoints][range...]enable所指定的停止點(diǎn),breakpoints為停止點(diǎn)號。
enable[breakpoints]oncerange...enable所指定的停止點(diǎn)一次,當(dāng)程序停止后,該停止點(diǎn)馬上被GDB自動disable。
enable[breakpoints]deleterange...enable所指定的停止點(diǎn)一次,當(dāng)程序停止后,該停止點(diǎn)馬上被GDB自動刪除。使用斷點(diǎn)----條件斷點(diǎn)維護(hù)為斷點(diǎn)設(shè)置一個條件,使用if關(guān)鍵詞,后面跟其斷點(diǎn)條件。并且,條件設(shè)置好后,可以用condition命令來修改斷點(diǎn)的條件。(只有break和watch命令支持if,catch目前暫不支持if)condition<bnum><expression>
修改斷點(diǎn)號為bnum的停止條件為expression。
condition<bnum>
清除斷點(diǎn)號為bnum的停止條件。使用斷點(diǎn)----斷點(diǎn)處執(zhí)行命令可以使用GDB提供的command命令來設(shè)置停止點(diǎn)的運(yùn)行命令。當(dāng)運(yùn)行的程序在被停止住時,我們可以讓其自動運(yùn)行一些別的命令,很有利行自動化調(diào)試。例如:
breakfooifx>0commandprintf"xis%d\n",xcontinueend
注:斷點(diǎn)設(shè)置在函數(shù)foo中,斷點(diǎn)條件是x>0,如果程序被斷住后,也就是,一旦x的值在foo函數(shù)中大于0,GDB會自動打印出x的值,并繼續(xù)運(yùn)行程序。使用斷點(diǎn)----單步調(diào)試step<count>stepin
單步跟蹤,如果有函數(shù)調(diào)用,他會進(jìn)入該函數(shù)。后面可以加count也可以不加,不加表示一條條地執(zhí)行,加表示執(zhí)行后面的count條指令,然后再停住。
next<count>stepover
單步跟蹤,如果有函數(shù)調(diào)用,他不會進(jìn)入該函數(shù)。后面可以加count也可以不加,不加表示一條條地執(zhí)行,加表示執(zhí)行后面的count條指令,然后再停住。使用斷點(diǎn)----恢復(fù)程序運(yùn)行continue[ignore-count]c[ignore-count]
恢復(fù)程序運(yùn)行,直到程序結(jié)束,或是下一個斷點(diǎn)到來。ignore-count表示忽略其后的斷點(diǎn)次數(shù)。使用斷點(diǎn)----多線程break<lineno>thread<threadno>break<lineno>thread<threadno>if...
lineno指定了斷點(diǎn)設(shè)置在的源程序的行號。threadno指定了線程的ID,注意,這個ID是GDB分配的,你可以通過“infothreads”命令來查看正在運(yùn)行程序中的線程信息。如果你不指定thread<threadno>則表示你的斷點(diǎn)設(shè)在所有線程上面。你還可以為某線程指定斷點(diǎn)條件。如:
(gdb)breakfrik.c:13thread28ifbartab>lim
當(dāng)你的程序被GDB停住時,所有的運(yùn)行線程都會被停住。這方便你你查看運(yùn)行程序的總體情況。而在你恢復(fù)程序運(yùn)行時,所有的線程也會被恢復(fù)運(yùn)行。那怕是主進(jìn)程在被單步調(diào)試時。查看棧----為什么要查看棧
當(dāng)程序異常退出,第一件事就是查看程序是在哪里退出的。當(dāng)程序調(diào)用了一個函數(shù),函數(shù)的地址,函數(shù)參數(shù),函數(shù)內(nèi)的局部變量都會被壓入“?!保⊿tack)中。可以用GDB命令來查看當(dāng)前的棧中的信息。查看棧----backtracebacktracebt
打印當(dāng)前的函數(shù)調(diào)用棧的所有信息。如:
(gdb)bt#0func(n=250)attst.c:6#10x08048524inmain(argc=1,argv=0xbffff674)attst.c:30#20x400409edin__libc_start_main()from/lib/libc.so.6
從上可以看出函數(shù)的調(diào)用棧信息:__libc_start_main-->main()-->func()查看運(yùn)行時數(shù)據(jù)----print
調(diào)試程序時,當(dāng)程序被中斷時,你可以使用print命令(簡寫命令為p),或是同義命令inspect來查看當(dāng)前程序的運(yùn)行數(shù)據(jù)。print命令的格式是:
print<expr>print/<f><expr><expr>是表達(dá)式,是你所調(diào)試的程序的語言的表達(dá)式(GDB可以調(diào)試多種編程語言),<f>是輸出的格式,比如,如果要把表達(dá)式按16進(jìn)制的格式輸出,那么就是/x。查看運(yùn)行時數(shù)據(jù)----變量在GDB中,你可以隨時查看以下三種變量的值:
1、全局變量(所有文件可見的)
2、靜態(tài)全局變量(當(dāng)前文件可見的)
3、局部變量(當(dāng)前Scope可見的)如果你的局部變量和全局變量發(fā)生沖突(也就是重名),一般情況下是局部變量會隱藏全局變量,如果此時你想查看全局變量的值時,你可以使用“::”操作符:
file::variablefunction::variable
可以通過這種形式指定你所想查看的變量,是哪個文件中的或是哪個函數(shù)中的。例如,查看文件f2.c中的全局變量x的值:
gdb)p'f2.c'::x查看運(yùn)行時數(shù)據(jù)----數(shù)組你需要查看一段連續(xù)的內(nèi)存空間的值。比如數(shù)組的一段,或是動態(tài)分配的數(shù)據(jù)的大小。你可以使用GDB的“@”操作符,“@”的左邊是第一個內(nèi)存的地址的值,“@”的右邊則你你想查看內(nèi)存的長度。例如,你的程序中有這樣的語句:
int[]array={1,2,3,4,5,6,7,8,9};
于是,在GDB調(diào)試過程中,你可以以如下命令顯示出這個數(shù)組的值:
(gdb)p*array@9$1={1,2,3,4,5,6,7,8,9}查看運(yùn)行時數(shù)據(jù)----顯示格式x按十六進(jìn)制格式顯示變量。
d按十進(jìn)制格式顯示變量。
u按十六進(jìn)制格式顯示無符號整型。
o按八進(jìn)制格式顯示變量。
t按二進(jìn)制格式顯示變量。
a按十六進(jìn)制格式顯示變量。
c按字符格式顯示變量。
f按浮點(diǎn)數(shù)格式顯示變量。例:
(gdb)pi$21=101
(gdb)p/ai$22=0x65修改運(yùn)行時數(shù)據(jù)----意義
一旦使用GDB掛上被調(diào)試程序,當(dāng)程序運(yùn)行起來后,你可以根據(jù)自己的調(diào)試思路來動態(tài)地在GDB中更改當(dāng)前被調(diào)試程序的運(yùn)行線路或是其變量的值,這個強(qiáng)大的功能能夠讓你更好的調(diào)試你的程序,比如,你可以在程序的一次運(yùn)行中走遍程序的所有分支。修改運(yùn)行時數(shù)據(jù)----修改變量值語法:setvar=newvalue例:
(gdb)whatisitype=int(gdb)pi$4=13(gdb)seti=47(gdb)pi$5=13修改運(yùn)行時數(shù)據(jù)----跳轉(zhuǎn)執(zhí)行
一般來說,被調(diào)試程序會按照程序代碼的運(yùn)行順序依次執(zhí)行。GDB提供了亂序執(zhí)行的功能,也就是說,GDB可以修改程序的執(zhí)行順序,可以讓程序執(zhí)行隨意跳躍。這個功能可以由GDB的jump命令來完:
jump<linespec>
指定下一條語句的運(yùn)行點(diǎn)。<linespce>可以是文件的行號,可以是file:line格式,可以是+num這種偏移量格式。表式著下一條運(yùn)行語句從哪里開始。
jump<address>
這里的<address>是代碼行的內(nèi)存地址
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 《金字塔原理》讀書筆記個人所感
- 2022年“安全生產(chǎn)月”宣傳活動方案【4篇】
- 2021公司年終個人總結(jié)五篇
- 幼兒園教育實(shí)習(xí)調(diào)查報告匯編4篇
- 驕傲的初中滿分作文素材700字
- 科學(xué)發(fā)展觀提出的背景及形成與發(fā)展
- 生物學(xué)院食品安全-課件
- 全面保潔服務(wù)協(xié)議書(2篇)
- 兒童圖書銷售代理合同(2篇)
- 山西呂梁2025屆高三上學(xué)期11月期中考試化學(xué)試卷試題及答案解析
- 財務(wù)共享中心招聘筆試環(huán)節(jié)第一部分附有答案
- 國產(chǎn)動漫中的價值觀承載與傳播探索
- 2021-2022學(xué)年重慶市渝北區(qū)西師大版六年級上冊期末調(diào)研測試數(shù)學(xué)試卷
- 吉林省白山市撫松縣2023-2024學(xué)年部編版八年級上學(xué)期期末測試歷史試卷
- 改革開放史智慧樹知到期末考試答案2024年
- 市政公司3年戰(zhàn)略規(guī)劃方案
- 2024年全國中考英語試單選(動詞時態(tài))
- 2024年江蘇護(hù)理職業(yè)學(xué)院高職單招(英語/數(shù)學(xué)/語文)筆試歷年參考題庫含答案解析
- 血糖儀使用規(guī)范課件
- DB21-T 2931-2018羊肚菌日光溫室栽培技術(shù)規(guī)程
- 貴州省黔東南州2023-2024學(xué)年九年級上學(xué)期期末文化水平測試化學(xué)試卷
評論
0/150
提交評論