什么是调试?
所谓调试(Debug),就是让代码一步一步慢慢执行,跟踪程序的运行过程。比如,可以让程序停在某个地方,查看当前所有变量的值,或者内存中的数据;也可以让程序一次只执行一条或者几条语句,看看程序到底执行了哪些代码。
在调试的过程中,我们可以监控程序的每一个细节,包括变量的值、函数的调用过程、内存中数据、寄存器、线程的调度等,从而发现隐藏的错误或者低效的代码。
调试需要借助专业的辅助软件——调试器(Debugger)。现在主流C/C++调试器有下面几种:
1) Remote Debugger
Remote Debugger 是 VC/VS 自带的调试器,与整个IDE无缝衔接,使用非常方便,初学者建议使用该调试器,本教程也以 VS2010 为例讲解调试技巧。
2) WinDbg
大名鼎鼎的 Windows 下的调试器,它的功能甚至超越了 Remote Debugger,它还有一个命令行版本(cdb.exe),但是这个命令行版本的调试器指令比较复杂,不建议初学者使用。
3) LLDB
XCode 自带的调试器,Mac OS X 下开发必备调试器。
4) GDB
Linux 下使用最多的一款调试器,也有 Windows 的移植版。
GDB 入门教程
下面给出一个具有buging.c
的程序:
#include <stdio.h> int getSum(int n) { int sum=0,i; for (i=1;i<=n;i++) sum+=i; return sum; } int main(){ int res=getSum(100); printf("1+2+...+100=%d ",res); }
如果要调试程序,则在进行gcc
编译的时候要加上-g
参数,gcc -g -o bugging bugging.c
。
1. 进入gdb
gdb bugging
gdb bugging -silent
选项-silent
用于屏蔽 GDB 的前导信息,否则它会在屏幕上打印一堆免责条款。
启动 GDB 后,它输出的信息表明已经读入了 mian.out 的符号表。接下来,GDB 会显示自己的提示符(gbd)
,提示并等待你输入调试命令。
2. gdb -b 选项:设置断点
设置断点的命令是b
或者break
, 可以根据行号、函数名、地址来设置断点位置。
b main b 10 b * 0x4004f4
3. gdb -r 选项:执行程序
一旦设置了断点,下一步就是用r
或者run
命令执行被调试的程序,执行后会自动在第一个断点处停下来:
可以用于 c/continue
继续。
4. gdb -p 选项:打印变量的值
(gdb) p i $1 = 0 (gdb) p sum $2 = 140737488347344
可见,gdb还将值存起来并编号了,因此也可以用这个编号访问:
(gdb) p $1 $3 = 0
5. gdb -n 选项:单步调试
调试命令n
或者next
用于继续执行源文件中的下一行。
6. gdb -l 选项:列出源文件
可以通过不带参数(默认展示10行)、行号、函数名
(gdb) list 2 (gdb) list main (gdb) list
7. 查看汇编
# 检查汇编 会给出对应的代码的汇编 disas # 查看寄存器内容 info registers # 打印指定寄存器 print $rsp # 每步执行 stepi # 检查寄存器或某个地址 x/4wd $rsp
8. gdb -q 选项:退出调试
参考链接: