新聞中心

EEPW首頁(yè) > gcc and g++編譯器和gdb調(diào)試器

gcc and g++編譯器和gdb調(diào)試器

——
作者: 時(shí)間:2007-04-18 來(lái)源:電子產(chǎn)品世界 收藏
gcc and g++分別是gnu的c & c++

gcc/g++在執(zhí)行編譯工作的時(shí)候,總共需要4步

1.預(yù)處理,生成.i的文件[預(yù)處理器cpp]
2.將預(yù)處理后的文件不轉(zhuǎn)換成匯編語(yǔ)言,生成文件.s[egcs]
3.有匯編變?yōu)槟繕?biāo)代碼(機(jī)器代碼)生成.o的文件[匯編器as]
4.連接目標(biāo)代碼,生成可執(zhí)行程序[鏈接器ld]



[參數(shù)詳解]
-x language filename 
   設(shè)定文件所使用的語(yǔ)言,使后綴名無(wú)效,對(duì)以后的多個(gè)有效.也就是根
   據(jù)約定C語(yǔ)言的后綴名稱是.c的,而C++的后綴名是.C或者.cpp,如果
   你很個(gè)性,決定你的C代碼文件的后綴名是.pig 哈哈,那你就要用這
   個(gè)參數(shù),這個(gè)參數(shù)對(duì)他后面的文件名都起作用,除非到了下一個(gè)參數(shù)
   的使用。
   可以使用的參數(shù)嗎有下面的這些
     `c', `objective-c', `c-header', `c++', `cpp-output', 
     `assembler', and `assembler-with-cpp'.
   看到英文,應(yīng)該可以理解的。
   例子用法:
   gcc -x c hello.pig
  
-x none filename
  關(guān)掉上一個(gè)選項(xiàng),也就是讓gcc根據(jù)文件名后綴,自動(dòng)識(shí)別文件類型
  例子用法:
  gcc -x c hello.pig -x none hello2.c
  
-c 
  只激活預(yù)處理,編譯,和匯編,也就是他只把程序做成obj文件
  例子用法:
  gcc -c hello.c
  他將生成.o的obj文件 

-S
  只激活預(yù)處理和編譯,就是指把文件編譯成為匯編代碼。
  例子用法
  gcc -S hello.c
  他將生成.s的匯編代碼,你可以用文本察看

-E
  只激活預(yù)處理,這個(gè)不生成文件,你需要把它重定向到一個(gè)輸出文件里
  面.
  例子用法:
  gcc -E hello.c > pianoapan.txt
  gcc -E hello.c | more
  慢慢看吧,一個(gè)hello word 也要與處理成800行的代碼

-o
  制定目標(biāo)名稱,缺省的時(shí)候,gcc 編譯出來(lái)的文件是a.out,很難聽(tīng),如果
  你和我有同感,改掉它,哈哈
  例子用法
  gcc -o hello.exe hello.c (哦,windows用習(xí)慣了)
  gcc -o hello.asm -S hello.c

-pipe
  使用管道代替編譯中臨時(shí)文件,在使用非gnu匯編工具的時(shí)候,可能有些問(wèn)
  題
  gcc -pipe -o hello.exe hello.c

-ansi
  關(guān)閉gnu c中與ansi c不兼容的特性,激活ansi c的專有特性(包括禁止一
  些asm inline typeof關(guān)鍵字,以及UNIX,vax等預(yù)處理宏,

-fno-asm
  此選項(xiàng)實(shí)現(xiàn)ansi選項(xiàng)的功能的一部分,它禁止將asm,inline和typeof用作
  關(guān)鍵字。
    
-fno-strict-prototype
  只對(duì)g++起作用,使用這個(gè)選項(xiàng),g++將對(duì)不帶參數(shù)的函數(shù),都認(rèn)為是沒(méi)有顯式
  的對(duì)參數(shù)的個(gè)數(shù)和類型說(shuō)明,而不是沒(méi)有參數(shù).
  而gcc無(wú)論是否使用這個(gè)參數(shù),都將對(duì)沒(méi)有帶參數(shù)的函數(shù),認(rèn)為城沒(méi)有顯式說(shuō)
  明的類型
  
-fthis-is-varialble
  就是向傳統(tǒng)c++看齊,可以使用this當(dāng)一般變量使用.
  
-fcond-mismatch
  允許條件表達(dá)式的第二和第三參數(shù)類型不匹配,表達(dá)式的值將為void類型
  
-funsigned-char
-fno-signed-char
-fsigned-char
-fno-unsigned-char
  這四個(gè)參數(shù)是對(duì)char類型進(jìn)行設(shè)置,決定將char類型設(shè)置成unsigned char(前
  兩個(gè)參數(shù))或者 signed char(后兩個(gè)參數(shù))
  
-include file
  包含某個(gè)代碼,簡(jiǎn)單來(lái)說(shuō),就是便以某個(gè)文件,需要另一個(gè)文件的時(shí)候,就可以
  用它設(shè)定,功能就相當(dāng)于在代碼中使用#include<filename>
  例子用法:
  gcc hello.c -include /root/pianopan.h {{分頁(yè)}}
  
-imacros file
  將file文件的宏,擴(kuò)展到gcc/g++的輸入文件,宏定義本身并不出現(xiàn)在輸入文件
  中
  
-Dmacro
  相當(dāng)于C語(yǔ)言中的#define macro
  
-Dmacro=defn
  相當(dāng)于C語(yǔ)言中的#define macro=defn
  
-Umacro
  相當(dāng)于C語(yǔ)言中的#undef macro

-undef
  取消對(duì)任何非標(biāo)準(zhǔn)宏的定義
  
-Idir
  在你是用#include"file"的時(shí)候,gcc/g++會(huì)先在當(dāng)前目錄查找你所制定的頭
  文件,如果沒(méi)有找到,他回到缺省的頭文件目錄找,如果使用-I制定了目錄,他
  回先在你所制定的目錄查找,然后再按常規(guī)的順序去找.
  對(duì)于#include<file>,gcc/g++會(huì)到-I制定的目錄查找,查找不到,然后將到系
  統(tǒng)的缺省的頭文件目錄查找
  
-I-
  就是取消前一個(gè)參數(shù)的功能,所以一般在-Idir之后使用
  
-idirafter dir
  在-I的目錄里面查找失敗,講到這個(gè)目錄里面查找.
  
-iprefix prefix
-iwithprefix dir
  一般一起使用,當(dāng)-I的目錄查找失敗,會(huì)到prefix+dir下查找
  
-nostdinc
  使不再系統(tǒng)缺省的頭文件目錄里面找頭文件,一般和-I聯(lián)合使用,明確
  限定頭文件的位置
  
-nostdin C++
  規(guī)定不在g++指定的標(biāo)準(zhǔn)路經(jīng)中搜索,但仍在其他路徑中搜索,.此選項(xiàng)在創(chuàng)建
  libg++庫(kù)使用
  
-C
  在預(yù)處理的時(shí)候,不刪除注釋信息,一般和-E使用,有時(shí)候分析程序,用這個(gè)很
  方便的
  
-M
  生成文件關(guān)聯(lián)的信息。包含目標(biāo)文件所依賴的所有源代碼
  你可以用gcc -M hello.c來(lái)測(cè)試一下,很簡(jiǎn)單。
  
-MM
  和上面的那個(gè)一樣,但是它將忽略由#include<file>造成的依賴關(guān)系。
  
-MD
  和-M相同,但是輸出將導(dǎo)入到.d的文件里面
  
-MMD
  和-MM相同,但是輸出將導(dǎo)入到.d的文件里面
  
-Wa,option
  此選項(xiàng)傳遞option給匯編程序;如果option中間有逗號(hào),就將option分成多個(gè)選
  項(xiàng),然后傳遞給會(huì)匯編程序
  
-Wl.option
  此選項(xiàng)傳遞option給連接程序;如果option中間有逗號(hào),就將option分成多個(gè)選
  項(xiàng),然后傳遞給會(huì)連接程序.
  

-llibrary 
  制定編譯的時(shí)候使用的庫(kù)
  例子用法
  gcc -lcurses hello.c
  使用ncurses庫(kù)編譯程序
  
-Ldir
  制定編譯的時(shí)候,搜索庫(kù)的路徑。比如你自己的庫(kù),可以用它制定目錄,不然
  編譯器將只在標(biāo)準(zhǔn)庫(kù)的目錄找。這個(gè)dir就是目錄的名稱。
  
-O0
-O1
-O2
-O3
  編譯器的優(yōu)化選項(xiàng)的4個(gè)級(jí)別,-O0表示沒(méi)有優(yōu)化,-O1為缺省值,-O3優(yōu)化級(jí)別最
  高  
  
-g
  只是編譯器,在編譯的時(shí)候,產(chǎn)生條是信息。
  
-gstabs
  此選項(xiàng)以stabs格式聲稱調(diào)試信息,但是不包括gdb調(diào)試信息.
  
-gstabs+
  此選項(xiàng)以stabs格式聲稱調(diào)試信息,并且包含僅供gdb使用的額外調(diào)試信息.
  
-ggdb
  此選項(xiàng)將盡可能的生成gdb的可以使用的調(diào)試信息.
-static
  此選項(xiàng)將禁止使用動(dòng)態(tài)庫(kù),所以,編譯出來(lái)的東西,一般都很大,也不需要什么
動(dòng)態(tài)連接庫(kù),就可以運(yùn)行.
-share
  此選項(xiàng)將盡量使用動(dòng)態(tài)庫(kù),所以生成文件比較小,但是需要系統(tǒng)由動(dòng)態(tài)庫(kù).
-traditional
  試圖讓編譯器支持傳統(tǒng)的C語(yǔ)言特性


GNU 的調(diào)試器稱為 gdb,該程序是一個(gè)交互式工具,工作在字符模式。在 X Window 系統(tǒng)中,有一個(gè) gdb 的
前端圖形工具,稱為 xxgdb。gdb 是功能強(qiáng)大的調(diào)試程序,可完成如下的調(diào)試任務(wù):
* 設(shè)置斷點(diǎn);
* 監(jiān)視程序變量的值;
* 程序的單步執(zhí)行;
* 修改變量的值。 {{分頁(yè)}}
在可以使用 gdb 調(diào)試程序之前,必須使用 -g 選項(xiàng)編譯源文件??稍?nbsp;makefile 中如下定義 CFLAGS 變量:
CFLAGS = -g
運(yùn)行 gdb 調(diào)試程序時(shí)通常使用如下的命令:
gdb progname

在 gdb 提示符處鍵入help,將列出命令的分類,主要的分類有:
* aliases:命令別名
* breakpoints:斷點(diǎn)定義;
* data:數(shù)據(jù)查看;
* files:指定并查看文件;
* internals:維護(hù)命令;
* running:程序執(zhí)行;
* stack:調(diào)用棧查看;
* statu:狀態(tài)查看;
* tracepoints:跟蹤程序執(zhí)行。
鍵入 help 后跟命令的分類名,可獲得該類命令的詳細(xì)清單。


#DENO#
gdb 的常用命令
                表 1-4  常用的 gdb 命令
命令                        解釋
break NUM               在指定的行上設(shè)置斷點(diǎn)。
bt                      顯示所有的調(diào)用棧幀。該命令可用來(lái)顯示函數(shù)的調(diào)用順序。
clear                   刪除設(shè)置在特定源文件、特定行上的斷點(diǎn)。其用法為:clear FILENAME:NUM。
continue                繼續(xù)執(zhí)行正在調(diào)試的程序。該命令用在程序由于處理信號(hào)或斷點(diǎn)而
                        導(dǎo)致停止運(yùn)行時(shí)。
display EXPR            每次程序停止后顯示表達(dá)式的值。表達(dá)式由程序定義的變量組成。
file FILE               裝載指定的可執(zhí)行文件進(jìn)行調(diào)試。
help NAME               顯示指定命令的幫助信息。
info break              顯示當(dāng)前斷點(diǎn)清單,包括到達(dá)斷點(diǎn)處的次數(shù)等。
info files              顯示被調(diào)試文件的詳細(xì)信息。
info func               顯示所有的函數(shù)名稱。
info local              顯示當(dāng)函數(shù)中的局部變量信息。
info prog               顯示被調(diào)試程序的執(zhí)行狀態(tài)。
info var                顯示所有的全局和靜態(tài)變量名稱。
kill                    終止正被調(diào)試的程序。
list                    顯示源代碼段。
make                    在不退出 gdb 的情況下運(yùn)行 make 工具。
next                    在不單步執(zhí)行進(jìn)入其他函數(shù)的情況下,向前執(zhí)行一行源代碼。
print EXPR              顯示表達(dá)式 EXPR 的值。


1.8.5  gdb 使用范例
-----------------
清單  一個(gè)有錯(cuò)誤的 C 源程序 bugging.c
-----------------
#include 
#include 

static char buff [256];
static char* string;
int main ()
{

    printf ("Please input a string: ");
    gets (string);

    printf ("nYour string is: %sn", string);
}
-----------------
上面這個(gè)程序非常簡(jiǎn)單,其目的是接受用戶的輸入,然后將用戶的輸入打印出來(lái)。該程序使用了一個(gè)未經(jīng)過(guò)初
始化的字符串地址 string,因此,編譯并運(yùn)行之后,將出現(xiàn) Segment Fault 錯(cuò)誤:
$ gcc -o test -g test.c
$ ./test
Please input a string: asfd
Segmentation fault (core dumped)
為了查找該程序中出現(xiàn)的問(wèn)題,我們利用 gdb,并按如下的步驟進(jìn)行:
1.運(yùn)行 gdb bugging 命令,裝入 bugging 可執(zhí)行文件;
2.執(zhí)行裝入的 bugging 命令;
3.使用 where 命令查看程序出錯(cuò)的地方;
4.利用 list 命令查看調(diào)用 gets 函數(shù)附近的代碼;
5.唯一能夠?qū)е?nbsp;gets 函數(shù)出錯(cuò)的因素就是變量 string。用 print 命令查看 string 的值;
6.在 gdb 中,我們可以直接修改變量的值,只要將 string 取一個(gè)合法的指針值就可以了,為此,我們?cè)诘?
 11 行處設(shè)置斷點(diǎn);
7.程序重新運(yùn)行到第 11 行處停止,這時(shí),我們可以用 set variable 命令修改 string 的取值;
8.然后繼續(xù)運(yùn)行,將看到正確的程序運(yùn)行結(jié)果。



評(píng)論


相關(guān)推薦

技術(shù)專區(qū)

關(guān)閉