自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

GDB 的 七個(gè)單步調(diào)試命令

系統(tǒng) Linux
即使是復(fù)雜的函數(shù),也有幾種方法可以單步調(diào)試,所以下次在排除代碼故障時(shí),可以嘗試一下這些 GDB 技術(shù)。

調(diào)試器 是一個(gè)可以運(yùn)行你的代碼并檢查問(wèn)題的軟件。??GNU Debugger???(GBD)是最流行的調(diào)試器之一,在這篇文章中,我研究了 GDB 的 ??step??? 命令和其他幾種常見情況的相關(guān)命令。??step?? 是一個(gè)被廣泛使用的命令,但它有一些人們不太了解的地方,可能會(huì)使得他們十分困惑。此外,還有一些方法可以在不使用 ??step??? 命令的情況下進(jìn)入一個(gè)函數(shù),比如使用不太知名的 ??advance?? 命令。

1、無(wú)調(diào)試符號(hào)

考慮以下這個(gè)簡(jiǎn)單的示例程序:

#include <stdio.h>int num() {    return 2;}void bar(int i) {    printf("i = %d\n", i);}int main() {    bar(num());    return 0;}

如果你在沒有 調(diào)試符號(hào)debugging sysbols 的情況下進(jìn)行編譯(LCTT 譯注:即在使用 ??gcc?? 編譯程序時(shí)沒有寫 ??-g?? 選項(xiàng)),然后在 ??bar?? 上設(shè)置一個(gè)斷點(diǎn),然后嘗試在這個(gè)函數(shù)內(nèi)使用 ??step?? 來(lái)單步執(zhí)行語(yǔ)句。GDB 會(huì)給出一個(gè) 沒有行號(hào)信息no line number information

gcc exmp.c -o exmpgdb ./exmp(gdb) b barBreakpoint 1 at 0x401135(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, 0x0000000000401135 in bar ()(gdb) stepSingle stepping until exit from function bar,which has no line number information.i = 20x0000000000401168 in main ()

2、stepi 命令

但是你仍然可以在沒有行號(hào)信息的函數(shù)內(nèi)部單步執(zhí)行語(yǔ)句,但要使用 ??stepi?? 命令來(lái)代替 ??step??。??stepi?? 一次只執(zhí)行一條指令。當(dāng)使用 GDB 的 ??stepi?? 命令時(shí),先做 ??display/i $pc?? 通常很有用,這會(huì)在每一步之后顯示 程序計(jì)數(shù)器program counter 的值和相應(yīng)的 機(jī)器指令machine instruction:

(gdb) b barBreakpoint 1 at 0x401135(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, 0x0000000000401135 in bar ()(gdb) display/i $pc1: x/i $pc=> 0x401135 <bar+4>: sub $0x10,%rsp

在上述的 ??display?? 命令中,??i?? 代表機(jī)器指令,??$pc?? 表示程序計(jì)數(shù)器寄存器(即 PC 寄存器)。

使用 ??info registers?? 命令,來(lái)打印寄存器的內(nèi)容,也是十分有用的。

(gdb) info registersrax 0x2 2rbx 0x7fffffffdbc8 140737488346056rcx 0x403e18 4210200(gdb) print $rax$1 = 2(gdb) stepi0x0000000000401139 in bar ()1: x/i $pc=> 0x401139 <bar+8>: mov %edi,-0x4(%rbp)

3、復(fù)雜的函數(shù)調(diào)用

在帶調(diào)試符號(hào)的 ??-g?? 選項(xiàng),重新編譯示例程序后,你可以使用行號(hào)在 ??main?? 中 ??bar?? 調(diào)用上設(shè)置斷點(diǎn),然后再單步執(zhí)行 ??bar?? 函數(shù)的語(yǔ)句:

gcc -g exmp.c -o exmpgdb ./exmp(gdb) b exmp.c:14Breakpoint 1 at 0x401157: file exmp.c, line 14.(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, main () at exmp.c:1414 bar(num());

接下來(lái),用 ??step??,來(lái)單步執(zhí)行 ??bar()?? 函數(shù)的語(yǔ)句:

(gdb) stepnum () at exmp.c:44 return 2;

函數(shù)調(diào)用的參數(shù)需要在實(shí)際的函數(shù)調(diào)用之前進(jìn)行處理,??bar()?? 函數(shù)的參數(shù)是 ??num()?? 函數(shù),所以 ??num()?? 會(huì)在 ??bar()?? 被調(diào)用之前執(zhí)行。但是,通過(guò) GDB 調(diào)試,你怎么才能如愿以償?shù)剡M(jìn)入 ??bar()?? 函數(shù)呢?你可以使用 ??finish?? 命令,并再次使用 ??step?? 命令。

(gdb) finishRun till exit from #0 num () at exmp.c:40x0000000000401161 in main () at exmp.c:1414 bar(num());Value returned is $1 = 2(gdb) stepbar (i=2) at exmp.c:99 printf("i = %d\n", i);

4、tbreak 命令

??tbreak?? 命令會(huì)設(shè)置一個(gè)臨時(shí)斷點(diǎn)。如果你不想設(shè)置永久斷點(diǎn),那么這個(gè)命令是很有用的。舉個(gè)例子??,你想進(jìn)入一個(gè)復(fù)雜的函數(shù)調(diào)用,例如 ??f(g(h()), i(j()), ...)??,在這種情況下,你需要一個(gè)很長(zhǎng)的 ??step/finish/step?? 序列,才能到達(dá) ??f?? 函數(shù)。如果你設(shè)置一個(gè)臨時(shí)斷點(diǎn),然后再使用 ??continue?? 命令,這樣就不需要以上的序列了。為了證明這一點(diǎn),你需要像以前一樣將斷點(diǎn)設(shè)置在 ??main?? 的 ??bar?? 調(diào)用上。然后在 ??bar?? 上設(shè)置臨時(shí)斷點(diǎn)。當(dāng)?shù)竭_(dá)該臨時(shí)斷點(diǎn)后,臨時(shí)斷點(diǎn)會(huì)被自動(dòng)刪除。

(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, main () at exmp.c:1414 bar(num());(gdb) tbreak barTemporary breakpoint 2 at 0x40113c: file exmp.c, line 9.

在調(diào)用 ??bar?? 的時(shí)候遇到斷點(diǎn),并在 ??bar?? 上設(shè)置臨時(shí)斷點(diǎn)后,你只需要使用 ??continue?? 繼續(xù)運(yùn)行直到 ??bar?? 結(jié)束。

(gdb) continueContinuing.Temporary breakpoint 2, bar (i=2) at exmp.c:99 printf("i = %d\n", i);

5、disable 命令

類似地,你也可以在 ??bar?? 上設(shè)置一個(gè)正常的斷點(diǎn),然后執(zhí)行 ??continue??,然后在不再需要第二個(gè)斷點(diǎn)時(shí),使用 ??disable?? 命令禁用這個(gè)斷點(diǎn),這樣也能達(dá)到與 ??tbreak?? 相同的效果。

(gdb) b exmp.c:14Breakpoint 1 at 0x401157: file exmp.c, line 14.(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, main () at exmp.c:1414 bar(num());(gdb) b barBreakpoint 2 at 0x40113c: file exmp.c, line 9.(gdb) cContinuing.Breakpoint 2, bar (i=2) at exmp.c:99 printf("i = %d\n", i);(gdb) disable 2

正如你所看到的,??info breakpoints?? 命令在 ??Enb?? 列下顯示為 ??n??,這意味著這個(gè)斷點(diǎn)已被禁用。但你也能在再次需要這個(gè)斷點(diǎn)時(shí),再啟用它。

(gdb) info breakpointsNum Type Disp Enb Address What1 breakpoint keep y 0x0000000000401157 in main at exmp.c:14breakpoint already hit 1 time2 breakpoint keep n 0x000000000040113c in bar at exmp.c:9breakpoint already hit 1 time(gdb) enable 2(gdb) info breakpointsNum Type Disp Enb Address What1 breakpoint keep y 0x000000000040116a in main at exmp.c:19breakpoint already hit 1 time2 breakpoint keep y 0x0000000000401158 in bar at exmp.c:14breakpoint already hit 1 time

6、advance 命令運(yùn)行程序到指定的位置

另一個(gè)進(jìn)入函數(shù)內(nèi)部的方法是 ??advance?? 命令。你可以簡(jiǎn)單地用 ??advance bar??,來(lái)代替 ??tbreak bar ; continue??。這一命令會(huì)將程序繼續(xù)運(yùn)行到指定的位置。

??advance?? 命令的一個(gè)很棒的地方在于:如果程序并沒有到達(dá)你試圖進(jìn)入的位置,那么 GDB 將在當(dāng)前函數(shù)運(yùn)行完成后停止。因此,程序的執(zhí)行會(huì)受到限制:

Breakpoint 1 at 0x401157: file exmp.c, line 14.(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, main () at exmp.c:1414 bar(num());(gdb) advance barbar (i=2) at exmp.c:99 printf("i = %d\n", i);

7、skip 命令

進(jìn)入 ??bar?? 函數(shù)的另一種方式是使用 ??skip num?? 命令:

(gdb) b exmp.c:14Breakpoint 1 at 0x401157: file exmp.c, line 14.(gdb) skip numFunction num will be skipped when stepping.(gdb) rStarting program: /home/ahajkova/exmpBreakpoint 1, main () at exmp.c:1414 bar(num());(gdb) stepbar (i=2) at exmp.c:99 printf("i = %d\n", i);

請(qǐng)使用 ??info skip?? 命令,來(lái)了解 GDB 跳過(guò)了哪些函數(shù)。??num()?? 函數(shù)被標(biāo)記為 ??y??,表示跳過(guò)了 ??num()?? 函數(shù):

(gdb) info skipNum Enb Glob File RE Function1 y n <none> n num

如果不再需要 ??skip??,可以禁用(并稍后重新啟用)或完全刪除它。你可以添加另一個(gè) ??skip??,并禁用第一個(gè) ??skip??,然后全部刪除。要禁用某個(gè) ??skip??,必須指定其編號(hào)(例如,??skip disable 1??),如果沒有指定,則會(huì)禁用所有的 ??skip??。啟用或刪除 ??skip?? 的工作原理相同:

(gdb) skip bar(gdb) skip disable 1(gdb) info skipNum Enb Glob File RE Function1 n n <none> n num2 y n <none> n bar(gdb) skip delete(gdb) info skipNot skipping any files or functions.

GDB 的 step 命令

使用 GDB 的 ??step?? 命令是調(diào)試程序的一個(gè)有用工具。即使是復(fù)雜的函數(shù),也有幾種方法可以單步調(diào)試這些函數(shù),所以下次你在排除代碼問(wèn)題的時(shí)候,可以嘗試一下這些 GDB 技術(shù)。

責(zé)任編輯:龐桂玉 來(lái)源: Linux中國(guó)
相關(guān)推薦

2010-11-10 15:47:59

2009-07-14 11:15:35

MyEclipse 單

2021-11-17 15:28:06

LinuxLinux命令

2023-11-06 18:06:00

Docker容器

2021-11-22 12:13:54

Linuxwget 命令

2019-07-11 15:26:50

數(shù)據(jù)中心技術(shù)數(shù)據(jù)網(wǎng)絡(luò)

2023-12-21 18:01:58

Docker容器部署

2023-11-03 18:01:59

Docker開源平臺(tái)

2010-03-04 15:00:12

Linux毀壞命令

2016-11-18 08:57:46

2009-02-03 08:23:35

Linux命令安全

2023-07-12 23:41:04

Linuxfind

2020-12-15 11:05:21

JavascriptChrome瀏覽器

2022-11-18 14:33:39

2011-03-02 09:34:58

AppFuse

2023-07-14 14:53:38

人工智能prompt

2018-05-17 13:59:28

IT顧問(wèn)

2022-09-21 11:47:15

CIO虛假敏捷

2024-11-06 14:26:40

2015-06-11 13:34:54

編程編程階段
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)