《嵌入式Linux開發(fā)實(shí)踐教程第2版》課件匯 下 平震宇 gdb的基本調(diào)試-嵌入式GUI應(yīng)用開發(fā)與移植_第1頁
《嵌入式Linux開發(fā)實(shí)踐教程第2版》課件匯 下 平震宇 gdb的基本調(diào)試-嵌入式GUI應(yīng)用開發(fā)與移植_第2頁
《嵌入式Linux開發(fā)實(shí)踐教程第2版》課件匯 下 平震宇 gdb的基本調(diào)試-嵌入式GUI應(yīng)用開發(fā)與移植_第3頁
《嵌入式Linux開發(fā)實(shí)踐教程第2版》課件匯 下 平震宇 gdb的基本調(diào)試-嵌入式GUI應(yīng)用開發(fā)與移植_第4頁
《嵌入式Linux開發(fā)實(shí)踐教程第2版》課件匯 下 平震宇 gdb的基本調(diào)試-嵌入式GUI應(yīng)用開發(fā)與移植_第5頁
已閱讀5頁,還剩333頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡介

gdb的基本調(diào)試調(diào)試器的基本功能任何一種調(diào)試器,都必須具備如下基本功能建立可執(zhí)行程序與源碼的聯(lián)系(查看源碼)設(shè)置斷點(diǎn)執(zhí)行行基本的調(diào)試命令程序暫停后,查看各種信息查看源程序

GDB可以打印出所調(diào)試程序的源代碼,當(dāng)然,在程序編譯時(shí)一定要加上-g的參數(shù),把源程序信息編譯到執(zhí)行文件中。當(dāng)程序停下來以后,GDB會報(bào)告程序停在了那個(gè)文件的第幾行上。你可以用list命令來打印程序的源代碼??梢钥s寫為llist<linenum>

顯示程序第linenum行的周圍的源程序。list<function>

顯示函數(shù)名為function的函數(shù)的源程序。list

顯示當(dāng)前行后面的源程序。list-

顯示當(dāng)前行前面的源程序。一般是打印當(dāng)前行的上5行和下5行,如果顯示函數(shù)是是上2行下8行,默認(rèn)是10行,當(dāng)然,你也可以定制顯示的范圍,使用下面命令可以設(shè)置一次顯示源程序的行數(shù)。setlistsize<count>

設(shè)置一次顯示源代碼的行數(shù)。setlistsize20設(shè)置顯示一次20行showlistsize

查看當(dāng)前l(fā)istsize的設(shè)置。

查看源程序(2)list命令還有下面的用法list<first>,<last>

顯示從first行到last行之間的源代碼。list,<last>

顯示從當(dāng)前行到last行之間的源代碼。list+

往后顯示源代碼。

一般來說在list后面可以跟以下這們的參數(shù):<linenum>行號。

<+offset>當(dāng)前行號的正偏移量。

<-offset>當(dāng)前行號的負(fù)偏移量。

<filename:linenum>哪個(gè)文件的哪一行。lgdb_tst.c:20<function>函數(shù)名。

<filename:function>

哪個(gè)文件中的哪個(gè)函數(shù)lgdb_tst.c:main<*address>程序運(yùn)行時(shí)的語句在內(nèi)存中的地址。l*0x0804835a調(diào)試程序執(zhí)行g(shù)dbgdbgdb_tst設(shè)置斷點(diǎn)通常至少要設(shè)一個(gè)斷點(diǎn),要不然gdb會直接運(yùn)行到程序結(jié)束.bmain#在主函數(shù)入口設(shè)斷點(diǎn)設(shè)置命令行參數(shù)如果程序需要用到命令行參數(shù),直接在gdb命令是無法輸入setargs

可指定運(yùn)行時(shí)參數(shù)。如:gdb>setargs1020304050開始調(diào)試進(jìn)入gdb提示符后,gdb并沒有進(jìn)調(diào)試狀態(tài)需要用r,即run進(jìn)行調(diào)試在GDB中運(yùn)行程序

當(dāng)以gdb<program>方式啟動gdb后,gdb會在PATH路徑和當(dāng)前目錄中搜索<program>的源文件。如要確認(rèn)gdb是否讀到源文件,可使用l或list命令,看看gdb是否能列出源代碼。在gdb中,運(yùn)行程序使用r或是run命令。程序的運(yùn)行,你有可能需要設(shè)置下面四方面的事。程序運(yùn)行參數(shù)。setargs可指定運(yùn)行時(shí)參數(shù)。如:setargs1020304050運(yùn)行環(huán)境path<dir>可設(shè)定程序的運(yùn)行路徑。showpaths查看程序的運(yùn)行路徑。setenvironmentvarname[=value]設(shè)置環(huán)境變量。如:setenvUSER=hchenshowenvironment[varname]查看環(huán)境變量。工作目錄。cd<dir>

相當(dāng)于shell的cd命令。pwd顯示當(dāng)前的所在目錄。程序的輸入輸出infoterminal顯示你程序用到的終端的模式。使用重定向控制程序輸出。如:run>outfiletty命令可以指寫輸入輸出的終端設(shè)備。如:tty/dev/ttyb常用調(diào)試命令

當(dāng)程序被停住了,你可以用continue命令恢復(fù)程序的運(yùn)行直到程序結(jié)束,或下一個(gè)斷點(diǎn)到來。也可以使用step或next命令單步跟蹤程序。continue[ignore-count]

c[ignore-count]

fg[ignore-count]

恢復(fù)程序運(yùn)行,直到程序結(jié)束,或是下一個(gè)斷點(diǎn)到來。ignore-count表示忽略其后的斷點(diǎn)次數(shù)。continue,c,fg三個(gè)命令都是一樣的意思。step<count>

單步跟蹤,如果有函數(shù)調(diào)用,他會進(jìn)入該函數(shù)。進(jìn)入函數(shù)的前提是,此函數(shù)被編譯有debug信息。很像VC等工具中的stepin。后面可以加count也可以不加,不加表示一條條地執(zhí)行,加表示執(zhí)行后面的count條指令,然后再停住。next<count>

同樣單步跟蹤,如果有函數(shù)調(diào)用,他不會進(jìn)入該函數(shù)。很像VC等工具中的stepsetstep-mode

setstep-modeon

打開step-mode模式,于是,在進(jìn)行單步跟蹤時(shí),程序不會因?yàn)闆]有debug信息而不停住。這個(gè)參數(shù)有很利于查看機(jī)器碼。常用調(diào)試命令(2)setstep-modoff

關(guān)閉step-mode模式。finish

運(yùn)行程序,直到當(dāng)前函數(shù)完成返回。并打印函數(shù)返回時(shí)的堆棧地址和返回值及參數(shù)值等信息。相當(dāng)于VC的stepoutuntil或u

當(dāng)你厭倦了在一個(gè)循環(huán)體內(nèi)單步跟蹤時(shí),這個(gè)命令可以運(yùn)行程序直到退出循環(huán)體。

untillinenumstepi或si

nexti或ni

單步跟蹤一條機(jī)器指令!一條程序代碼有可能由數(shù)條機(jī)器指令完成,stepi和nexti可以單步執(zhí)行機(jī)器指令。與之一樣有相同功能的命令是“display/i$pc”,當(dāng)運(yùn)行完這個(gè)命令后,單步跟蹤會在打出程序代碼的同時(shí)打出機(jī)器指令(也就是匯編代碼)查看運(yùn)行數(shù)據(jù)GDB主要采用print來查看運(yùn)行數(shù)據(jù)print<expr>#顯示表達(dá)式值print/f#f表示格式,如print/x按十六進(jìn)制顯示printf“xis%d\n”,x#格式化輸出GDB可以顯示被調(diào)試程序的const常量、變量、函數(shù),但不能顯示宏內(nèi)容GDB可以查看三種變量全局變量(所有文件可見的)靜態(tài)全局變量(當(dāng)前文件可見的)局部變量(當(dāng)前Scope可見的)如果你的局部變量和全局變量發(fā)生沖突(也就是重名),一般情況下是局部變量會隱藏全局變量使用“::”操作符強(qiáng)制指定變量所在文件或函數(shù),file::variable,function::variable查看運(yùn)行數(shù)據(jù)(2)print后接結(jié)構(gòu)變量名,則可以把它所有成員打印出來查看數(shù)組p*array@len

#人為數(shù)組,查看內(nèi)存中的連續(xù)對象如果是靜態(tài)數(shù)組,直接parrayprint輸出格式x按十六進(jìn)制格式顯示變量。d按十進(jìn)制格式顯示變量。u按十六進(jìn)制格式顯示無符號整型。o按八進(jìn)制格式顯示變量。t按二進(jìn)制格式顯示變量。a按十六進(jìn)制格式顯示變量。p/ai

c按字符格式顯示變量。p/ci

f按浮點(diǎn)數(shù)格式顯示變量。print顯示實(shí)例(gdb)pi$21=101(gdb)p/ai$22=0x65(gdb)p/ci$23=101'e'(gdb)p/fi$24=1.41531145e-43(gdb)p/xi$25=0x65(gdb)p/ti$26=1100101查看內(nèi)存使用examine命令(簡寫是x)來查看內(nèi)存地址中的值。x命令的語法如下所示x/n、f、u是可選的參數(shù)n是一個(gè)正整數(shù),表示顯示內(nèi)存的長度,也就是說從當(dāng)前地址向后顯示幾個(gè)地址的內(nèi)容。f表示顯示的格式,跟print的格式參數(shù)相同u表示從當(dāng)前地址往后請求的字節(jié)數(shù),如果不指定的話,GDB默認(rèn)是4個(gè)bytes。u參數(shù)可以用下面的字符來代替,b表示單字節(jié),h表示雙字節(jié),w表示四字節(jié),g表示八字節(jié)。當(dāng)我們指定了字節(jié)長度后,GDB會從指內(nèi)存定的內(nèi)存地址開始,讀寫指定字節(jié),并把其當(dāng)作一個(gè)值取出來。

n/f/u三個(gè)參數(shù)可以一起使用x/3uh0x54320

表示,從內(nèi)存地址0x54320讀取內(nèi)容,h表示以雙字節(jié)為一個(gè)單位,3表示三個(gè)單位,u表示按十六進(jìn)制顯示。

查看棧信息

當(dāng)程序被停住了,你需要做的第一件事就是查看程序是在哪里停住的。當(dāng)你的程序調(diào)用了一個(gè)函數(shù),函數(shù)的地址,函數(shù)參數(shù),函數(shù)內(nèi)的局部變量都會被壓入“?!保⊿tack)中。你可以用GDB命令來查看當(dāng)前的棧中的信息。backtrace

bt

backtrace<n>

bt<n>

n是一個(gè)正整數(shù),表示只打印棧頂上n層的棧信息。backtrace<-n>

bt<-n>

-n表一個(gè)負(fù)整數(shù),表示只打印棧底下n層的棧信息。

查看棧信息

(2)如果你要查看某一層的信息,你需要在切換當(dāng)前的棧,一般來說,程序停止時(shí),最頂層的棧就是當(dāng)前棧,如果你要查看棧下面層的詳細(xì)信息,首先要做的是切換當(dāng)前棧。frame<n>

f<n>

n是一個(gè)從0開始的整數(shù),是棧中的層編號。比如:frame0,表示棧頂,frame1,表示棧的第二層。up<n>表示向棧的上面移動n層,并打印棧詳細(xì)信息.可以不打n,表示向上移動一層。down<n>表示向棧的下面移動n層,并打印棧詳細(xì)信息,可以不打n,表示向下移動一層。上面的命令,都會打印出移動到的棧層的信息。如果你不想讓其打出信息。你可以使用這三個(gè)命令:select-frame<n>對應(yīng)于frame命令。up-silently<n>對應(yīng)于up命令。down-silently<n>對應(yīng)于down命令。

查看棧信息

(3)infoframe

infof

這個(gè)命令會打印出更為詳細(xì)的當(dāng)前棧層的信息,只不過,大多數(shù)都是運(yùn)行時(shí)的內(nèi)內(nèi)地址。比如:函數(shù)地址,調(diào)用函數(shù)的地址,被調(diào)用函數(shù)的地址,目前的函數(shù)是由什么樣的程序語言寫成的、函數(shù)參數(shù)地址及值、局部變量的地址等等。如:

infoargs

打印出當(dāng)前函數(shù)的參數(shù)名及其值。

infolocals

打印出當(dāng)前函數(shù)中所有局部變量及其值。

infocatch

打印出當(dāng)前的函數(shù)中的異常處理信息查看堆棧的對比查看本地變量對比GDB命令示例在進(jìn)入函數(shù)func時(shí),設(shè)置一個(gè)斷點(diǎn)??梢郧萌隻reakfunc,或是直接就是bfuncbfunc敲入b按兩次TAB鍵,你會看到所有b打頭的命令-b只記得函數(shù)的前綴,可以輸入前綴按tabbmake_<按TAB鍵>調(diào)試C++的程序時(shí),有可以函數(shù)名一樣,輸入前綴按M-?b'bubble(M-?要退出gdb時(shí),只用發(fā)quit或命令簡稱q就行了GDB中運(yùn)行shell命令在gdb環(huán)境中,你可以運(yùn)行shell命令,使用gdb的shell命令來完成:shell<commandstring>調(diào)用Linux的shell來執(zhí)行<commandstring>,環(huán)境變量SHELL中定義的Linux的shell將會被用來執(zhí)行<commandstring>,如果SHELL沒有定義,那就使用Linux的標(biāo)準(zhǔn)shell:/bin/sh。(在Windows中使用C或cmd.exe)make可直接在gdb執(zhí)行make<make-args>可以在gdb中執(zhí)行make命令來重新build自己的程序。這個(gè)命令等價(jià)于“shellmake<make-args>”。Kill

不退出gdb殺死被調(diào)程序,更改程序后重新run保持原有斷點(diǎn)信息gdb特殊調(diào)試方法(選)暫停/恢復(fù)程序運(yùn)行

調(diào)試程序中,暫停程序運(yùn)行是必須的,GDB可以方便地暫停程序的運(yùn)行。你可以設(shè)置程序的在哪行停住,在什么條件下停住,在收到什么信號時(shí)停往等等。以便于你查看運(yùn)行時(shí)的變量,以及運(yùn)行時(shí)的流程。當(dāng)進(jìn)程被gdb停住時(shí),你可以使用infoprogram來查看程序的是否在運(yùn)行,進(jìn)程號,被暫停的原因。在gdb中,我們可以有以下幾種暫停方式:斷點(diǎn)(BreakPoint)、觀察點(diǎn)(WatchPoint)、捕捉點(diǎn)(CatchPoint)、信號(Signals)、線程停止(ThreadStops)。如果要恢復(fù)程序運(yùn)行,可以使用c或是continue命令。VC++不支持attach調(diào)試,也不支持信號和線程停止.暫停方法(2)設(shè)置斷點(diǎn)(BreakPoint)我們用break命令來設(shè)置斷點(diǎn)。有如下設(shè)置斷點(diǎn)的方法:break<function>在進(jìn)入指定函數(shù)時(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ù)的入口處停住。break*address

在程序運(yùn)行的內(nèi)存地址處停住。break

break命令沒有參數(shù)時(shí),表示在下一條指令處停住。break...if<condition>

可以是上述的參數(shù),condition表示條件,在條件成立時(shí)停住。比如在循環(huán)境體中,可以設(shè)置breakifi=100,表示當(dāng)i為100時(shí)停住程序。暫停方法(3)設(shè)置觀察點(diǎn)WatchPoint)觀察點(diǎn)一般來觀察某個(gè)表達(dá)式(變量也是一種表達(dá)式)的值是否有變化了,如果有變化,馬上停住程序。我們有下面的幾種方法來設(shè)置觀察點(diǎn):watch<expr>

為表達(dá)式(變量)expr設(shè)置一個(gè)觀察點(diǎn)。一量表達(dá)式值有變化時(shí),馬上停住程序rwatch<expr>

當(dāng)表達(dá)式(變量)expr被讀時(shí),停住程序。awatch<expr>

當(dāng)表達(dá)式(變量)的值被讀或被寫時(shí),停住程序。

暫停方法(4)設(shè)置捕捉點(diǎn)(CatchPoint)你可設(shè)置捕捉點(diǎn)來補(bǔ)捉程序運(yùn)行時(shí)的一些事件。如:載入共享庫(動態(tài)鏈接庫)或是C++的異常。設(shè)置捕捉點(diǎn)的格式為:catch<event>當(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<libname>載入共享庫(動態(tài)鏈接庫)時(shí)。(load為關(guān)鍵字,目前此功能只在HP-UX下有用)7、unload或unload<libname>卸載共享庫(動態(tài)鏈接庫)時(shí)。(unload為關(guān)鍵字,目前此功能只在HP-UX下有用)

tcatch<event>

只設(shè)置一次捕捉點(diǎn),當(dāng)程序停住以后,應(yīng)點(diǎn)被自動刪除。

信號(Signals)信號是一種軟中斷,是一種處理異步事件的方法。一般來說,操作系統(tǒng)都支持許多信號。尤其是Linux,比較重要應(yīng)用程序一般都會處理信號。Linux定義了許多信號,比如SIGINT表示中斷字符信號,也就是Ctrl+C的信號,SIGBUS表示硬件故障的信號;SIGCHLD表示子進(jìn)程狀態(tài)改變信號;SIGKILL表示終止程序運(yùn)行的信號,等等。信號量編程是Linux下非常重要的一種技術(shù)。GDB有能力在你調(diào)試程序的時(shí)候處理任何一種信號,你可以告訴GDB需要處理哪一種信號。你可以要求GDB收到你所指定的信號時(shí),馬上停住正在運(yùn)行的程序,以供你進(jìn)行調(diào)試。你可以用GDB的handle命令來完成這一功能。handle<signal><keywords...>

在GDB中定義一個(gè)信號處理。信號<signal>可以以SIG開頭或不以SIG開頭,可以用定義一個(gè)要處理信號的范圍(如:SIGIO-SIGKILL,表示處理從SIGIO信號到SIGKILL的信號,其中包括SIGIO,SIGIOT,SIGKILL三個(gè)信號),也可以使用關(guān)鍵字all來標(biāo)明要處理所有的信號。一旦被調(diào)試的程序接收到信號,運(yùn)行程序馬上會被GDB停住,以供調(diào)試。其<keywords>可以是以下幾種關(guān)鍵字的一個(gè)或多個(gè)。信號(Signals)(2)Handle的keywordsnostop

當(dāng)被調(diào)試的程序收到信號時(shí),GDB不會停住程序的運(yùn)行,但會打出消息告訴你收到這種信號。

stop

當(dāng)被調(diào)試的程序收到信號時(shí),GDB會停住你的程序。

print

當(dāng)被調(diào)試的程序收到信號時(shí),GDB會顯示出一條信息。

noprint

當(dāng)被調(diào)試的程序收到信號時(shí),GDB不會告訴你收到信號的信息。

pass

noignore

當(dāng)被調(diào)試的程序收到信號時(shí),GDB不處理信號。這表示,GDB會把這個(gè)信號交給被調(diào)試程序會處理。

nopass

ignore

當(dāng)被調(diào)試的程序收到信號時(shí),GDB不會讓被調(diào)試程序來處理這個(gè)信號。線程(ThreadStops)

如果你程序是多線程的話,你可以定義你的斷點(diǎn)是否在所有的線程上,或是在某個(gè)特定的線程。GDB很容易幫你完成這一工作。break<linespec>thread<threadno>

break<linespec>thread<threadno>if...linespec指定了斷點(diǎn)設(shè)置在的源程序的行號。threadno指定了線程的ID,注意,這個(gè)ID是GDB分配的,你可以通過“infothreads”命令來查看正在運(yùn)行程序中的線程信息。如果你不指定thread<threadno>則表示你的斷點(diǎn)設(shè)在所有線程上面。你還可以為某線程指定斷點(diǎn)條件。(gdb)breakfrik.c:13thread28ifbartab>lim當(dāng)你的程序被GDB停住時(shí),所有的運(yùn)行線程都會被停住。這方便你你查看運(yùn)行程序的總體情況。而在你恢復(fù)程序運(yùn)行時(shí),所有的線程也會被恢復(fù)運(yùn)行。那怕是主進(jìn)程在被單步調(diào)試時(shí)。

查看信息info查看斷點(diǎn)時(shí),(注:n表示斷點(diǎn)號)

infobreakpoints[n]

infobreak[n]列出當(dāng)前所設(shè)置了的所有觀察點(diǎn)。infowatchpoints

查看有哪些信號在被GDB檢測中infosignals

infohandle

維護(hù)停止點(diǎn)上面說了如何設(shè)置程序的停止點(diǎn),GDB中的停止點(diǎn)也就是上述的三類。在GDB中,如果你覺得已定義好的停止點(diǎn)沒有用了,你可以使用delete、clear、disable、enable這幾個(gè)命令來進(jìn)行維護(hù)。clear<function>clear<filename:function>

清除所有設(shè)置在函數(shù)上的停止點(diǎn)。delete[breakpoints][range...]

刪除指定的斷點(diǎn),breakpoints為斷點(diǎn)號。如果不指定斷點(diǎn)號,則表示刪除所有的斷點(diǎn)。range表示斷點(diǎn)號的范圍(如:3-7)。其簡寫命令為d。維護(hù)停止點(diǎn)(2)比刪除更好的一種方法是disable停止點(diǎn),disable了的停止點(diǎn),GDB不會刪除,當(dāng)你還需要時(shí),enable即可,就好像回收站一樣。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自動刪除。停止條件維護(hù)

前面在說到設(shè)置斷點(diǎn)時(shí),我們提到過可以設(shè)置一個(gè)條件,當(dāng)條件成立時(shí),程序自動停止,這是一個(gè)非常強(qiáng)大的功能.條件有相關(guān)維護(hù)命令。一般來說,為斷點(diǎn)設(shè)置一個(gè)條件,我們使用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的停止條件。還有一個(gè)比較特殊的維護(hù)命令ignore,你可以指定程序運(yùn)行時(shí),忽略停止條件幾次。ignore<bnum><count>

表示忽略斷點(diǎn)號為bnum的停止條件count次。為停止點(diǎn)設(shè)定運(yùn)行命令我們可以使用GDB提供的command命令來設(shè)置停止點(diǎn)的運(yùn)行命令。也就是說,當(dāng)運(yùn)行的程序在被停止住時(shí),我們可以讓其自動運(yùn)行一些別的命令,這很有利行自動化調(diào)試。對基于GDB的自動化調(diào)試是一個(gè)強(qiáng)大的支持。commands[bnum]

...command-list...

end為斷點(diǎn)號bnum指寫一個(gè)命令列表。當(dāng)程序被該斷點(diǎn)停住時(shí),gdb會依次運(yùn)行命令列表中的命令。如果你要清除斷點(diǎn)上的命令序列,那么只要簡單的執(zhí)行一下commands命令,并直接在打個(gè)end就行了。斷點(diǎn)菜單在C++中,可能會重復(fù)出現(xiàn)同一個(gè)名字的函數(shù)若干次(函數(shù)重載),在這種情況下,break<function>不能告訴GDB要停在哪個(gè)函數(shù)的入口。當(dāng)然,你可以使用break<function(type)>也就是把函數(shù)的參數(shù)類型告訴GDB,以指定一個(gè)函數(shù)。否則的話,GDB會給你列出一個(gè)斷點(diǎn)菜單供你選擇你所需要的斷點(diǎn)。你只要輸入你菜單列表中的編號就可以了.GDB列出了所有的重載函數(shù),你可以選一下列表編號就行了。0表示放棄設(shè)置斷點(diǎn),1表示所有函數(shù)都設(shè)置斷點(diǎn)。搜索源代碼向前面搜索。forward-search<regexp>

search<regexp>全部搜索。reverse-search<regexp>其中,<regexp>就是正則表達(dá)式,也主一個(gè)字符串的匹配模式

源代碼處理指定源文件的路徑某些時(shí)候,用-g編譯過后的執(zhí)行程序中只是包括了源文件的名字,沒有路徑名。GDB提供了可以讓你指定源文件的路徑的命令,以便GDB進(jìn)行搜索。directory<dirname...>

dir<dirname...>

加一個(gè)源文件路徑到當(dāng)前路徑的前面。如果你要指定多個(gè)路徑,UNIX下你可以使用“:”,Windows下你可以使用“;”。directory

清除所有的自定義的源文件搜索路徑信息。showdirectories

顯示定義了的源文件搜索路徑。查看源代碼的內(nèi)存你可以使用infoline命令來查看源代碼在內(nèi)存中的地址。infoline后面可以跟“行號”,“函數(shù)名”,“文件名:行號”,“文件名:函數(shù)名”,這個(gè)命令會打印出所指定的源碼在運(yùn)行時(shí)的內(nèi)存地址,查看源碼的匯編disassemblefuncGDB環(huán)境變量你可以在GDB的調(diào)試環(huán)境中定義自己的變量,用來保存一些調(diào)試程序中的運(yùn)行數(shù)據(jù)。要定義一個(gè)GDB的變量很簡單只需。使用GDB的set命令。GDB的環(huán)境變量和UNIX一樣,也是以$起頭。set$foo=*object_ptr使用環(huán)境變量時(shí),GDB會在你第一次使用時(shí)創(chuàng)建這個(gè)變量,而在以后的使用中,則直接對其賦值。環(huán)境變量沒有類型,你可以給環(huán)境變量定義任一的類型。包括結(jié)構(gòu)體和數(shù)組。showconvenience

該命令查看當(dāng)前所設(shè)置的所有的環(huán)境變量。

改變程序的執(zhí)行

一旦使用GDB掛上被調(diào)試程序,當(dāng)程序運(yùn)行起來后,你可以根據(jù)自己的調(diào)試思路來動態(tài)地在GDB中更改當(dāng)前被調(diào)試程序的運(yùn)行線路或是其變量的值,這個(gè)強(qiáng)大的功能能夠讓你更好的調(diào)試你的程序,修改變量值修改被調(diào)試程序運(yùn)行時(shí)的變量值,在GDB中很容易實(shí)現(xiàn),使用GDB的print命令即可完成。如:printx=4跳轉(zhuǎn)執(zhí)行

一般來說,被調(diào)試程序會按照程序代碼的運(yùn)行順序依次執(zhí)行。GDB提供了亂序執(zhí)行的功能,也就是說,GDB可以修改程序的執(zhí)行順序,可以讓程序執(zhí)行隨意跳躍。這個(gè)功能可以由GDB的jump命令來完成:jump<linespec>指定下一條語句的運(yùn)行點(diǎn)。<linespce>可以是文件的行號,可以是file:line格式,可以是+num這種偏移量格式。表式著下一條運(yùn)行語句從哪里開始。jump<address>

這里的<address>是代碼行的內(nèi)存地址。注意,jump命令不會改變當(dāng)前的程序棧中的內(nèi)容,所以,當(dāng)你從一個(gè)函數(shù)跳到另一個(gè)函數(shù)時(shí),當(dāng)函數(shù)運(yùn)行完返回時(shí)進(jìn)行彈棧操作時(shí)必然會發(fā)生錯誤,可能結(jié)果還是非常奇怪的,甚至于產(chǎn)生程序CoreDump。所以最好是同一個(gè)函數(shù)中進(jìn)行跳轉(zhuǎn)。

改變程序的執(zhí)行(2)產(chǎn)生信號量使用singal命令,可以產(chǎn)生一個(gè)信號量給被調(diào)試的程序。如:中斷信號Ctrl+C。這非常方便于程序的調(diào)試,可以在程序運(yùn)行的任意位置設(shè)置斷點(diǎn),并在該斷點(diǎn)用GDB產(chǎn)生一個(gè)信號量,這種精確地在某處產(chǎn)生信號非常有利程序的調(diào)試。signal<singal>Linux的系統(tǒng)信號量通常從1到15。所以<singal>取值也在這個(gè)范圍。強(qiáng)制函數(shù)返回如果你的調(diào)試斷點(diǎn)在某個(gè)函數(shù)中,并還有語句沒有執(zhí)行完。你可以使用return命令強(qiáng)制函數(shù)忽略還沒有執(zhí)行的語句并返回。return

return<expression>

使用return命令取消當(dāng)前函數(shù)的執(zhí)行,并立即返回,如果指定了<expression>,那么該表達(dá)式的值會被認(rèn)作函數(shù)的返回值。強(qiáng)制調(diào)用函數(shù)call<expr>

pfunc

表達(dá)式中可以一是函數(shù),以此達(dá)到強(qiáng)制調(diào)用函數(shù)的目的。并顯示函數(shù)的返回值,如果函數(shù)返回值是void,那么就不顯示。另一個(gè)相似的命令也可以完成這一功能——print,print后面可以跟表達(dá)式,所以也可以用他來調(diào)用函數(shù),print和call的不同是,如果函數(shù)返回void,call則不顯示,print則顯示函數(shù)返回值,并把該值存入歷史數(shù)據(jù)中。

gdb特殊應(yīng)用調(diào)試已運(yùn)行的程序

兩種方法在Linux下用ps查看正在運(yùn)行的程序的PID(進(jìn)程ID),然后用gdb<program>PID格式掛接正在運(yùn)行的程序。先用gdb<program>關(guān)聯(lián)上源代碼,并進(jìn)行g(shù)db,在gdb中用attach命令來掛接進(jìn)程的PID。并用detach來取消掛接的進(jìn)程。這是調(diào)試守護(hù)進(jìn)程常用這兩種方法調(diào)試已運(yùn)行進(jìn)程運(yùn)行程序,并用ps查看進(jìn)程編號./server&進(jìn)入gdbgdbserver設(shè)置斷點(diǎn)掛接進(jìn)程attach<pid>掛接進(jìn)程,如attach2595此時(shí)被掛接進(jìn)程會暫停下來用continue命令恢復(fù)運(yùn)行,進(jìn)行調(diào)試C正常調(diào)試階段使用gdb查找段錯誤在Linux下,程序經(jīng)常出現(xiàn)段錯誤(segmentfault)通常是訪問錯誤的地址,如向空指針賦值,訪問不存在的地址,寫到不可能區(qū)段產(chǎn)生段錯誤原因1)訪問系統(tǒng)數(shù)據(jù)區(qū),尤其是往系統(tǒng)保護(hù)的內(nèi)存地址寫數(shù)據(jù),向空地址寫值也歸屬此類2)內(nèi)存越界(數(shù)組越界,變量類型不一致等)訪問到不屬于你的內(nèi)存區(qū)域在Linux下,出現(xiàn)段錯誤會觸發(fā)SIGSEGV信號這個(gè)信號的缺省結(jié)果打印段錯誤,并產(chǎn)生一個(gè)coredump文件用gdb打開coredump文件會快速定位出現(xiàn)段錯誤代碼段錯誤實(shí)例#include<stdio.h>intmain(){char*a=0x00;

*a=100;

return0;}生成CoreDump文件缺省Linux不生成CoreDump用ulimit–cxxx來改變尺寸,生成CoreDump文件當(dāng)產(chǎn)生段錯誤時(shí),在可執(zhí)行文件同一目錄生成core.XXX的文件用gdb打開Coredump定位gdb<可執(zhí)行文件><core文件名>ddd-gdb的圖形版ddd的編譯安裝要求安裝gdb和圖形界面安裝步驟解壓:tarxvzfddd-3.3.10.tar.gz生成Makefile:cdddd-3.3.10;./configure編譯make安裝makeinstall運(yùn)行ddd直接在命令行下輸入ddd即可或輸入調(diào)試程序名字dddgdb_tstddd運(yùn)行效果Debugger進(jìn)行調(diào)試KDE自帶Debugger也是一個(gè)圖形調(diào)試器調(diào)試時(shí)用File->Executable…打開一個(gè)帶調(diào)試信息的可執(zhí)行文件,它將自動打開同一目錄下的源碼課堂練習(xí)設(shè)計(jì)一個(gè)字符串比較程序,把一個(gè)數(shù)組中多個(gè)字符串進(jìn)行排序.并按降序輸出,用GDB進(jìn)行調(diào)試用gdb調(diào)試有問題的程序謝謝,請?zhí)釂栐诏偪竦臅r(shí)代把握未來Micro2440軟件資源光盤映象用戶手冊LinuxWindowsCEAndroidMicro2440光盤文件Micro2440光盤文件Micro2440硬件資源ARM9開發(fā)板目前市場上ARM9的開發(fā)板很多,如天嵌、友善之臂等,它們都以S3C2440為核心,加上對片上資源的外設(shè)設(shè)計(jì),其結(jié)構(gòu)和配置基本類似。

Micro2440開發(fā)板本書目標(biāo)板采用友善之臂的Micro2440。Micro2440開發(fā)板由核心板Micro2440和底板Micro2440SDK組成

嵌入式系統(tǒng)運(yùn)行環(huán)境CPU:SamsungS3C2440AL-40SDRAM:32-bit64Mbyte2MNorflash+64MNandFlash(板上跳線選擇)10針2.0mm間距在板JTAG接口(無需底板即可調(diào)試編程)4個(gè)用戶LED162針2.0mm間距三圍插座

板載復(fù)位電路,有復(fù)位按鍵5Vpowersupply

操作系統(tǒng)支持 Linux-2.6.13+Qtopia WindowsCE5.0 uCos2Micro2440核心板Micro2440有兩種Flash,一種是NORFlash,大小為2Mbyte;另一種是NandFlash,大小為256M(可兼容最大1GNandFlash),通過跳線J1可以選擇從NAND或NOR啟動系統(tǒng)。一般NORFLASH里面放置的是不經(jīng)常更改的BIOS(如supervivi),NANDFLASH里面則燒寫完整的系統(tǒng)程序(bootloader、內(nèi)核、文件系統(tǒng)等)。Micro2440底板1個(gè)100M網(wǎng)絡(luò)RJ-45接口,采用DM9000網(wǎng)卡芯片3個(gè)串口接口,分別有RS232接口和TTL接口引出4個(gè)USBHost(使用USB1.1協(xié)議),通過USBHUB芯片擴(kuò)展1個(gè)USBSlave(使用USB1.1協(xié)議)標(biāo)準(zhǔn)音頻輸出接口,在板麥克風(fēng)(MIC)1個(gè)PWM控制蜂鳴器1個(gè)可調(diào)電阻接W1,用于AD轉(zhuǎn)換測試6個(gè)用戶按鍵,并通過排針座引出,可作為其他用途。安裝與體驗(yàn)Linux+QT嵌入式系統(tǒng)初始的嵌入式系統(tǒng)是一個(gè)空白的系統(tǒng),就如同沒有安裝操作系統(tǒng)的PC機(jī)一樣,需要通過主機(jī)為它構(gòu)建基本的軟件系統(tǒng)并燒制到嵌入式設(shè)備中。

“宿主機(jī)/目標(biāo)板”開發(fā)模式利用宿主機(jī)(PC機(jī))上豐富的軟硬件資源及良好的開發(fā)環(huán)境和調(diào)試工具來開發(fā)目標(biāo)板上的軟件,通過交叉編譯環(huán)境生成可執(zhí)行文件,通過串口/USB/以太網(wǎng)等方式下載到目標(biāo)板上,利用交叉調(diào)試器在監(jiān)控程序運(yùn)行,實(shí)時(shí)分析,最后,將程序下載固化到目標(biāo)機(jī)上,完成整個(gè)開發(fā)過程。

嵌入式系統(tǒng)運(yùn)行環(huán)境Bootloader內(nèi)核文件系統(tǒng)系統(tǒng)應(yīng)用與圖形界面系統(tǒng)任務(wù)要求StepOne外部接口連接StepTwo超級終端配置StepThree安裝USB下載驅(qū)動StepFour下載文件系統(tǒng)StepTwo開機(jī)初始化QT圖形界面StepOne使用直連串口線連接開發(fā)板的串口0和PC機(jī)的串口用交叉網(wǎng)線將開發(fā)板的網(wǎng)絡(luò)接口與PC相連用5V電源適配器連接到板上的5V輸入插座用USB電纜連接開發(fā)板和PC開發(fā)板的啟動模式S2接到NorFlash標(biāo)識一側(cè)時(shí),系統(tǒng)將從NorFlash啟動StepTwo為了通過串口連接開發(fā)板,必須使用一個(gè)模擬終端程序,通常使用Windows自帶的超級終端,Linux系統(tǒng)也自帶串口終端軟件(minicom)需要選擇連接開發(fā)板的串口,配置串口參數(shù)StepThree安裝USB下載驅(qū)動可以使用DNW軟件與Supervivi配合,通過USB下載內(nèi)核與文件系統(tǒng)DNW是三星公司開發(fā)的串口小工具,在使用2440開發(fā)板進(jìn)行開發(fā)過程中,DNW可以實(shí)現(xiàn)上傳下載文件,燒寫文件,運(yùn)行映像等功能。也可以使用MiniTools軟件通過USB下載內(nèi)核與文件系統(tǒng)StepFour通過DNW與Supervivi提供的功能菜單配合完成下載文件對NandFlash進(jìn)行分區(qū)安裝bootloader安裝內(nèi)核文件安裝文件系統(tǒng)StepFour使用MiniTools軟件通過USB下載內(nèi)核與文件系統(tǒng)連接開發(fā)板選擇內(nèi)核與文件系統(tǒng)下載文件StepFive初始化QT圖形界面minicom仿真終端minicomWindows下的串口通信軟件軟件有前面介紹過的超級終端、串口調(diào)試助手、Putty、SecureCRT等。Linux下的串口通信軟件使用最廣泛的是minicom。

minicom是一個(gè)像Windows下的超級終端一樣的串口通信工具,可用來與串口設(shè)備通信,具有很強(qiáng)的功能。任務(wù)要求StepOne安裝minicomStepTwo虛擬機(jī)串口的設(shè)置

StepThree配置MinicomStepFour使用MinicomStepOne安裝minicom使用apt-get安裝minicom源碼包方式安裝apt-getinstallminicomtar–zxvfminicom-2.4.tar.gz./configuremakemakeinstallStepTwo虛擬機(jī)串口的設(shè)置關(guān)閉電源后,給虛擬機(jī)添加一個(gè)串口StepThree配置Minicom按上下光標(biāo)鍵進(jìn)行上下移動選擇,選中Serialportsetup對串行端口進(jìn)行設(shè)置minicom-sminicom–s+-----[configuration]------+|Filenamesandpaths||Filetransferprotocols||Serialportsetup||Modemanddialing||Screenandkeyboard||Savesetupasdfl||Savesetupas..||Exit||ExitfromMinicom|+--------------------------++-----------------------------------------------------------------------+|A-SerialDevice:/dev/ttyS1||B-LockfileLocation:/var/lock||C-CallinProgram:||D-CalloutProgram:||E-Bps/Par/Bits:1152008N1||F-HardwareFlowControl:Yes||G-SoftwareFlowControl:No||||Changewhichsetting?|+-----------------------------------------------------------------------+

StepFour“D”鍵:撥號目錄“S”鍵:發(fā)送文件,上傳文件有幾種方式:zmodem、ymodem、xmodem、kermit、ascii“P”鍵:通信參數(shù)。對波特率進(jìn)行設(shè)置。“L”鍵:捕捉開關(guān)。“F”鍵:發(fā)送中斷?!癟”鍵:終端設(shè)置?!癢”鍵:換行開關(guān)“G”鍵:運(yùn)行腳本“R”鍵:接收文件“A”鍵:添加一個(gè)換行符“H”鍵:掛斷“M”鍵:初始化調(diào)制解調(diào)器“K”鍵:運(yùn)行kermit進(jìn)行刷屏“E”鍵:切換本地回顯開關(guān)“C”鍵:清除屏幕“O”鍵:配置minicom“J”鍵:暫停minicom“X”鍵:退出和復(fù)位“Q”鍵:退出沒有復(fù)位“I”鍵:光標(biāo)模式“Z”鍵:幫助屏幕“B”鍵:滾動返回配置嵌入式開發(fā)環(huán)境交叉編譯環(huán)境交叉開發(fā)環(huán)境是指實(shí)現(xiàn)編譯、鏈接和調(diào)試應(yīng)用程序代碼的環(huán)境。

宿主機(jī)(host)目標(biāo)機(jī)(target)交叉編譯硬件環(huán)境文件傳輸方式串口傳輸方式網(wǎng)絡(luò)傳輸方式USB接口傳輸方式移動存儲設(shè)備網(wǎng)絡(luò)文件系統(tǒng)交叉編譯工具.uk/安裝交叉編譯器解壓tarzxvfarm-linux-gcc-4.4.3.tar.gz-C/exportPATH=$PATH:/opt/FriendlyARM/toolschain/4.4.3/bin編輯root目錄下的.bashrc文件配置環(huán)境變量交叉編譯物聯(lián)網(wǎng)工程學(xué)院平震宇STEPONE什么是交叉編譯STEPONE編輯和編譯程序的平臺,一般是基于x86體系結(jié)構(gòu)的PC機(jī),通常也被稱為主機(jī)。宿主機(jī)(host)目標(biāo)機(jī)(target)用戶開發(fā)的系統(tǒng),通常都是非X86平臺。host編譯得到的可執(zhí)行代碼在target上運(yùn)行。STEPONE就是在一個(gè)平臺上生成另一個(gè)平臺上的可執(zhí)行代碼。交叉編譯STEPTWO如何交叉編譯STEPTWO宿主機(jī)(host)目標(biāo)機(jī)(target)[root@localhost~]#gcc-v使用內(nèi)建specs。COLLECT_GCC=gccCOLLECT_LTO_WRAPPER=/usr/lib/gcc/i686-linux-gnu/4.6/lto-wrapper目標(biāo):i686-linux-gnugcc版本4.6.3(Ubuntu/Linaro4.6.3-1ubuntu5)[root@localhost~]#arm-linux-gcc-vUsingbuilt-inspecs.Target:arm-none-linux-gnueabigccversion4.3.2(SourceryG++Lite2008q3-72)謝謝配置嵌入式開發(fā)環(huán)境交叉編譯環(huán)境交叉開發(fā)環(huán)境是指實(shí)現(xiàn)編譯、鏈接和調(diào)試應(yīng)用程序代碼的環(huán)境。

宿主機(jī)(host)目標(biāo)機(jī)(target)交叉編譯硬件環(huán)境文件傳輸方式串口傳輸方式網(wǎng)絡(luò)傳輸方式USB接口傳輸方式移動存儲設(shè)備網(wǎng)絡(luò)文件系統(tǒng)交叉編譯工具.uk/安裝交叉編譯器解壓tarzxvfarm-linux-gcc-4.4.3.tar.gz-C/exportPATH=$PATH:/opt/FriendlyARM/toolschain/4.4.3/bin編輯root目錄下的.bashrc文件配置環(huán)境變量配置ARM虛擬機(jī)任務(wù)要求StepOne下載安裝qemuformini2440StepTwo下載u-bootformini2440StepThree下載

linuxkernelformini2440StepFour修改啟動文件mini2440_start.shStepFive修改網(wǎng)絡(luò)配置腳本StepSix掛載nfs文件系統(tǒng)StepOne下載qemuformini2440gitclonegit://repo.or.cz/qemu/mini2440.gitqemu./configure--target-list=arm-softmmu--prefix=/opt/mini2440編譯

make-j4StepTwo下載u-bootformini2440makemini2440_config編譯make-j4gitclonegit://repo.or.cz/u-boot-openmoko/mini2440.gitu-bootStepThree下載u-bootformini2440makemini2440_defconfigARCH=arm編譯makeARCH=armmenuconfiggitclonegit://repo.or.cz/linux-2.6/mini2440.gitkernelmakeARCH=armCROSS_COMPILE=arm-linux-uImagesetbootargsnoinitrdroot=/dev/nfsrwnfsroot=:/opt/root_qtopiaip=0:::console=ttySAC0,115200mini2440=1tbStepFour修改啟動文件mini2440_start.shStepFive修改網(wǎng)絡(luò)配置腳本管理Glibc庫文件GlibcGlibc(GNUCLibrary)是GNU發(fā)布的C語言標(biāo)準(zhǔn)庫,即C語言運(yùn)行庫。Glibc是GNU工具鏈的關(guān)鍵組件用Glibc

做為系統(tǒng)的C語言運(yùn)行庫,是Linux演進(jìn)的一個(gè)重要里程碑

Glibc主要包含以下內(nèi)容動態(tài)庫與靜態(tài)庫函數(shù)庫頭文件函數(shù)庫說明文件字集轉(zhuǎn)換模組與區(qū)域化資料庫時(shí)區(qū)資料庫Glibc主要包含以下內(nèi)容動態(tài)庫與靜態(tài)庫 /lib與/usr/lib函數(shù)庫頭文件

/usr/include函數(shù)庫說明文件

/usr/man

/usr/share/manGlibc主要包含以下內(nèi)容字集轉(zhuǎn)換模組與區(qū)域化資料庫/usr/lib/gconv/內(nèi)含大量的字集轉(zhuǎn)換模塊,各種字集及編碼方式與系統(tǒng)的基底字集之間的轉(zhuǎn)換

/usr/lib/locale,內(nèi)含以系統(tǒng)基底字集寫成的區(qū)域化資料庫(locale)

/usr/share/locale/,內(nèi)含可跨平臺使用的區(qū)域化資料,主要是各應(yīng)用程式的信息翻譯部分/usr/share/i18n/,其內(nèi)容是各區(qū)域化資料庫的原始碼,以及系統(tǒng)支援的內(nèi)碼對應(yīng)表等時(shí)區(qū)資料庫

/usr/share/zoneinfo目錄下包含世界各地時(shí)區(qū)與格林威治時(shí)間的轉(zhuǎn)換資料GlibcGlibc是Linux平臺C程序運(yùn)行的基礎(chǔ),提供一組頭文件和一組庫文件,最基本、最常用的C標(biāo)準(zhǔn)庫函數(shù)和系統(tǒng)函數(shù)在libc.so庫文件中。數(shù)學(xué)計(jì)算的C程序

libm.so多線程的C程序

libpthread.so

GlibcGlibc的庫有靜態(tài)庫和動態(tài)庫兩個(gè)版本,都位于/lib和/usr/lib目錄中,靜態(tài)庫的文件以.a為后綴名,動態(tài)庫以.so為后綴名。

lddldd命令用于判斷一個(gè)程序必須使用的動態(tài)庫。參數(shù)說明:

--version打印ldd的版本號

-v--verbose打印所有信息,例如包括符號的版本信息

-d--data-relocs執(zhí)行符號重部署,并報(bào)告缺少的目標(biāo)對象(只對ELF格式適用)

-r--function-relocs對目標(biāo)對象和函數(shù)執(zhí)行重新部署,并報(bào)告缺少的目標(biāo)對象和函數(shù)(只對ELF格式適用)

ldconfigldconfig是一個(gè)動態(tài)鏈接庫管理命令,其目的為了讓動態(tài)鏈接庫為系統(tǒng)所共享。ldconfig的主要用途:默認(rèn)搜尋/lilb和/usr/lib,以及配置文件/etc/ld.so.conf內(nèi)所列的目錄下的庫文件。搜索出可共享的動態(tài)鏈接庫,庫文件的格式為:lib***.so.**,進(jìn)而創(chuàng)建出動態(tài)裝入程序(ld.so)所需的連接和緩存文件。緩存文件默認(rèn)為/etc/ld.so.cache,該文件保存已排好序的動態(tài)鏈接庫名字列表。ldconfig通常在系統(tǒng)啟動時(shí)運(yùn)行,而當(dāng)用戶安裝了一個(gè)新的動態(tài)鏈接庫時(shí),就需要手工運(yùn)行這個(gè)命令。

GCC編譯器動態(tài)庫的搜索路徑搜索的先后順序

編譯目標(biāo)代碼時(shí)指定的動態(tài)庫搜索路徑;環(huán)境變量

LD_LIBRARY_PATH

指定的動態(tài)庫搜索路徑;配置文件

/etc/ld.so.conf

中指定的動態(tài)庫搜索路徑;默認(rèn)的動態(tài)庫搜索路徑

/lib

;默認(rèn)的動態(tài)庫搜索路徑

/usr/lib

文件I/O編程文件描述符文件描述符是一個(gè)非負(fù)的整數(shù),它是一個(gè)索引值,并指向在內(nèi)核中每個(gè)進(jìn)程打開文件的記錄表。當(dāng)打開一個(gè)現(xiàn)存文件或創(chuàng)建一個(gè)新文件時(shí),內(nèi)核就向進(jìn)程返回一個(gè)文件描述符;當(dāng)需要讀寫文件時(shí),也需要把文件描述符作為參數(shù)傳遞給相應(yīng)的函數(shù)。打開文件Flag標(biāo)記O_RDONLY就表示以只讀方式打開O_WRONLY表示以只寫方式打開O_RDWR表示以可讀可寫方式打開當(dāng)打開已經(jīng)存在并且內(nèi)部有內(nèi)容的文件時(shí)O_APPEND標(biāo)志:以添加方式打開文件,在打開文件的同時(shí),文件指針指向文件的末尾,即將寫入的數(shù)據(jù)添加到文件的末尾O_TRUNC標(biāo)志:若文件已經(jīng)存在,那么會刪除文件中的全部原有數(shù)據(jù),并且設(shè)置文件大小為0文件讀寫控制文件讀寫位置lseek參數(shù)fd:已經(jīng)打開的文件描述符。offset:偏移量,每一讀寫操作所需要移動的距離,單位是字節(jié),可正可負(fù)(向前移,向后移)。whence:當(dāng)前位置的基點(diǎn)。SEEK_SET:當(dāng)前位置為文件的開頭,新位置為偏移量的大小SEEK_CUR:當(dāng)前位置為文件指針的位置,新位置為當(dāng)前位置加上偏移量SEEK_END:當(dāng)前位置為文件的結(jié)尾,新位置為文件的大小lseeklseek文件開始文件結(jié)束fcntl函數(shù)fcntl參數(shù)fd:已經(jīng)打開的文件描述符。cmd

:不同的命令struct

flock

*lock:設(shè)置記錄鎖的具體狀態(tài)

fcntl參數(shù)F_DUPFD與dup函數(shù)功能一樣,復(fù)制由fd指向的文件描述符,調(diào)用成功后返回新的文件描述符,與舊的文件描述符共同指向同一個(gè)文件。F_GETFD讀取文件描述符close-on-exec標(biāo)志F_SETFD將文件描述符close-on-exec標(biāo)志設(shè)置為第三個(gè)參數(shù)arg的最后一位F_GETFL獲取文件打開方式的標(biāo)志,標(biāo)志值含義與open調(diào)用一致F_SETF設(shè)置文件打開方式為arg指定方式fcntl參數(shù)F_SETLK此時(shí)fcntl函數(shù)用來設(shè)置或釋放鎖。當(dāng)short_l_type為F_RDLCK為讀鎖,F(xiàn)_WDLCK為寫鎖,F(xiàn)_UNLCK為解鎖。如果鎖被其他進(jìn)程占用,則返回-1;這種情況設(shè)的鎖遇到鎖被其他進(jìn)程占用時(shí),會立刻停止進(jìn)程。F_SETLKW此時(shí)也是給文件上鎖,不同于F_SETLK的是,該上鎖是阻塞方式。當(dāng)希望設(shè)置的鎖因?yàn)槠渌i而被阻止設(shè)置時(shí),該命令會等待相沖突的鎖被釋放。F_GETLK第3個(gè)參數(shù)lock指向一個(gè)希望設(shè)置的鎖的屬性結(jié)構(gòu),如果鎖能被設(shè)置,該命令并不真的設(shè)置鎖,而是只修改lock的l_type為F_UNLCK,然后返回該結(jié)構(gòu)體。如果存在一個(gè)或多個(gè)鎖與希望設(shè)置的鎖相互沖突,則fcntl返回其中的一個(gè)鎖的flock結(jié)構(gòu)。structflock標(biāo)準(zhǔn)I/O編程文件I/O與標(biāo)準(zhǔn)I/O文件I/O:文件I/O稱之為不帶緩存的IO(unbufferedI/O)。標(biāo)準(zhǔn)I/O:基于流緩沖的,提供了三種類型的緩存。全緩存:當(dāng)填滿標(biāo)準(zhǔn)I/O緩存后才進(jìn)行實(shí)際的I/O操作。

行緩存:當(dāng)輸入或輸出中遇到新行符時(shí),標(biāo)準(zhǔn)I/O庫執(zhí)行I/O操作。

不帶緩存:標(biāo)準(zhǔn)出錯stderr。文件I/O與標(biāo)準(zhǔn)I/O

標(biāo)準(zhǔn)I/O文件I/O打開fopen,freopen,fdopenopen關(guān)閉fcloseclose讀getc,fgetc,getchar

fgets,gets

freadread寫putc,fputc,putchar

fputs,puts,

fwritewrite打開文件Mode取值標(biāo)志名說

明r或rb打開只讀文件,該文件必須存在r+或r+b打開可讀寫的文件,該文件必須存在W或wb打開只寫文件。若文件不存在則建立該文件w+或w+b打開可讀寫文件。若文件不存在則建立該文件a或ab以附加的方式打開只寫文件。a+或a+b以附加方式打開可讀寫的文件。文件讀寫文件狀態(tài)structstat網(wǎng)絡(luò)通訊編程TCP/IP協(xié)議模型TCP/IP協(xié)議模型TCP/IP協(xié)議模型Socket套接字

socket起源于Unix,而Unix/Linux基本哲學(xué)之一就是“一切皆文件”,都可以用“打開open–>讀寫write/read–>關(guān)閉close”模式來操作。socket就是該模式的一個(gè)實(shí)現(xiàn),socket即是一種特殊的文件,一些socket函數(shù)就是對其進(jìn)行的操作(讀/寫IO、打開、關(guān)閉).Socket套接字

流式套接字socket(SOCK_STREAM)數(shù)據(jù)報(bào)套接字socket(SOCK_DGRAM)原始套接字socket客戶/服務(wù)模式socket()建立一個(gè)socket連接bind()用于將本地IP地址綁定到端口號sockaddr獲取本地IP地址listen()讓Socket偵聽傳入的連接嘗試,并指定偵聽隊(duì)列容量accept()接收連接并返回一個(gè)新的socketconnect()初始化與另一個(gè)Socket的連接send()和recv()發(fā)送和接收數(shù)據(jù)網(wǎng)絡(luò)編程實(shí)例當(dāng)用戶從客戶端輸入“HelloServer”傳送到服務(wù)器端,服務(wù)器端發(fā)送“Hello,Client”到客戶端;如果從客戶端輸入“HelloABC”,傳送到服務(wù)器端,服務(wù)器端發(fā)送“Helloabc”到客戶端;如果從客戶端輸入“exit”,傳送到服務(wù)器端,服務(wù)器端程序退出,不向客戶端送回任何信息。網(wǎng)絡(luò)編程實(shí)例串口通訊編程并行通信與串行通信并行通信:是指利用多條數(shù)據(jù)傳輸線將數(shù)據(jù)的各位同時(shí)傳送優(yōu)點(diǎn):傳輸速度快缺點(diǎn):數(shù)據(jù)有多少位就需要多少根傳輸線,所以在位數(shù)多、傳輸距離遠(yuǎn)時(shí),通信線路復(fù)雜,成本高。串行通信:是指利用一條傳輸線將數(shù)據(jù)一位位地順序傳送。優(yōu)點(diǎn):這種通信方式的數(shù)據(jù)傳輸只需一、兩根傳輸線,通信線路簡單,成本低,特別適用于遠(yuǎn)程通信缺點(diǎn):傳輸速度較慢。多用于傳輸距離長、低速度的場合。串口簡介

RS-232-C:也稱標(biāo)準(zhǔn)串口,是目前最常用的一種串行通訊接口RS-422:為改進(jìn)RS-232通信距離短、速率低的缺點(diǎn)RS-485:為擴(kuò)展應(yīng)用范圍,EIA又于1983年在RS-422基礎(chǔ)上制定了RS-485標(biāo)準(zhǔn),增加了多點(diǎn)、雙向通信能力USB:通用串行總線,用于規(guī)范電腦與外部設(shè)備的連接和通訊。是應(yīng)用在PC領(lǐng)域的接口技術(shù)。RJ-45:RJ-45接口,適用于由雙絞線構(gòu)建的網(wǎng)絡(luò),以太網(wǎng)集線器都會提供這種端口串行接口簡稱串口,也稱串行通信接口(通常指COM接口),是采用串行通信方式的擴(kuò)展接口。9芯D型插座(DB9)針腳名稱全名3TDTransmitData2RDReceiveData7RTSRequestToSend8CTSClearToSend6DSRDataSetReady4DTRDataTerminalReady1CDDataCarrierDetect9RIRingIndicator5-SignalGround串口文件在linux中,針對所有的周邊設(shè)備都提供了設(shè)備文件供用戶訪問,所以如果要訪問串口,只要打開相關(guān)的設(shè)備文件即可。在Linux下串口文件是位于/dev下的COM1串口一為/dev/ttyS0COM2串口二為/dev/ttyS1串口設(shè)置在使用串口之前必須設(shè)置相關(guān)配置,包括:波特率、數(shù)據(jù)位、校驗(yàn)位、停止位等c_cflag常量名稱

設(shè)置波特率設(shè)置數(shù)據(jù)位設(shè)置奇偶校驗(yàn)位設(shè)置停止位

激活配置

打開串口fd=open("/dev/ttyUSB0",O_RDWR|O_NOCTTY|O_NDELAY);if(fd<0){

perror("openserialport");

return(-1);}打開串口讀寫串口fd=open("/dev/ttyUSB0",O_RDWR|O_NOCTTY|O_NDELAY);if(fd<0){

perror("openserialport");

return(-1);}3認(rèn)識Bootloader3BootLoaderBoot+LoadBoot,啟動(上電)Load,加載(系統(tǒng))系統(tǒng)加電后運(yùn)行的第一段軟件代碼。擔(dān)負(fù)著初始化硬件和引導(dǎo)操作系統(tǒng)的雙重責(zé)任。

3BootLoader功能初始化硬件設(shè)備建立內(nèi)存空間的映射圖調(diào)整系統(tǒng)的軟硬件環(huán)境,以便操作系統(tǒng)內(nèi)核啟動不通用依賴于硬件CPU依賴于主板board不同的CPU有不同的BootLoader

3Linux系統(tǒng)的啟動過程BootLoader運(yùn)行階段Linux初始化階段系統(tǒng)的正常運(yùn)行階段

3BootLoader支持的體系結(jié)構(gòu)名稱功能說明體系結(jié)構(gòu)LILOLINUX的磁盤引導(dǎo)加載程序x86GRUBLILO的GRU版x86Loadlin從Dos引導(dǎo)Linux系統(tǒng)x86U-BOOT通用引導(dǎo)加載程序x86,ARM,PowerPC,MIPS等RedBoot以eCos為基礎(chǔ)的引導(dǎo)程序x86,ARM,PowerPC,MIPS,M68KVIVI為S3C24XX處理器引導(dǎo)LinuxARMROLO可替代BIOS,能從ROM引導(dǎo)Linuxx86Etherboot從以太網(wǎng)卡啟動Linux系統(tǒng)的固件x86LinuxBIOS以Linux為基礎(chǔ)的BIOS替代品x86BLOB來自LART計(jì)劃的引導(dǎo)程序ARM3BootLoader的安裝系統(tǒng)加電或復(fù)位后,所有的CPU通常都從某個(gè)由CPU制造商預(yù)先安排的地址上取指令。比如,基于ARM7TDMI的CPU在復(fù)位時(shí)通常都從地址0x00000000取它的第一條指令?;贑PU構(gòu)建的嵌入式系統(tǒng)通常都有某種類型的固態(tài)存儲設(shè)備被映射到這個(gè)預(yù)先安排的地址上。比如:ROM、EEPROM或FLASH等。因此在系統(tǒng)加電后,CPU將首先執(zhí)行Bootloader程序。

3用來控制BootLoader的設(shè)備或機(jī)制主機(jī)和目標(biāo)機(jī)之間一般通過串口建立連接BootLoader軟件在執(zhí)行時(shí)通常會通過串口來進(jìn)行I/O,比如輸出打印信息到串口從串口讀取用戶控制字符等。最常用的串口通信軟件Linux:minicomWindows:附件中的超級終端

3BootLoader的啟動過程BootLoader的啟動過程可以是單階段(SingleStage)一些只需完成很簡單功能的bootloader可能是單階段的多階段(Multi-Stage)通常多階段的BootLoader能提供更為復(fù)雜的功能,以及更好的可移植性從固態(tài)存儲設(shè)備上啟動的BootLoader大多都是2階段的啟動過程,也即啟動過程可以分為stage1和stage2兩部分3BootLoader的操作模式大多數(shù)BootLoader包含兩種不同的操作模式啟動加載(Bootloading)模式下載(Downloading)模式這種區(qū)別僅對于開發(fā)人員才有意義,從最終用戶的角度看,BootLoader的作用就是加載操作系統(tǒng),并不存在上述兩種模式的區(qū)別3啟動加載模式也稱為自主(Autonomous)模式BootLoader從目標(biāo)機(jī)上的某個(gè)固態(tài)存儲設(shè)備上將操作系統(tǒng)加載到RAM中運(yùn)行,整個(gè)過程并沒有用戶的介入。這種模式是Boo

溫馨提示

  • 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)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

最新文檔

評論

0/150

提交評論