c语言debug查看变量值的命令,用 GDB 调试程序并查看dump文件

本文详细介绍了GDB调试器的基本命令,包括file、kill、list、next、step、run、quit等,以及断点设置、清除、执行控制、变量观察和源代码查看等关键操作。还涵盖了Coredump文件的处理和核心命令的实战应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

基本 gdb 命令.

命   令        描  述

file        装入想要调试的可执行文件.

kill        终止正在调试的程序.

list        列出产生执行文件的源代码的一部分.

next        执行一行源代码但不进入函数内部.

step        执行一行源代码而且进入函数内部.

run        执行当前被调试的程序

quit        终止 gdb

watch        使你能监视一个变量的值而不管它何时被改变.

break        在代码里设置断点, 这将使程序执行到这里时被挂起.

make        使你能不退出 gdb 就可以重新产生可执行文件.

shell        使你能不离开 gdb 就执行 UNIX shell 命令.

print       打印函数或变量值

info b      显示所有的断点

info display 显示所有的display

disable 断点号 暂停某个断点

enable 断点号 启动某个断点

delete (断点号) 删除某个断点,不带断点号,全部删除

在调试到链接库函数里,s进行就可以了;不过如果链接库源文件不在同一个目录下的话,要用dir 命令把链接库源文件所在目录加到gdb调试路径里去,同时把源文件放到lib目录下

进入 GDB 及指定可执行档:

1. 进入 GDB 并读入可执行档 (档名为 'PROGRAM'),准备进行除错。

gdb PROGRAM

指定程序代码所在目录及检视程序代码

1. 增加目录 DIR 到收寻程序代码的目录列表 (如果你的程序代码和可执行档放在同一个目录下,就不须指定程序代码所在目录。):

(gdb) directory DIR

2. 检视程序代码,格式计有:

(gdb) list => 显示目前执行程序代码前后各五行的程序代码;或是显示从上次 list 之后的程序代码

(gdb) list function => 显示该程序开始处前后五行的程序代码。

(gdb) list - =>上次显示程序代码的前面的十行。

断点的设定与清除

1. 设定断点(指令为 break,可简写为 (b),格式计有:

(gdb) break filename.c:30 => 在 filename.c 的第三十行处停止执行。

(gdb) break function => 在进入 function 时中断程序的执行。

(gdb) break filename.c:function => 在程序代码档 filename.c 中的函数 function 处设定断点。

(gdb) break => 在下一个将被执行的命令设定断点。

(gdb) break ... if cond => 只有当 cond 成立的时候才中断。cond 须以 C 语言的语法写成。

2. 显示各个断点的信息。

(gdb) info break

3. 清除断点(命令为 clear),格式同 break 。例如 :

(gdb) clear filename.c:30

4. 清除断点,NUM 是在 info break 显示出来的断点编号。

(gdb) delete NUM

全速及逐步执行程序

1. 从程序开头全速执行程序,直到遇到断点或是程序执行完毕为止。

(gdb) run

2. 在程序被中断后,全速执行程序到下一个断点或是程序结束为止 (continue 指令可简写为 c)。

(gdb) continue

3. 执行一行程序. 若呼叫函数, 则将该包含该函数程序代码视为一行程序 (next 指令可简写为 n)。

(gdb) next

4. 执行一行程序. 若呼叫函数, 则进入函数逐行执行 (step 指令可简写为 s)。

(gdb) step

5. 执行一行程序,若此时程序是在 for/while/do loop 循环的最后一行,则一直执行到循环结束后的第一行程序后停止 (until 指令可简写为 u)。

(gdb) until

6. 执行现行程序到回到上一层程序为止。

(gdb) finish

检视及更改变量值

1. print 叙述,显示该叙述执行的结果 (print 指令可简写为 p)。如

(gdb) print a => 显示 a 变量的内容.

(gdb) print sizeof(a) => 显示 a 变量的长度.

2. display 叙述,在每个断点或是每执行一步时显示该叙述值。如

(gdb) display a

3. 更改变量值:

(gdb) print (a=10) => 将变量 a 的值设定为 10.

检视程序执行状态

1. 查看程序执行到此时,是经过哪些函数呼叫的程序 (backtrace 指令可简写为 bt),也就是查看函数呼叫堆栈。

(gdb) backtrace

读取 Core 文件信息

1. 读入 PROGRAM 及 PROGRAM.CORE 档,可检视 Core Dump 时程序变量值及程序流程状态 。

gdb PROGRAM core

说明:'core' 档案是由 PROGRAM 档执行后,遇到 Core Dump 时产生的 Core 檔檔名。如果你还需要该 Core 档,我们建议你将该档案档名更改为 PROGRAM.core。在输入上述命令后,你可以用 GDB 提供的检视变量值以及检视程序执行状态来读取程序 Core Dump 时的状态。

用clear清除断点的时候要和break相对应

如果是用functionName设置的断点就只能 clear functionName

用lineNum设置的断点就只能用clear lineNum

delete 断点号

删除

断点号可以使用info break 得到

我也说说我的体会:

r (程序运行的参数) 可以设置运行时的参数

shell 运行shell环境的东西,比如shell make,完了以后直接r重新启动程序,就可以带上次已经加过的参数运行,不用再敲参数了

b 文件名:行号 有的时候很有用,嘿嘿

x/32uxb 指针 以16进制显示该指针指向的32个字节的数据

-------------------------------------------------------------

Core dump file

查看coredump 文件来源于那个进程

file core.26140

core.26140: ELF 32-bit LSB core file Intel 80386, version 1 (SYSV), SVR4-style, from 'exhpdfmx'

首先要先验证进程是否在运行

ps -ef | grep exhpdfmx

查看coredump

gdb exhpdfmx core.26140

gdb --core=core.26140 exhpdfmx

(gdb) bt #0  0x0053bd46 in malloc_consolidate () from /lib/tls/libc.so.6 #1  0x0053cf57 in _int_malloc () from /lib/tls/libc.so.6 #2  0x0053f0a1 in malloc () from /lib/tls/libc.so.6 #3  0xf600ae47 in operator new () from /usr/lib/libstdc++.so.6 #4  0xf600af59 in operator new[] () from /usr/lib/libstdc++.so.6 #5  0xf7165371 in errAtomHelper_c::WriteToLogFile (this=0x812ad20, location=0x0) at weratohelpermx.cc:1154 #6  0xf71652b6 in errAtomHelper_c::WriteToLogFile (this=0x812ad20) at weratohelpermx.cc:1108 #7  0xf7162fc7 in errAtom_c::WriteToLogFile (this=0x81364d0) at weratomx.cc:670 #8  0x0806f904 in std::operator==, std::allocator > () #9  0x08066b2a in std::operator==, std::allocator > () #10 0x0805ae3b in std::operator+, std::allocator > () #11 0x0804ecae in EXHPDF::NewHandler () #12 0x004eee93 in __libc_start_main () from /lib/tls/libc.so.6 #13 0x0804e345 in ?? ()

<think>好的,用户问的是如何用GDB调试C语言程序。之前用户还问了关于在Win10下调试ARM Neon程序的问题,所以可能他们对底层开发和调试有一定兴趣。需要先确定用户的基础,是否已经了解GDB的基本使用,还是需要从头开始讲解。 首先,用户可能是开发者,正在学习C语言,或者需要调试一个具体的项目。他们可能遇到了程序崩溃、逻辑错误,或者内存泄漏等问题,想用GDB来排查。因为之前的问题涉及ARM和Neon,可能他们现在转向更基础的调试方法,或者是跨平台开发的需要。 接下来,我需要考虑回答的结构。GDB调试C程序的基础步骤包括编译时加入调试信息、启动GDB、设置断点、运行程序、查看变量、单步执行等。还需要覆盖一些高级技巧,比如查看内存、堆栈跟踪、条件断点等。此外,用户可能对可视化工具或替代方案感兴趣,比如VS Code集成,可以适当提及。 需要确保步骤清晰,适合新手跟随操作。例如,编译时要加-g选项,启动GDB命令,常用命令如list、break、run、next、step、print等。可能还需要提醒常见问题,比如没有调试信息导致无法设置断点,或者程序崩溃时的backtrace使用。 另外,用户可能是在Linux环境下使用GDB,但之前的问题涉及Windows,所以可能需要说明GDB在Windows下的安装方式,比如通过MinGW或Cygwin,或者使用WSL。不过根据问题本身,重点还是GDB的使用方法,环境可能用户已经准备好。 需要检查是否有遗漏的关键点,比如处理信号、修改变量值、观察点等。还有如何调试多线程程序,或者核心转储文件,这些可能属于进阶内容,但可以简要提及,供用户进一步学习。 最后,确保语言简洁,步骤明确,示例代码易懂。比如,给出一个简单的C程序示例,演示如何编译和调试。同时,注意排版,使用代码块来展示命令和输出,便于用户复制粘贴和参考。</think>以下是使用GDB调试C语言程序的完整指南,包含基础操作和实用技巧: --- ### 一、基础调试流程 #### 1. 编译时加入调试信息 ```bash gcc -g main.c -o demo # -g选项生成调试符号 ``` #### 2. 启动GDB ```bash gdb ./demo # 启动调试器 (gdb) set args 10 20 # 设置程序参数(可选) ``` #### 3. 核心操作命令 | 命令 | 说明 | 示例 | |---------------|-------------------------------|------------------------| | `list`/`l` | 查看源代码(默认显示10行) | `l 15` 显示第15行附近 | | `break`/`b` | 设置断点 | `b main` 在main函数暂停| | `run`/`r` | 启动程序 | | | `next`/`n` | 单步执行(跳过函数) | | | `step`/`s` | 单步进入函数 | | | `print`/`p` | 打印变量/表达式 | `p *ptr` 查看指针内容 | | `continue`/`c`| 继续运行到下一个断点 | | | `quit`/`q` | 退出GDB | | --- ### 二、高级调试技巧 #### 1. 断点管理 ```gdb b 20 if x>5 # 条件断点(当x>5时在第20行暂停) info breakpoints # 查看所有断点 delete 2 # 删除编号为2的断点 ``` #### 2. 堆栈跟踪 ```gdb backtrace/bt # 查看函数调用栈 frame 2 # 切换到第2层栈帧 up/down # 在栈帧间移动 ``` #### 3. 内存检查 ```gdb x/8xb &array # 以十六进制查看8字节内存 x/s str_ptr # 查看字符串内容 watch var # 设置变量监视点(当var改变时暂停) ``` #### 4. 信号处理 ```gdb handle SIGSEGV stop # 在段错误时暂停程序 signal 9 # 强制发送指定信号 ``` --- ### 三、实战示例 #### 调试以下程序(demo.c): ```c #include <stdio.h> int buggy_add(int a, int b) { return a * b; // 故意写错的加法函数 } int main() { int x = 3; int y = 5; int result = buggy_add(x, y); printf("3 + 5 = %d\n", result); return 0; } ``` #### 调试过程: ```gdb (gdb) b buggy_add # 在错误函数设置断点 (gdb) run # 启动程序 Breakpoint 1, buggy_add (a=3, b=5) at demo.c:3 3 return a * b; (gdb) print a # 查看参数值 $1 = 3 (gdb) print b $2 = 5 (gdb) set var a = 3 # 临时修复错误(改为加法) (gdb) set var b = a + b (gdb) print b $3 = 8 (gdb) continue # 继续执行 Program output: 3 + 5 = 8 ``` --- ### 四、可视化调试(VS Code配置) 1. 安装扩展:`C/C++`、`Native Debug` 2. 创建`.vscode/launch.json`: ```json { "version": "0.2.0", "configurations": [ { "name": "GDB Debug", "type": "cppdbg", "request": "launch", "program": "${workspaceFolder}/demo", "args": [], "stopAtEntry": false, "cwd": "${workspaceFolder}", "environment": [], "externalConsole": false, "MIMode": "gdb", "setupCommands": [ { "description": "启用整齐打印", "text": "-enable-pretty-printing", "ignoreFailures": true } ] } ] } ``` --- ### 五、常见问题排查 1. **无符号信息** 错误提示:`No symbol table is loaded` 解决方案:重新用`gcc -g`编译 2. **多线程调试** ```gdb info threads # 查看线程列表 thread 2 # 切换到线程2 ``` 3. **核心转储分析** ```bash ulimit -c unlimited # 启用core dump gdb ./demo core # 分析崩溃现场 ``` --- 通过掌握这些技巧,您可以高效定位以下问题: - 段错误(SIGSEGV)的崩溃位置 - 逻辑错误导致的错误输出 - 内存泄漏或越界访问 - 多线程竞争条件
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值