GDB调试
一、概念
GDB
是由 GNU 软件系统社区提供的调试工具,同GCC
配套组成了一套完整的开发环境,GDB
是 Linux 和许多类 Unix 系统中的标准开发环境- 一般来说,
GDB
主要帮助你完成下面四个方面的功能- 启动程序,可以按照自定义的要求随心所欲的运行程序
- 可让被调试的程序在所指定的调置的断点处停住(断点可以是条件表达式)
- 当程序被停住时,可以检查此时程序中所发生的事
- 可以改变程序,将一个 BUG 产生的影响修正从而测试其他 BUG
二、准备工作
-
使用以下命令编译:
gcc -g -Wall program.c -o program
- 通常,在为调试而编译时,我们会关掉编译器的优化选项(
-O
), 并打开调试选项(-g
)。另外,-Wall
在尽量不影响程序行为的情况下选项打开所有warning,也可以发现许多问题,避免一些不必要的 BUG -g
选项的作用是在可执行文件中加入源代码的信息,比如可执行文件中第几条机器指令对应源代码的第几行,但并不是把整个源文件嵌入到可执行文件中,所以在调试时必须保证gdb
能找到源文件
- 通常,在为调试而编译时,我们会关掉编译器的优化选项(
-
注:当在
gdb
中直接使用回车
时,会默认执行上一条命令
三、常用命令
实例说明
下面是一个使用GDB进行调试的具体实例,包括代码编写、编译、启动GDB、设置断点、执行调试等。
示例代码
假设你有一个简单的C++程序 example.cpp
:
// example.cpp
#include <iostream>int factorial(int n) {if (n == 0) return 1;return n * factorial(n - 1);
}int main() {int num;std::cout << "Enter a number: ";std::cin >> num;int result = factorial(num);std::cout << "Factorial of " << num << " is " << result << std::endl;return 0;
}
1. 编译程序
首先,使用 -g
选项编译程序以包含调试信息:
g++ -g -o example example.cpp
2. 启动GDB
启动GDB并加载编译后的程序:
gdb ./example
3. 设置断点
在 factorial
函数的入口处设置断点:
(gdb) break factorial
在 main
函数的入口处设置断点:
(gdb) break main
4. 运行程序
运行程序并提供输入:
(gdb) run
程序会在 main
函数的入口处暂停。此时,GDB会显示程序的状态和当前执行的位置。
5. 单步执行
逐行执行 main
函数以查看程序的执行过程:
(gdb) step
继续执行到 factorial
函数的调用处:
(gdb) continue
6. 查看变量
在 factorial
函数内查看传递的参数:
(gdb) print n
查看 result
变量的值:
(gdb) print result
7. 修改变量
在调试过程中,你可以修改变量的值。例如,将 num
改为 5:
(gdb) set var num = 5
8. 查看调用栈
查看当前的调用栈:
(gdb) backtrace
9. 继续执行
继续执行程序,直到下一个断点或程序结束:
(gdb) continue
10. 退出GDB
完成调试后,退出GDB:
(gdb) quit