在我们写代码的过程中,Bug是不可避免的.为了找出这写BUG,我们常常需要借助调试工具.在Windows下,我们可以借助各种各样的IDE来进行调试,例如visual studio,visual code,codeblocks等.在Linux平台下,同样也有调试工具,今天这篇博文就来介绍Linux下面被广泛使用的调试工具--GDB。gdb是GNU组织发布的Linux平台下的调试工具,主要用来调试C/C++程序。通过GDB可以获取很多程序运行时基本信息,帮助我们定位错误。

我们调试程序时大致要干什么?

         之所以要调试程序,是因为程序的运行结果和预期结果不一致,或者程序出现运行时出现错误。因为当前的报错信息无法帮我们发现错误,所以需要更多的信息来定位错误,调试就是个获取信息,帮助定位错误的过程。

调试的基本流程可以总结为:

 

 下面我们来看看GDB怎么帮我们实现这些步骤:

 启动gdb

为了使用gdb,需要在编译程序时添加-g选项,使执行文件包含调试信息.

gcc -g main.c  -o filename

在命令行中键入gdb,即可启动gdb,要使用gdb调试某可执行文件,只需要在gdb后加上文件名即可.

gdb filename

 

 

查看代码

 

list 或 l
list linenum 根据行号查看源码
list functionname 根据函数名查看源码

 

 进行调试的时候,我们有的时候会希望一边查看源代码,一边调试,使用list或l命令可以查看源代码(默认)是10行。在后面加参数可以定位到具体的行数。gdb中,按ENTER时会执行上一行命令,所以要持续查看只需要不停按ENTER就行了。

 

命令 作用
list 显示当前行之后的源程序
layout 用于分割窗口,一边查看代码,一边调试

 

 

 

这样子看肯定不方便,在GDB中可以使用layout,一边查看代码,一边调试。

layout src   查看源码

  

 

layout asm 查看汇编窗口
layout regs 查看寄存器与汇编窗口
layout split 查看源码与汇编窗口

使用layout还可以查看汇编和寄存器窗口:

 

 

 

layout prev 切换到上一个窗口
layout next 切换到下一个窗口
focus winname 将视角聚集在某窗口上,winname为窗口名字

 

有一些快捷键可以帮助我们切换:

 

CTRL + X     再按1 单窗口模式,显示一个窗口
CTRL + X     再按2 双窗口模式,显示两个窗口
CTRL + X     再按a 退出layout

 

2. 设置断点

    断点,是所有调试器的重要调试功能,可以让程序中断在指定的地方,便于分析,在gdb中可以使用break或者b设置断点。

 

break 或者 b 设置断点
break linename 在某行设置断点
break functionname 在某函数入口处设置断点
info breakpoints [n] 可以查看某个断点的具体信息

 

 

3. 执行

命令 作用
run或r 开始从头运行当前程序,直到出现断点
step或s 执行当前语句,如果遇上调用的函数,则进入函数当中
next或n 执行当前语句,如果遇上调用的函数,则进入函数当中
cont或c 继续程序的运行,直到出现下一个断点

4 查看变量信息

命令 作用
print var 显示变量var的值
display var 运行时自动显示var的值
watch var 设置var为观察者,当该变量发生变化时,停止运行

 

5. 追踪调用信息

命令 作用
backtrace或bt 回溯查找函数的调用栈,定位错误
frame n 定位源代码中的错误,n代表忽略前几行

6.其他

命令 作用
set args

为程序的运行设置参数

info

列出关于命令的信息

disable 禁用设置
quit 退出

7. 修改程序中的逻辑

命令 作用
set variable 修改临时变量的值
jump 跳转执行
signal 产生信号量给正在调试的程序
return 强制函数返回
call 强制调用程序中的函数

 

对core dump进行调试

core dump是什么

  core dump是Linux系统下程序崩溃时,系统产生的文件,中文叫做转储文件.它相当于会记录下发生错误时,进程空间中内存的信息映射.通过对这些信息进行调试,我们可以了解为什么系统会发生错误.

产生core dump的原因

一般来说,出现core dump往往是出现了内存错误,包括下面几种情况:

  • 访问空指针
  • 内存访问越界
  • 堆栈溢出

开启core dump调试

  Linux系统默认是不产生core dump文件的,因为如果产生的core dump文件过大,就是很大的存储负担,所以在程序上线的过程中,默认不产生core dump文件.在调试阶段,可以使用ulimit命令产生core dump文件

ulimit -c unlimited // unlimited代表不限制产生core文件的内存大小

如何调试core dump

  就像调试普通可执行文件一样,可以使用gdb+执行文件名+core dump文件名调试core dump文件

gdb filename coredumfilename

  执行该命令后,gdb会显示错误出现在filename中的第几行,然后,可以用backtrace命令回溯追踪,查看函数的调用情况