一、编译c:编译命令使用-g参数,向可执行程序中加入调试信息,包括源代码、符号表等,GDB 需要这些额外的信息来完成调试工作。
gcc test.c -o main.o -g
二、启动GDB:使用-silent参数,屏蔽 GDB 的前导信息(GDB免责条款)
gdb test.out -silent
Reading symbols from main.o...done.
(gdb)
三、设置断点:b(break)命令设置断点,
(gdb)b 函数名称,如:b main; 显示结果:
Breakpoint 1 at 0x10040108d: file main.c, line 4.
(gdb) b 行号,如:b 5;
(gdb) b * 内存地址,如:b * 0x10040108d
四、运行程序: r(run)命令运行程序
(gdb) r
Starting program: /home/gao/test/test1/main.o
[New Thread 9984.0x2144]
[New Thread 9984.0x2310]
[New Thread 9984.0xe50]
[New Thread 9984.0x2f30]
Thread 1 "main.o" hit Breakpoint 1, main () at main.c:4
4 n = 1;
在运行了被调试的程序后,GDB 的输出信息显示程序己经启动,下一个将要执行的语句是第 4 行的n = 1;
注意,这条语句并没有执行,而仅仅是告诉你,再继续执行程序的话,执行的语句会是它。
五、查看打印变量:p(print)命令打印变量值
(gdb) p n
$1 = 0
(gdb) p sum
$2 = 4294954103
GDB 先计算表达式的值,并把它保存在一个存储区中,存储区的名字用$
外加数字来表示,并且这个数字会随着调试过程的进行而不断递增(这意味着存储区也是不断开辟的)。以上,第一个 p 命令执行后,GDB 的回应是$1 = 0
,意思是表达式 n 的值保存在 $1 中,其内容为 0。
注意,在你的计算机上,变量 n 和 sum 的当前值可能和这里显示的不同。这很好理解,内存是反复使用的,当一个程序终止后,它占用的内存会分配给其他程序使用;当一个变量不再使用后,它占用的内存也会重新分配,并成为另一个变量。因为变量 n 和 sum 刚刚分配,还没有往里面保存任何数值,故它们的内容是随机的,是其他程序或者变量用过的垃圾值。
六、单步执行:n(next)命令运行到下一行
(gdb) n
5 sum = 0;
执行 n 命令后,实际执行的是第 4 行n = 1;,GDB 显示下一个即将执行的源代码行,也就是第 5 行的sum = 0;
(gdb) n
6 while (n <= 100)
继续执行n命令后,用p n;p sum监视n和sum的值,可见:
(gdb) p n
$3 = 1
(gdb) p sum
$4 = 0
也可以用p{n, sum}命令监视n和sum的值
(gdb) p{n, sum}
$5 = {1, 0}
七、列出原文件内容:l(list)命令
(gdb) l
4 n = 1;
5 sum = 0;
6 while (n <= 100)
7 {
8 sum = sum + n;
9 n = n + 1;
10 }
11 return 0;
12 }
l 命令默认每次显示 10 行源代码,如果没有显示下我们想要看的代码,可以继续运行l命令
八、继续运行程序:c(continue)命令
可以用一个新的命令c
或者continue
来持续执行程序,直至遇到断点或者程序结束
九、退出程序:q(quit)命令
用q
或者quit
结束本次调试工作,这将使得调试器 GDB 结束运行并返回到操作系统
以上内容参照:http://c.biancheng.net/gdb/