gdb 调试_GDB调试指南-源码查看

前言

我们在调试过程中难免要对照源码进行查看,如果已经开始了调试,而查看源码或者编辑源码却要另外打开一个窗口,那未免显得太麻烦。文本将会介绍如何在GDB调试模式下查看源码或对源码进行编辑

准备工作

为了说明后面的内容,我们先准备一些源码,分别是main.c:

//main.c

头文件test.h:

#ifndef _TEST_H

以及test.c:

#include

编译运行:

$ gcc -g  -o main  main.c test.c
$ chmod +x main
$ ./main
it will print from 5 to 1
5
4
3
2
1
print end
it will print 1 to 5
1
2
3
4
5
print end

程序功能比较简单,用来打印5到1的数以及1到5的数,这里也就不多做解释。

列出源码

首先要介绍的就是list命令(可简写为l),它用来打印源码。

直接打印源码

例如:

$ gdb main
(gdb) l
1   //main.c
2   #include<stdio.h>
3   #include"test.h"
4   int main(void)
5   {
6       printf("it will print from 5 to 1n");
7       printNum(5);
8       printf("print endn");
9   
10      printf("it will print 1 to 5n");
(gdb)

直接输入l可从第一行开始显示源码,继续输入l,可列出后面的源码。后面也可以跟上+或者-,分别表示要列出上一次列出源码的后面部分或者前面部分。

列出指定行附近源码

l后面可以跟行号,表明要列出附近的源码:

(gdb) l 9
4   int main(void)
5   {
6       printf("it will print from 5 to 1n");
7       printNum(5);
8       printf("print endn");
9   
10      printf("it will print 1 to 5n");
11      printNum1(5);
12      printf("print endn");
13      return 0;

在这里,l后面跟上9,表明要列出第9行附近的源码。

列出指定函数附近的源码

这个很容易理解,而使用也很简单,l后面跟函数名即可,例如:

(gdb) l printNum
1   #include"test.h"
2   void printNum(int n)
3   {
4       if( n < 0)
5           return;
6       while(n > 0)
7       {
8           printf("%dn",n);
9           n--;
10      }

在这里,l后面跟上函数名printNum,它便列出了printNum函数附近的源码。

设置源码一次列出行数

不知道你有没有发现,在列出函数源码的时候,它并没有列全,因为l每次只显示10行,那么有没有方法每次列出更多呢? 我们可以通过listsize属性来设置,例如设置每次列出20行:

(gdb) set listsize 20
(gdb) show listsize
Number of source lines gdb will list by default is 20.

这样每次就会列出20行,当然也可以设置为0或者unlimited,这样设置之后,列出就没有限制了,但源码如果较长,查看将会不便。

列出指定行之间的源码

list first,last 例如,要列出3到15行之间的源码:

(gdb) l 3,15
3   {
4       if( n < 0)
5           return;
6       while(n > 0)
7       {
8           printf("%dn",n);
9           n--;
10      }
11  }
12  
13  void printNum1(int n)
14  {
15      if( n < 0)

启始行和结束行号之间用逗号隔开。两者之一也可以省略,例如:

(gdb) list 3,
3   {
4       if( n < 0)
5           return;
6       while(n > 0)
7       {
8           printf("%dn",n);
9           n--;
10      }
11  }
12

省略结束行的时候,它列出从开始行开始,到指定大小行结束,而省略开始行的时候,到结束行结束,列出设置的大小行,例如默认设置为10行,则到结束行为止,总共列出10行。前面我们也介绍了修改和查看默认列出源码行数的方法。

列出指定文件的源码

前面执行l命令时,默认列出main.c的源码,如果想要看指定文件的源码呢?可以

l location

其中location可以是文件名加行号或函数名,因此可以使用:

(gdb) l test.c:1
1   #include"test.h"
2   void printNum(int n)
3   {
4       if( n < 0)
5           return;
6       while(n > 0)
7       {
8           printf("%dn",n);
9           n--;
10      }
(gdb)

来查看指定文件指定行,或者指定文件指定函数:

(gdb) l test.c:printNum1
9           n--;
10      }
11  }
12  
13  void printNum1(int n)
14  {
15      if( n < 0)
16          return;
17      int i = 1;
18      while(i <= n)
(gdb)

或者指定文件指定行之间:

(gdb) l test.c:1,test.c:3
1   #include"test.h"
2   void printNum(int n)
3   {
(gdb)

指定源码路径

在查看源码之前,首先要确保我们的程序能够关联到源码,一般来说,我们在自己的机器上加上-g参数编译完之后,使用gdb都能查看到源码,但是如果出现下面的情况呢?

源码被移走

例如,我现在将main.c移动到当前的temp目录下,再执行l命令:

(gdb) l
1   main.c: No such file or directory.
(gdb)

它就会提示找不到源码文件了,那么怎么办呢? 我们可以使用dir命名指定源码路径,例如:

(gdb) dir ./temp
Source directories searched: /home/hyb/workspaces/gdb/sourceCode/./temp:$cdir:$cwd

这个时候它就能找到源码路径了。我这里使用的是相对路径,保险起见,你也可以使用绝对路径。

更换源码目录

例如,你编译好的程序文件,放到了另外一台机器上进行调试,或者你的源码文件全都移动到了另外一个目录,怎么办呢?当然你还可以使用前面的方法添加源码搜索路径,也可以使用set substitute-path from to将原来的路径替换为新的路径,那么我们如何知道原来的源码路径是什么呢?借助readelf命令可以知道:

$ readelf main -p .debug_str[     0]  long unsigned int[    12]  short int[    1c]  /home/hyb/workspaces/gdb/sourceCode[    40]  main.c
(显示部分内容)

main为你将要调试的程序名,这里我们可以看到原来的路径,那么我们现在替换掉它:

(gdb) set substitute-path /home/hyb/workspaces/gdb/sourceCode /home/hyb/workspaces/gdb/sourceCode/temp
(gdb) show substitute-path
List of all source path substitution rules:`/home/hyb/workspaces/gdb/sourceCode' -> `/home/hyb/workspaces/gdb/sourceCode/temp'.
(gdb)

设置完成后,可以通过show substitute-path来查看设置结果。这样它也能在正确的路径查找源码啦。

需要注意的是,这里对路径做了字符串替换,那么如果你有多个路径,可以做多个替换。甚至可以对指定文件路径进行替换。

最后你也可以通过unset substitute-path [path]取消替换。

编辑源码

为了避免已经启动了调试之后,需要编辑源码,又不想退出,可以直接在gdb模式下编辑源码,它默认使用的编辑器是/bin/ex,但是你的机器上可能没有这个编辑器,或者你想使用自己熟悉的编辑器,那么可以通过下面的方式进行设置:

$ EDITOR=/usr/bin/vim
$ export EDITOR

/usr/bin/vim可以替换为你熟悉的编辑器的路径,如果你不知道你的编辑器在什么位置,可借助whereis命令或者witch命令查看:

$ whereis vim
vim: /usr/bin/vim /usr/bin/vim.tiny /usr/bin/vim.basic /usr/bin/vim.gnome /etc/vim /usr/share/vim /usr/share/man/man1/vim.1.gz
$ which vim
/usr/bin/vim

设置之后,就可以在gdb调试模式下进行编辑源码了,使用命令edit location,例如:

(gdb)edit 3  #编辑第三行
(gdb)edit printNum #编辑printNum函数
(gdb)edit test.c:5 #编辑test.c第五行

可自行尝试,这里的location和前面介绍的一样,可以跟指定文件的特定行或指定文件的指定函数。 编辑完保存后,别忘了重新编译程序:

(gdb)shell gcc -g -o main main.c test.c

这里要注意,为了在gdb调试模式下执行shell命令,需要在命令之前加上shell,表明这是一条shell命令。这样就能在不用退出GDB调试模式的情况下编译程序了。

另外一种模式

启动时,带上tui(Text User Interface)参数,会有意想不到的效果,它会将调试在多个文本窗口呈现:

gdb main -tui

070635b200050f4bf3cb43b85189b8e7.png

但是本文不作介绍,有兴趣的可以探索一下。

总结

本文介绍了GDB调试中的源码查看,源码编辑以及如何在GDB调试模式下执行shell命令。

本文最新内容地址:GDB调试指南-源码查看

相关内容

GDB调试指南-启动调试

GDB调试指南-断点设置

GDB调试指南-变量查看

GDB调试指南-单步调试

微信公众号【编程珠玑】:专注但不限于分享计算机编程基础,Linux,C语言,C++,数据结构与算法,工具,资源等编程相关[原创]技术文章,号内包含大量经典电子书和视频学习资源。欢迎一起交流学习,一起修炼计算机“内功”,知其然,更知其所以然。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/507712.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

深度学习(2)--常见概率分布(2)

上一部分介绍了伯努利分布、二项式分布、多项式分布以及范畴分布&#xff0c;这里将继续介绍高斯分布、指数分布、Laplace分布、Dirac分布、经验分布及混合分布。 高斯分布 高斯分布又称为正态分布&#xff0c;其图形为钟形曲线(bell-shaped curve)&#xff0c;特点是中间高、…

update 千万数据_mysql学习(四)数据库

创建数据库create database 数据库名; 创建数据库的时候&#xff0c;我们应该记住以下几点&#xff1a; 1 不能与其他数据库名重复 2 名称可以由任意字母&#xff0c;阿拉伯数字&#xff0c;下划线&#xff0c;美元符&#xff0c;但是必须以字母开头 3 名称最长为64个字符&…

linux gpio按键驱动程序,Linux GPIO Key 驱动的加载

gpio-keys是基于input子系统实现的一个通用的GPIO按键驱动,基于platform来实现,位于drivers/input/keyboard/gpio_keys.c,这个文件是硬件无关的,而硬件有关的需要我们自己来注册.进入这个gpio_keys.c这个函数,第一步就是初始化.static int __init gpio_keys_init(void){return …

深度学习(3)--常用激活函数的有用性质

1 sigmoid函数 sigmoid函数是一个在生物学中常见的S型函数&#xff0c;也称为S型生长曲线。 sigmoid函数由下列公式定义: σ(x)11e−x(1)\sigma(x) \frac{1}{1 e^{-x}} \tag1σ(x)1e−x1​(1) sigmoid函数的级数表示&#xff1a; σ(x)1214x−148x31480x5−1780640x73114515…

kvm虚拟机不通网关_linux ssh 虚拟机下CentOS7开启SSH连接

一. 没开启&#xff0c;连接会报错二. 开启后&#xff0c;连接成功在虚拟机(Vmware Workstation)下&#xff0c;安装了CentOS7&#xff0c;现在想通过SSH工具连接虚拟机中的CentOS71、 首先&#xff0c;要确保CentOS7安装了 openssh-server&#xff0c;在终端中输入 yum list i…

linux netstat服务,linux netstat查看服务和端口状态

netstat可以查看linux系统中正在使用的服务和端口情况常见参数-a (all)显示所有选项&#xff0c;默认不显示LISTEN相关-t (tcp)仅显示tcp相关选项-u (udp)仅显示udp相关选项-n 拒绝显示别名&#xff0c;能显示数字的全部转化成数字。-l 仅列出有在 Listen (监听) 的服务状态-p …

memcpy函数实现_等比例缩放c++ opencv 实现

背景&#xff1a;在目标检测算法中&#xff0c; 输入图片等比例resize时mAP比直接resize会高几个点。实现&#xff1a;使用c 和opencv实现(之所以没用python&#xff0c;是因为用于生产环境)先贴代码&#xff1a;#include <math.h> #include <opencv2/core/core.hpp&g…

睡眠音频分割及识别问题(十一)--基于Android的YAMNet音频识别(总结)

WAV文件格式介绍 WAV文件遵守资源交换文件格式之规则&#xff0c;在文件的前44(或46)字节放置标头(header)&#xff0c;使播放器或编辑器能够简单掌握文件的基本信息&#xff0c;其内容以区块(chunk)为最小单位&#xff0c;每一区块长度为4字节&#xff0c;而区块之上则由子区…

黑白棋游戏水平(2)--pytorch剪裁

系统需求 Linux系统&#xff0c;并已安装git、gcc、g、cmake⼯具 下载源码 从github克隆Pytorch仓库 git clone --recursive https://github.com/pytorch/pytorch如果已经克隆过&#xff0c;则使⽤以下命令更新 git submodule sync git submodule update --init --recurs…

二维码图像去噪文献调研(1)--Real Image Denoising with Feature Attention

简介 &#xff08;1&#xff09; 论文&#xff08;包括期刊和发表时间&#xff09;&#xff1a; Real Image Denoising with Feature Attention&#xff08;ICCV 2019&#xff09; &#xff08;2&#xff09; 论文链接&#xff1a; https://arxiv.org/pdf/1904.07396.pdf &…

idea gui插件_给 IDEA 换了酷炫的主题,研发小姐姐看到:feel so high。。。

点击上方[全栈开发者社区]→右上角[...]→[设为星标⭐]IntelliJ IDEA介绍IDEA&#xff0c;全称 IntelliJ IDEA &#xff0c;是 Java 语言的集成开发环境&#xff0c; IDEA 在业界被公认为是最好的 java 开发工具之一&#xff0c;尤其在智能 代码助手、代码自动提示、重构、 J2E…

华为荣耀电脑第三方linux,【第三方Linux版】荣耀MagicBook Pro 16.1英寸全面屏如何?某东入手评测...

这款【第三方Linux版】荣耀MagicBook Pro 16.1英寸全面屏轻薄笔记本电脑(酷睿i5 8G 512G MX250 IPS)冰河银&#xff0c;看网上评测推荐的&#xff0c;后面网上种草了这款笔记本&#xff0c;用过一段日子了&#xff0c;分享使用感受如下&#xff1a;一、【第三方Linux版】荣耀Ma…

二维码提升对比度文献调研(1)--Fast Image Processing with Fully-Convolutional Networks

简介 (1) 论文 &#xff08;期刊和发表时间&#xff09; Fast Image Processing with Fully-Convolutional Networks (ICCV 会议 2017) (2) 论文链接 https://openaccess.thecvf.com/content_iccv_2017/html/Chen_Fast_Image_Processing_ICCV_2017_paper.html (3) 源代码链接 …

linux下 c语言 用write open二进制写文件,Linux下用C语言fopen、fread和fwrite函数对二进制文件的操作-Go语言中文社区...

一、前言在做一个镜头的初始化操作&#xff0c;需要加载一个648*522像素大小的文件&#xff0c;厂商提供的是一个excel表&#xff0c;如果要加载数据&#xff0c;可用加载txt文本的方式&#xff0c;我选用二进制方式加载文件&#xff1b;大家都知道电脑真正执行的不是高级语言&…

二维码提升对比度文献调研(2)--Zero-Reference Deep Curve Estimation for Low-Light Image Enhancement

简介 论文 &#xff08;期刊和发表时间&#xff09; Zero-Reference Deep Curve Estimation for Low-Light Image Enhancement (CVPR 会议 2020)论文链接 https://openaccess.thecvf.com/content_CVPR_2020/html/Guo_Zero-Reference_Deep_Curve_Estimation_for_Low-Light_Imag…

python打开是什么样子的图片_黑洞6问:黑洞内部是什么样子?黑洞图片发布,理论和实测的碰撞...

在科学领域&#xff0c;没有什么比你在第一次观察或实验结果中验证一个长期的理论预测时更令人兴奋的了。2012年&#xff0c;大型强子对撞机揭示了希格斯玻色子——标准模型中最后未发现的基本粒子的存在。 几年前&#xff0c;LIGO合作直接探测到了引力波&#xff0c;证实了对爱…

二维码提升对比度文献调研(3)--A Low-Complexity Algorithm for Contrast Enhancement of Digital Images

简介 &#xff08;1&#xff09;论文&#xff08;包括期刊和发表时间&#xff09;&#xff1a;A Low-Complexity Algorithm for Contrast Enhancement of Digital Images &#xff08;2&#xff09;论文链接&#xff1a; http://www.mecs-press.net/ijigsp/ijigsp-v10-n2/IJIG…

安卓checkbox无响应_【安卓手机】无法连接电脑的解决方法

转自&#xff1a;广西南宁平衡信息技术有限公司&#xff0c;作者&#xff1a;平衡LivY一般在对手机的数据采集过程中&#xff0c;尤其是安卓手机&#xff0c;最令人头疼的就是手机接入电脑后无法识别。相信以下窗口是大家在做手机取证的时候最不想看到的。那么这里大伙就会有疑…

linux s删除第一行,Linux文本处理三驾马车之一sed

sed对"行"操作动作含义a &#xff1a;新增&#xff0c; a 接字串&#xff0c;而这些字串会在新的一行出现(目前的下一行)&#xff5e;sed 1a\llll llllllll \n lllllll t.txtnl /etc/passwd | sed 2a drink teased -i $a# This is a test regular_express.txt ####文…

二维码提升对比度文献调研(4)--Attention Guided Low-light Image Enhancement

简介 &#xff08;1&#xff09;论文2&#xff1a; Attention Guided Low-light Image Enhancement with a Large Scale Low-light Simulation Dataset &#xff08;2&#xff09;论文链接&#xff1a; https://arxiv.org/pdf/1908.00682v3.pdf &#xff08;3&#xff09;源代…