当前位置: 首页 > news >正文

【Linux指南】Linux调试利器gdb入门:从编译到基础命令实战

一、引言:为什么gdb是Linux开发者的必备技能?

在Linux环境下开发C/C++程序时,遇到bug是家常便饭。无论是逻辑错误、内存泄漏还是运行时崩溃,一款强大的调试工具都能帮我们快速定位问题根源。gdb(GNU Debugger) 作为Linux系统中最常用的命令行调试工具,支持断点设置、变量查看、单步执行等核心功能,是开发者排查问题的"利器"。

本文将从最基础的"如何生成可调试程序"讲起,逐步介绍gdb的启动方式、核心调试命令及实战技巧,帮助新手快速掌握gdb的使用方法。

在这里插入图片描述

文章目录

    • 一、引言:为什么gdb是Linux开发者的必备技能?
    • 二、前提:生成可调试的程序
      • 2.1 程序的两种发布模式
      • 2.2 实战:编译可调试程序
    • 三、gdb基础操作:启动与退出
      • 3.1 启动gdb
      • 3.2 退出gdb
    • 四、查看源代码:list命令详解
      • 4.1 基本用法
      • 4.2 示例
    • 五、程序运行控制:从启动到单步执行
      • 5.1 启动程序:run命令
      • 5.2 单步执行:next与step
      • 5.3 结束当前函数:finish命令
      • 5.4 继续运行:continue命令
    • 六、变量与表达式操作:查看与修改
      • 6.1 打印变量/表达式值:print命令
      • 6.2 修改变量值:set var命令
      • 6.3 跟踪变量:display命令
      • 6.4 取消跟踪:undisplay命令
    • 七、断点管理:精准控制暂停位置
      • 7.1 设置断点:break命令
      • 7.2 查看断点:info break命令
      • 7.3 删除断点:delete命令
      • 7.4 禁用/启用断点:disable与enable
    • 八、实战案例:调试一个简单程序
    • 九、总结:必备命令速查表

二、前提:生成可调试的程序

2.1 程序的两种发布模式

Linux下用gcc/g++编译的程序有两种发布模式,调试前必须了解两者的区别:

  • release模式:默认编译模式,生成的二进制文件体积小、运行效率高,但不包含调试信息(如行号、变量类型等),无法用gdb调试。
  • debug模式:需在编译时添加-g选项,会在二进制文件中嵌入调试信息,供gdb识别。只有这种模式的程序才能被gdb调试。

2.2 实战:编译可调试程序

以一个简单的C程序test.c为例:

#include <stdio.h>
int main() {int sum = 0;for (int i = 1; i <= 5; i++) {sum += i;}printf("sum = %d\n", sum);return 0;
}

编译生成可调试文件的命令:

gcc -g test.c -o test  # 关键:-g选项必须添加,否则无法调试

若未加-g选项,使用gdb调试时会提示无法识别调试信息,导致无法正常调试。

三、gdb基础操作:启动与退出

3.1 启动gdb

gdb只能调试**二进制文件**(编译后的可执行程序),不能直接调试源文件
启动命令格式:

gdb 二进制文件名

示例:调试上面生成的test程序

gdb test

执行后会进入gdb调试界面,显示版本信息及命令提示:

GNU gdb (GDB) Red Hat Enterprise Linux 7.6.1-119.el7
Copyright (C) 2013 Free Software Foundation, Inc.
...
(gdb)  # 命令输入提示符

3.2 退出gdb

退出调试界面有两种方式:

  • 输入quit命令并回车
  • 按下Ctrl + d组合键

四、查看源代码:list命令详解

在调试过程中,我们需要随时查看源代码以确定调试位置。gdb的list(缩写l)命令用于显示源代码,支持多种灵活用法。

4.1 基本用法

  • list(或l):默认从当前位置显示10行源代码,多次执行会继续显示后续内容。
  • list 行号(如l 5):显示指定行号附近的代码(以该行号为中心,显示前后内容)。
  • list 函数名(如l main):显示指定函数的源代码,方便快速定位函数入口。
  • list 文件名:行号(如l test.c:8):当调试多文件项目时,可指定文件名和行号查看代码。

4.2 示例

test程序的gdb界面中执行:

(gdb) l main  # 查看main函数代码
1       #include <stdio.h>
2       int main() {
3           int sum = 0;
4           for (int i = 1; i <= 5; i++) {
5               sum += i;
6           }
7           printf("sum = %d\n", sum);
8           return 0;
9       }

五、程序运行控制:从启动到单步执行

掌握程序运行的控制命令是调试的核心,gdb提供了丰富的命令用于控制程序执行流程。

5.1 启动程序:run命令

  • 命令:run(缩写r
  • 功能:启动程序运行,若程序有断点,会在第一个断点处暂停;若无断点,程序会直接运行结束。
  • 示例:
(gdb) r  # 启动test程序
Starting program: /home/user/test 
sum = 15
[Inferior 1 (process 12345) exited normally]

5.2 单步执行:next与step

单步执行用于逐行检查代码执行过程,两者的区别在于是否进入函数内部:

  • next(缩写n):单步执行,不进入函数内部(适合跳过无关函数,关注当前逻辑)。
  • step(缩写s):单步执行,进入函数内部(适合调试函数调用时的逻辑)。

5.3 结束当前函数:finish命令

  • 命令:finish
  • 功能:当进入函数内部调试时,执行该命令可直接运行到函数返回处并暂停,适合快速跳出无关函数。
  • 示例:若在sum += i处单步进入了某个函数,执行finish可直接回到循环逻辑。

5.4 继续运行:continue命令

  • 命令:continue(缩写c
  • 功能:从当前暂停位置继续运行程序,直到遇到下一个断点或程序结束。
  • 场景:常用于多个断点之间的跳转,避免重复单步执行。

六、变量与表达式操作:查看与修改

调试的核心目的之一是观察变量值的变化,gdb提供了多种命令用于操作变量和表达式。

6.1 打印变量/表达式值:print命令

  • 命令:print(缩写p
  • 功能:打印变量值或表达式计算结果。
  • 示例:
(gdb) p sum  # 打印变量sum的值
$1 = 0
(gdb) p i  # 打印变量i的值
$2 = 1
(gdb) p sum + i  # 计算表达式结果
$3 = 1

6.2 修改变量值:set var命令

  • 命令:set var 变量名=值
  • 功能:直接修改程序中变量的值,无需重新编译即可测试不同场景(如强制跳过错误分支)。
  • 示例:
(gdb) set var i=5  # 将i的值改为5,强制循环提前结束
(gdb) p i
$4 = 5

6.3 跟踪变量:display命令

  • 命令:display 变量名
  • 功能:设置变量跟踪,程序每次暂停时会自动打印该变量的值,无需反复输入print
  • 示例:
(gdb) display sum  # 跟踪sum的值
1: sum = 0
(gdb) n  # 单步执行后自动显示sum
4           for (int i = 1; i <= 5; i++) {
1: sum = 0
(gdb) n
5               sum += i;
1: sum = 0
(gdb) n
4           for (int i = 1; i <= 5; i++) {
1: sum = 1

6.4 取消跟踪:undisplay命令

  • 命令:undisplay 编号(编号可通过display命令的输出查看,如上述示例中的1
  • 功能:取消对指定变量的跟踪显示。
  • 示例:
(gdb) undisplay 1  # 取消对sum的跟踪

七、断点管理:精准控制暂停位置

断点是调试中最常用的功能,用于在指定位置暂停程序,以便观察状态。

7.1 设置断点:break命令

  • 命令:break(缩写b

  • 功能:在指定行号、函数或文件中设置断点。

  • 常用用法:

    • b 行号(如b 5):在当前文件第5行设置断点。
    • b 函数名(如b main):在函数入口处设置断点。
    • b 文件名:行号(如b test.c:5):在指定文件的指定行设置断点。
  • 示例:在test.c第5行(sum += i)设置断点:

(gdb) b test.c:5
Breakpoint 1 at 0x400526: file test.c, line 5.

7.2 查看断点:info break命令

  • 命令:info break(缩写info b
  • 功能:显示当前所有断点的信息,包括编号、位置、状态等。
  • 示例:
(gdb) info b
Num     Type           Disp Enb Address            What
1       breakpoint     keep y   0x0000000000400526 in main at test.c:5

7.3 删除断点:delete命令

  • 命令:delete(缩写d
  • 功能:删除断点,支持删除单个或所有断点。
  • 用法:
    • delete 断点编号(如delete 1):删除指定编号的断点。
    • delete breakpoints:删除所有断点。

7.4 禁用/启用断点:disable与enable

  • disable 断点编号:临时禁用断点(断点仍存在,不触发暂停)。
  • enable 断点编号:重新启用被禁用的断点。
  • 场景:暂时不需要某个断点但不想删除时使用。

八、实战案例:调试一个简单程序

下面通过调试test.c演示完整流程:

  1. 编译可调试程序
gcc -g test.c -o test
  1. 启动gdb
gdb test
  1. 设置断点:在循环的sum += i处(第5行)设置断点:
(gdb) b test.c:5
Breakpoint 1 at 0x400526: file test.c, line 5.
  1. 启动程序
(gdb) r
Starting program: /home/user/test Breakpoint 1, main () at test.c:5
5               sum += i;
  1. 单步执行并观察变量
(gdb) n  # 执行sum += i
6           }
(gdb) p sum  # 此时sum=1
$1 = 1
(gdb) n  # 进入下一次循环
5               sum += i;
(gdb) p i  # 此时i=2
$2 = 2
(gdb) p sum  # 执行sum += i前,sum=1
$3 = 1
(gdb) n  # 再次执行sum += i
6           }
(gdb) p sum  # 此时sum=3
$4 = 3
  1. 继续运行到结束
(gdb) c  # 继续执行
Continuing.
sum = 15
[Inferior 1 (process 12345) exited normally]
  1. 退出gdb
(gdb) quit

九、总结:必备命令速查表

命令用途命令(全称/缩写)示例
启动gdbgdb 二进制文件gdb test
退出gdbquit / Ctrl+dquit
查看源代码list / l 行号/函数名l 5、l main
启动程序run / rr
单步执行(不进函数)next / nn
单步执行(进函数)step / ss
继续运行continue / cc
设置断点break / b 位置b 5、b main
查看断点info break / info binfo b
删除断点delete 编号 / delete breakpointsdelete 1、delete breakpoints
打印变量print / p 变量/表达式p sum、p sum+i
修改变量set var 变量=值set var i=5

通过本文的学习,你已经掌握了gdb的基础用法。下一篇将介绍gdb的进阶技巧,包括条件断点、变量跟踪等高级功能,帮助你更高效地调试复杂程序。

http://www.dtcms.com/a/428215.html

相关文章:

  • 住房建设网站用什么技术来做网站
  • 如何对接API接口?需要用到哪些软件工具?
  • App防止恶意截屏功能的方法:iOS、Android和鸿蒙系统的实现方案
  • 做阅读理解的网站兰州专业做网站的公司有哪些
  • windows输入法中英切换(英文提示)ALT + SHIFT切换(搜狗输入法CTRL+SHIFT+E切换)英文键盘
  • 国外支付对接流程记录
  • SRE角度的LSTM学习
  • 外贸网站案例wapcms建站系统
  • 网站服务器失去响应怎么解决wordpress 百度分享
  • 【鬼灭之刃无限城篇4k高清版】免费分享
  • Java8 Function、Consumer、Supplier
  • 网站美化模板长治做网站哪家好
  • UVa11211 Digital Logic
  • 在门户网站做产品seowordpress 上传中文文件名
  • 营销网站建站开发整站seo策略实施
  • Day04_总线驱动
  • 成都市成华区建设局官方网站wordpress啦去
  • 901-008_高级系统架构设计师-考试范围-系统质量属性与架构评估
  • 重庆做网站seo优化选哪家好php数据库的网站模板
  • RMBG2.0 vs. BiRefNet_HR:从「人像抠图」到「万物分割」
  • 怎么做外卖网站网站怎么被搜到首页
  • 无锡做公司网站西固网页设计
  • 【K8s】升级节点
  • Spring Boot自定义全局异常处理:从痛点到优雅实现
  • 网站正在建设中的素材动图网站设计制作程序
  • 企业网站的搭建流程河南论坛网站建设
  • wap网站建设策划方案做艺术字的网站
  • 电脑实用工具,资源下载
  • 曲阳有没有做网站里2345网站登录
  • PostgreSQL 向量操作符的计算和使用方式