linux—常用gdb调试命令汇总
Posted 就要 宅在家
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了linux—常用gdb调试命令汇总相关的知识,希望对你有一定的参考价值。
目录
(四).断点(b、info b、d、c、disable、enable)
(五).打印变量和数组(p、display、undisplay)
一.准备工作
首先,我们需要将文件编译为debug版本。因为在linux系统下,默认生成的可执行程序是release版,但是调试需要debug版本。
我们需要在gcc或g++命令后加上限定符-g。这样生成的程序就是debug版本的。
方式如下:
gcc/g++ -g test.c/test.cpp -o test
二.调试命令
*gdp会自动记录最近的命令,如果没有输入其他命令,可以按enter键继续执行最近命令。
(一).查看代码内容(l)
l 命令是用来查看代码内容的。使用方式为
l 行号 默认生成10行,当指定行号时,会生成以指定行号为中间的共10行代码
默认不指定行号时:
(gdb) l
1 #include<iomanip>
2 #include<stdio.h>
3 #include<string.h>
4 #include<iostream>
5 #include<stdlib.h>
6 #include<unistd.h>
7 using namespace std;
8 int main()
9
10 char arr[102] = 0 ;
(gdb)
指定行号:
(gdb) l 10
5 #include<stdlib.h>
6 #include<unistd.h>
7 using namespace std;
8 int main()
9
10 char arr[102] = 0 ;#会以第10行为中心
11 const char* Lop = "|/-\\\\";
12 memset(arr, 0, sizeof(arr));
13 int i = 0;
14 for(i = 0; i <= 100; i++)
(gdb)
(二).开始调试(r)
r命令用来开始代码调试工作,使用方式如下:
r 开始调试,直到程序结束或遇到断点暂停。在调试过程中,再次使用r命令会重新开始调试。
(三).查看当前调试位置(where)
where 查看此时执行位置
(四).断点(b、info b、d、c、disable、enable)
1.打断点
b 行号 在指定行打断点
2.显示断点
info b 显示全部断点信息,也可以在b后加编号显示指定断点
(gdb) b 10 #打断点
Breakpoint 3 at 0x400ac8: file cdl.cpp, line 10.
(gdb) b 15
Breakpoint 4 at 0x400b23: file cdl.cpp, line 15.
(gdb) info b #显示断点
Num Type Disp Enb Address What
3 breakpoint keep y 0x0000000000400ac8 in main() at cdl.cpp:10
4 breakpoint keep y 0x0000000000400b23 in main() at cdl.cpp:15
(gdb)
3.删除断点
d 断点编号 删除指定断点,不加编号则删除全部
注意断点编号不是行号,可以使用info来查看。
(gdb) info b
Num Type Disp Enb Address What
5 breakpoint keep y 0x0000000000400ac8 in main() at cdl.cpp:7
6 breakpoint keep y 0x0000000000400ac8 in main() at cdl.cpp:10
7 breakpoint keep y 0x0000000000400b23 in main() at cdl.cpp:15
8 breakpoint keep y 0x0000000000400b39 in main() at cdl.cpp:17
(gdb) d 5 #删除指定断点
(gdb) d #删除全部断点
Delete all breakpoints? (y or n) y
(gdb) info b
No breakpoints or watchpoints.
(gdb)
4.调试至下一个断点
c 从当前调试位置直接执行到下一个断点处
#断点为10、17、18行
Num Type Disp Enb Address What
1 breakpoint keep y 0x0000000000400ac8 in main() at cdl.cpp:10
2 breakpoint keep y 0x0000000000400b39 in main() at cdl.cpp:17
3 breakpoint keep y 0x0000000000400c04 in main() at cdl.cpp:20
(gdb) r #执行到第10行暂停
Breakpoint 1, main () at cdl.cpp:10
10 char arr[102] = 0 ;
(gdb) c #执行到第17行暂停
Continuing.
Breakpoint 3, main () at cdl.cpp:17
17 cout << '[' << setw(100) << arr << ']' << '[' << i << '%' << ']' << Lop[i % 4] << '\\r';
(gdb)
5.关闭断点
disable 断点编号 关闭断点
注意,关闭断点并不是删除断点。只是在调试时不会在该处暂停,但是断点依旧存在。
使用info b即可看断点关闭与否。
6.打开断点
enable 变量编号 打开断点
同样的,指令需要输入的也是断点编号
(五).打印变量和数组(p、display、undisplay)
1.打印某变量值
p 变量 打印对应的变量值,打印地址直接加取地址符&即可
需要注意的是,这种方法只能显示一次变量值,当继续调试时变量不再显示。
(gdb) p i
$5 = 4
(gdb) n
14 for(i = 0; i <= 100; i++)
(gdb) #变量i没有再次显示
如果我们需要打印数组的值,输入数组名即可。
2.常显示某变量
如果我们需要在调试中一直显示某个变量的值,那么就需要display命令了。
display 变量 常显示指定变量值,使用方式与p一致
(gdb) display arr
3: arr = "---------", '\\000' <repeats 92 times>
(gdb) c
Continuing.
[--------- ][9%]/
Breakpoint 1, main () at cdl.cpp:17
#arr数组常显示
3: arr = "----------", '\\000' <repeats 91 times>
(gdb)
3.删除常显示
undisplay 常显示变量编号 删除指定常显示变量
需要注意的是,不能直接写变量名,变量编号使用info display即可知道。
(六).逐语句、逐过程调试(s、n)
1.逐语句调试(step)
s 逐语句调试。相当于vs中的F11
2.逐过程调试(next)
n 逐过程调试。相当于vs中的F10
(七).函数(bt、finish、until)
1.查看当前堆栈调用
bt 查看当前堆栈调用
主要用于调试至函数内部或者递归调用函数时。
我们以一个递归程序举例:
#include<stdio.h>
void func(int i);
void func(int i)
if(i == 0) return;
printf("hello world\\n");
func(i - 1);
int main()
3
4 func(3);
5 return 0;
6
当我们执行至i == 1时:
2.直接跑完当前函数
finish 可以直接跑完当前函数,若函数只有一层则直接跑完函数。
如果是函数递归调用,当还没开始递归时,finish会执行完整个函数,自动走完全部递归过程(前提无断点)。
当已经递归调用后,在哪一层递归finish就会返回至它的前一层。
我们依旧以上一个递归程序为例:
3.执行至指定行
until 行号 执行至指定行
1 #include"head.h"
2 void func(int i)
3
4 if(i == 0) return;
5 printf("hello world\\n");
6 func(i-1);
7
(gdb) until 5
func (i=3) at function.c:5
5 printf("hello world\\n");
1: i = 3
(gdb)
until也可以在main函数中使用,但一般until用于小范围跳动。
(八).反汇编(disassemble)
disassemble 查看指令附近区域的反汇编
(九).在gdb界面执行linux指令(shell)
shell 指令 在gdb界面中执行linux指令
(十).退出gdb(quit)
(gdb) quit
(gdb) quit
A debugging session is active.
Inferior 1 [process 10341] will be killed.
Quit anyway? (y or n) y
[cdl@VM-16-9-centos ~]$
- “一名优秀的程序员,在穿越单行道时也会确认双向的来车情况。”——道格拉斯·林德(Doug Linder)
如有错误,敬请斧正
GDB调试技巧:常用命令
一 写在开头
1.1 本文内容
总结GDB调试的一些常用命令。不定期更新。
二 常用命令
GDB和VIM一样,功能异常强大,但要熟练掌握它却很需要费时间。不过,尽管它们两个的命令多如牛毛,但只要掌握最常用的那几个命令就可以快速上手。下面的列表总结了GDB最常用的几个命令。
简写 | 全称 | 备注 |
l | list | 显示指定行号或者指定函数附近的源代码 |
b | break | 在指定行号或者指定函数开头处设置断点。如b main |
r | run | 运行程序,直到程序结束或者遇到断点而停下 |
c | continue | 在程序中断后继续执行程序,直到程序结束或者遇到断点而停下。注意在程序开始执行前只能用r,不能用c |
n | next | 执行一条语句。如果有函数调用,则把它作为一个整体 |
s | step | 执行一条语句。如果有函数调用,则进入函数内部 |
u | until | 执行到指定行号或者指定函数的开头 |
p | 显示变量或表达式的值 | |
disp | display | 把一个表达式设置为display,当程序每次停下来时都会显示其值 |
cl | clear | 取消断点,和b的格式相同。如果该位置有多个断点,将同时取消 |
i | info | 显示各种信息。如i b显示所有断点,i disp显示display,而i lo显示所有局部变量 |
h | help | 获取帮助信息 |
三 调试技巧
1. 打印数组中的值
打印数组array的前6个值:p *[email protected]
打印数组array的第6个元素开始的后4个值:p *(array + 5)@4
四 参考资料
1. 《算法竞赛入门经典》
以上是关于linux—常用gdb调试命令汇总的主要内容,如果未能解决你的问题,请参考以下文章