Linux環境開發工具(2)gdb除錯工具+Makefile自動化構建工具
- Linux編譯器-gcc/g++使用
- 程式編譯程序
- 重要概念:函式庫
- 靜態庫與動態庫
- gcc選項
- gdb使用
- 具體命令
- Makefile 工具
- 使用程序
- 專案清理
- 關于專案清理
- Linux小程式---理解緩沖區概念
- 注意點
- git命令的使用
Linux編譯器-gcc/g++使用
程式編譯程序
- 預處理(進行宏替換)
- 編譯(生成匯編)
- 匯編(生成機器可識別代碼)
- 連接(生成可執行檔案或庫檔案)
以hello.c 為例
gcc -E hello.c -o hello.i #預處理后停止編譯程序
gcc -S hello.i -o hello.s #編譯后(生成匯編代碼)停止編譯程序
gcc -c hello.s -o hello.o #匯編后(生成二進制代碼)停止編譯程序
gcc hello.o -o hello #進行鏈接最終生成可執行檔案
重要概念:函式庫
如函式printf,我們可以直接呼叫,我們或許認為<stdio.h>是原因的,但頭檔案里我們發現,printf只有宣告,那函式實作去哪兒了?

原因::系統把這些函式實作都被做到名為 libc.so.6 的庫檔案中去了,在沒有特別指定時,gcc 會到系統默認的搜索路徑“/usr/lib”下進行查找,也就是鏈接到 libc.so.6 庫函式中去,這樣就能實作函式“printf”了,而這也就是鏈接的作用
靜態庫與動態庫
·靜態庫是指編譯鏈接時,把庫檔案的代碼全部加入到可執行檔案中,因此生成的檔案比較大,但在運行時也就不再需要庫檔案了,其后綴名一般為“.a”
·動態庫與之相反,在編譯鏈接時并沒有把庫檔案的代碼加入到可執行檔案中,而是在程式執行時由運行時鏈接檔案加載庫,這樣可以節省系統的開銷,動態庫一般后綴名為“.so”,如前面所述的 libc.so.6 就是動態庫,gcc 在編譯時默認使用動態庫,完成了鏈接之后,gcc 就可以生成可執行檔案,如下所示, gcc hello.o –o hello
·gcc默認生成的二進制程式,是動態鏈接的,這點可以通過 file 命令驗證,
動態庫VS靜態庫 優缺點比較

gcc選項
-E 只激活預處理,這個不生成檔案,你需要把它重定向到一個輸出檔案里面
-shared 此選項將盡量使用動態庫,所以生成檔案比較小,但是需要系統由動態庫.
-O0
-O1
-O2
-O3 編譯器的優化選項的4個級別,-O0表示沒有優化,-O1為預設值,-O3優化級別最高
-w 不生成任何警告資訊,
-Wall 生成所有警告資訊,
-S 編譯到匯編語言不進行匯編和鏈接
-c 編譯到目標代碼
-o 檔案輸出到 檔案
-static 此選項對生成的檔案采用靜態鏈接
-g 生成除錯資訊,GNU 除錯器可利用該資訊,
gdb使用
注意點,正常編譯即gcc xxx.c -o xxx得到的是release版本的檔案,所以不能進行除錯,必須在編譯時加上-g得到debug版本的檔案,
具體命令
list/l 行號:顯示binFile源代碼,接著上次的位置往下列,每次列10行,
list/l 函式名:列出某個函式的源代碼,
r或run:運行程式,
n 或 next:單條執行,
s或step:進入函式呼叫
break(b) 行號:在某一行設定斷點
break 函式名:在某個函式開頭設定斷點
info break :查看斷點資訊,
finish:執行到當前函式回傳,然后挺下來等待命令
print( p):列印運算式的值,通過運算式可以修改變數的值或者呼叫函式
p 變數:列印變數值,
set var:修改變數的值
continue(或c):從當前位置開始連續而非單步執行程式
run(或r):從開始連續而非單步執行程式
delete breakpoints:洗掉所有斷點
delete breakpoints n:洗掉序號為n的斷點
disable breakpoints:禁用斷點
enable breakpoints:啟用斷點
info(或i) breakpoints:參看當前設定了哪些斷點
display 變數名:跟蹤查看一個變數,每次停下來都顯示它的值
undisplay:取消對先前設定的那些變數的跟蹤
until X行號:跳至X行
breaktrace(或bt):查看各級函式呼叫及引數
info(i) locals:查看當前堆疊幀區域變數的值
quit:退出gdb
Makefile 工具
使用程序
- 創建Makefile檔案(檔案名不可更改)
- 寫入內容:依賴關系和依賴方法(本質和在teminal里輸入命令列一樣,可以將Makefile理解成打包執行)
hello:hello.o #依賴關系
gcc hello.o -o hello #依賴方法
hello.o:hello.s
gcc -c hello.s -o hello.o
hello.s:hello.i
gcc -S hello.i -o hello.s
hello.i:hello.c
gcc -E hello.c -o hello.i
#注意這邊一定是一個tab建不可以用空格替代
- wq保存退出,在terminal里執行make命令,就會生成對應的可執行檔案Make
- ./Mytest 就可以看到結果
專案清理
.PHONY:clean
clean:
rm -f hello.i hello.s hello.o hello
在terminal里執行make clean 命令就可以起到清理作用
關于專案清理
·像clean這種,沒有被第一個目標檔案直接或間接關聯,那么它后面所定義的命令將不會被自動執行,
·不過,我們可以顯示要make執行,即命令——“make clean”,以此來清除所有的目標檔案,以便重編譯,
·但是一般我們這種clean的目標檔案,我們將它設定為偽目標,用 .PHONY 修飾,偽目標的特性是,總是被執行的,
·可以將我們的 hello 目標檔案宣告成偽目標,測驗一下,
Linux小程式—理解緩沖區概念
void count(){
int i=10;
while(i){
printf("%2d\r",i);
fflush(stdout);
i--;
sleep(1);
}
}
void ProcBar(){
int i=0;
char proc[102];
char *run="|/-\\";
memset(proc,'\0',sizeof(proc));
while(i<=100){
printf("\033[44;37;31m [%-100s] [%d%%][%c]\033[40m\r",proc,i,run[i%4]);
fflush(stdout);
proc[i]='#';
usleep(30000);
i++;
}
printf("\n");
}
實作效果

注意點
printf("a");
sleep(1);
在程式中實作這個我們會發現,系統會先休眠一秒再輸出
printf("a\n");
sleep(1);
而這個程式則會先輸出再休眠
我們需要理解緩沖區的概念:
分為:行緩沖即緩沖區打滿一行才輸出到顯示幕
全緩沖即打滿緩沖區才輸出到顯示幕
無緩沖即輸入即輸出
由此可知,上文為行緩沖,
由此便可實作小程式
git命令的使用
git clone (網址) #在本地克隆庫
cp xx xx #將檔案考入本地庫
git add xx #將代碼放到剛才下載好的目錄中
git commit xx -"..." #備注日志,需要寫清楚
git push ##同步到云端庫
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/292323.html
標籤:其他
