GDB调试及其调试脚本的使用
返回脚本百事通
一、GDB调试

1.1. GDB 概述

GDB是GNU开源组织发布的一个强大的UNIX下的程序调试工具。或许,各位比较喜欢那种图形界面方式的,像VC、BCB等IDE的调试,但如果你是在UNIX/Linux平台下做软件,你会发现GDB这个调试工具有比VC、BCB的图形化调试器更强大的功能。所谓“寸有所长,尺有所短”就是这个道理。

一般来说,GDB主要帮忙你完成下面四个方面的功能:

1、启动你的程序,可以按照你的自定义的要求随心所欲的运行程序。
2、可让被调试的程序在你所指定的调置的断点处停住。(断点可以是条件表达式)
3、当程序被停住时,可以检查此时你的程序中所发生的事。
4、动态的改变你程序的执行环境。

从上面看来,GDB和一般的调试工具没有什么两样,基本上也是完成这些功能,不过在细节上,你会发现GDB这个调试工具的强大,大家可能比较习惯了图形化的调试工具,但有时候,命令行的调试工具却有着图形化工具所不能完成的功能。让我们一一看来。

1.2.GDB 使用示例

使用一个简单的判断来测试一下:文件名gdbtest.c

#include "stdio.h"
int main()
{
int x=3;
if(x<4)
printf("x is less than 4\n");
else 
printf("x is biger than 4\n");
}

程序很简单,设置x=3,然后判断x是否比4小,若比4小则输出”x is less than 4“,若比4大,则输出”x is biger than 4“ ,程序很无聊,但是我们可以用来做GDB的测试!

注: 编译的时候需要使用-g选项,我使用的是:gcc -g -o gdbtest gdbtest.c

使用GDB调试:

gdb ./gdbtest <------- 启动GDB 
GNU gdb (GDB) 7.5-ubuntu
Copyright (C) 2012 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "i686-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>...
Reading symbols from /home/long/gdbtest...done.
(gdb) l <------- l命令相当于list,从第一行开始例出原

1 #include "stdio.h"
2 int main()
3 {
4 int x=3;
5 if(x<4)
6 printf("x is less than 4\n");
7 else
8 printf("x is biger than 4\n");
9 }
(gdb) b 5 <------- b相当与break 设置断点,在源程序第5行处。
Breakpoint 1 at 0x8048935: file gdbtest.c, line 5.
(gdb) run <------- 运行程序,也可以用简写r
Starting program: /home/long/gdbtest

Breakpoint 1, main () at gdbtest.c:5 <------- 其实停在第一个断点,在第5行
5 if(x<4)
(gdb) info b <------- 查看断点的信息
Num Type Disp Enb Address What
1 breakpoint keep y 0x08048935 in main at gdbtest.c:5
breakpoint already hit 1 time
(gdb) print x <------- 打印x的值(print 也可以用其简写p)>,这时候x等于上面赋值的3
$1 = 3
(gdb) print &x <------- 打印x的地址
$2 = (int *) 0xbffff21c
(gdb) x/4x 0xbffff21c <------- 查看从0xbffff21c开始的4*4个字节的值
0xbffff21c: 0x00000003 0x0804a000 0x00000000 0x00000000 <------- x为int值,为4个字节
,所以x的值等于0x00000003,我们可以看到此时x等于3
(gdb) set x=5 <------- 我们设置x=5
(gdb) print x <------- 打印x的值,可以看到x已经被改成5了
$3 = 5
(gdb) x/4x 0xbffff21c
0xbffff21c: 0x00000005 0x0804a000 0x00000000 0x00000000
(gdb) n <------- 单条语句执行,next命令简写。 
8 printf("x is biger than 4\n");
(gdb) c <------- 继续运行程序,continue命令简写。
Continuing.
profiling:/home/zhouyl:Cannot create directory
profiling:/home/zhouyl/NicholClass/error_test/gdb/gdbtest.gcda:Skip
x is biger than 4[Inferior 1 (process 9265) exited with code 01] <------- 程序输出x is biger than 4,因为此时x已经被改为5了
(gdb) q <------- 退出gdb
#

在上述GDB调试测试中,我们可以将x的值改为5,然后程序的输出变为 x is biger than 4 。很有趣又很强大是不?

1.3.GDB 更多知识点总结(不断搜集)

1.3.1 GDB 调试如何传参数?

我们仍然使用示例来演示:

示例的代码很简单:test.c

#include <stdio.h>
int main(int argc, char **argv)
{
int i=0;
i=atoi(argv[1]);
i = i + 1;
printf("The value after add the first arg is : %d\n",i);
i=atoi(argv[2]);
i = i - 1;
printf("The value after minus the second arg is : %d\n",i);
return 0;
}

示例中我们分别打印第一个参数加1和第二个参数减1 的值。

我们使用gdb调试:

#gcc -g -o test test.c
#gdb ./test <------- 正常开始调剂程序
GNU gdb (GDB) 7.5-ubuntu
Copyright (C) 2012 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "i686-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>...
Reading symbols from /tmp/test...done.
(gdb) set args 111 1 <------- 在调试时给程序传入参数
(gdb) run
Starting program: /tmp/test 111 1
The value after add the first arg is : 112
The value after minus the second arg is : 0
[Inferior 1 (process 9667) exited normally]
(gdb) q
#

二、GDB调试脚本的使用

下面我们对第一章中的gdbtest.c文件使用gdb脚本调试,其实很简单我们只要把需要的操作放到一个文件中,比如叫做 gdbtest.sh

break 5
run
set x=5
c
q

那么我们如何使用?其实很简单,我们在使用时,不用直接gdb gdbtest ,而使用 gdb ./gdbtest -command=gdbtest.sh

其实还有种方法,我们直接在脚本中添加所要调试的文件信息,此时的 gdbtest.sh内容为:

file gdbtest
break 5
run
set x=5
c
q

而我们调试使用的命令就简单了,直接使用gdb -x gdbtest.sh 即可!

三、GCOV的使用

3.1 gcov是什么?

Gcov is GCC Coverage

是一个测试代码覆盖率的工具

是一个命令行方式的控制台程序

伴随GCC发布,配合GCC共同实现对C/C++文件的语句覆盖和分支覆盖测试;

与程序概要分析工具(profiling tool,例如gprof)一起工作,可以估计程序中哪一段代码最耗时;

注:程序概要分析工具是分析代码性能的工具。

3.2 gcov能做什么?

gcov可以统计:

每一行代码的执行频率

实际上哪些代码确实被执行了

每一段代码(section code)的耗时(执行时间)

因此,gcov可以帮你优化代码,当然这个优化动作还是应该有开发者完成。

3.3 gcov 使用

我们继续使用第一章中的gdbtest.c文件,使用gcov时候,在编译时使用 gcc -g3 -fprofile-arcs -ftest-coverage gdbtest.c

#ls
gdbtest.c gdbtest.sh
#gcc -g3 -fprofile-arcs -ftest-coverage gdbtest.c <-------- 使用-fprofile-arcs -ftest-coverage 参数添加gcov信息,其实可以不使用-g参数,我示例中需要使用gdb调试,所以添加了
#./a.out
x is less than 4
#gcov gdbtest
File‘gdbtest.c’
已执行的行数:83.33% (共 6 行)
Creating 'gdbtest.c.gcov'

# cat gdbtest.c.gcov
-: 0:Source:gdbtest.c
-: 0:Graph:gdbtest.gcno
-: 0:Data:gdbtest.gcda
-: 0:Runs:1
-: 0:Programs:1
-: 1:#include "stdio.h"
1: 2:int main() <----------- "1"为本行运行次数
-: 3:{
1: 4: int x=3;
1: 5: if(x<4)
1: 6: printf("x is less than 4\n");
-: 7: else 
#####: 8: printf("x is biger than 4\n"); <-----------"#####"代表此行未运>行 
1: 9:}

#gdb ./a.out -command=gdbtest.sh <-------- 使用上面的脚本调试,其
实我们的目的是运行 else ,然后看区别! 
GNU gdb (GDB) 7.5-ubuntu
Copyright (C) 2012 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "i686-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>...
Reading symbols from /home/long/gcovtest/a.out...done.
Breakpoint 1 at 0x80489dd: file gdbtest.c, line 5.
Breakpoint 1, main () at gdbtest.c:5
5 if(x<4)
x is biger than 4
[Inferior 1 (process 10165) exited with code 01]
#gcov gdbtest <----------- 多运行几次a.out或者
使用脚本,后想重新看看最新的测试代码覆盖率,需要重新 gcov gdbtest 
File‘gdbtest.c’ 
已执行的行数:100.00% (共 6 行)
Creating 'gdbtest.c.gcov'

#cat gdbtest.c.gcov
-: 0:Source:gdbtest.c
-: 0:Graph:gdbtest.gcno
-: 0:Data:gdbtest.gcda
-: 0:Runs:2
-: 0:Programs:1
-: 1:#include "stdio.h"
2: 2:int main()
-: 3:{
2: 4: int x=3;
2: 5: if(x<4)
1: 6: printf("x is less than 4\n"); <----------- 使用脚本运行时,此>行未执行,所以还是运行了1次
-: 7: else <----------- 其实本行else是运行>过一次的,但是gcov 统计时把本行与下一行打印放在一起计时的!
1: 8: printf("x is biger than 4\n");
2: 9:}
#

gdb调试相关的更多相关文章

  1. ffmpeg 使用 gdb 调试相关技巧

    本文说明了,在ffmpeg二次开发或调用库的过程,如何借助于ffmpeg源码进行调试. 注:ffmpeg版本是4.0. 1. 编写代码 编写将pcm数据转换为mp2的代码 pcm_to_mp2.c # ...

  2. roslaunch & gdb 调试指南(待补充)

    1. 安装xterm sudo apt-get install xterm 2. 在launch文件中添加如下内容: <node name="navigation" pkg= ...

  3. GDB调试-从入门到实践

    你好,我是雨乐! 在上篇文章中,我们分析了线上coredump产生的原因,其中用到了coredump分析工具gdb,这几天一直有读者在问,能不能写一篇关于gdb调试方面的文章,今天借助此文,分享一些工 ...

  4. gdb调试器在windows下的相关内容

    1.gdb调试器在visual studio或dev c++中也有类似的调试图形化可视界面,但是gdb不同的是它是由命令行组成,他的界面对于习惯图形化可视界面的用户来说一时间会不知所措 2.通过gcc ...

  5. gdb调试基本命令(常用)

    gdb调试命令 1>. 启动gdb gdb 可执行程序的名字 2>. 查看代码 l -- 查看当前文件 -- 默认main函数 2. 查看其它文件: l 文件名:行号, 显示指定行号的上下 ...

  6. GDB 调试 一些命令

    1. gdb查看指定地址的内存地址的值:examine 简写 x-----使用gdb> help x 来查看使用方式     x/ (n,f,u为可选参数)n: 需要显示的内存单元个数,也就是从 ...

  7. gdb 调试

    一.gdb 调试-源代码关联 在调试程序的过程中,可以自由地查看相关的源代码(如果有源代码的话)是一项最基本的特性.gdb 当然也提供了这项特性,虽然不如IDE直观,但在一定程度上要比IDE更加灵活和 ...

  8. Linux下GDB调试

    GDB 是一个强大的命令行调试工具.大家知道命令行的强大就是在于,其可以形成执行 序列,形成脚本.UNIX 下的软件全是命令行的,这给程序开发提供了极大的便利,命令行 软件的优势在于, 他们可以非常容 ...

  9. ndk学习6: 使用gdb调试ndk程序一

    生成debug版程序 方法一: 使用ndk-build编译时,加上如下参数NDK_DEBUG=1,之后生成so文件之外,还会生成gdbobserver,gdb.setup调式文件   方法二: 修改A ...

随机推荐

  1. CCNA实验(5) -- OSPF

    enableconf tno ip do loenable pass ciscoline con 0logg syncexec-t 0 0line vty 0 4pass ciscologg sync ...

  2. U盘重装系统win7

    步骤: 1开机f12进入bios模式设置光盘的第一驱动 2U盘拷贝好的ghost镜像插入usb接口,重启默认U盘启动 3启动后进入重装系统界面,选择要重新的系统,进入pe系统,格式化c盘,后面默认自动

  3. OOP中的多态

    尽管一直在说OOP,但说实话还不是真正的理解,面向对象的三个基本特性继承.封装.多态,前两个性质曾经 有接触听的比較多还好理解,以下主要介绍一下第三个特性--多态. 1. 定义     同一操作作用于 ...

  4. Android使用ViewFlipper实现左右滑动效果面

    在我的博客中,上次是使用ViewPager实现左右滑动的效果的,请看文章:Android使用ViewPager实现左右滑动效果. 这次我来使用ViewFlipper实现这种效果,好了,先看看效果吧: ...

  5. ANDROID对文件的操作介绍

    1. Android遵循MVC设计思想: M(业务层):service V:视图(main.xml). C:Activity 2.使用文件如何对数据进行存储 Activity提供了openFileOu ...

  6. 开启新的activity获取它的返回值

    1.开始界面 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:t ...

  7. iOS 10 创建iMessage App

    原文作者 澳大利亚19岁少年--Davis Allie ----原文地址 时值中秋佳节, 送给出门在外的程序猿们 ! 骚年们, 自己写个表情包斗图可否 ! 斗-seal.svg.png 第一. 介绍 ...

  8. 射频识别技术漫谈(24)——ISO15693的防冲突与传输协议

    遵守ISO15693协议的电子标签都有一个8字节共64bit的全球唯一序列号(UID),这个UID一方面可以使全球范围内的标签互相区别,更重要的是可以在多标签同时读写时用于防冲突.8字节UID按权重从 ...

  9. Delphi中的内存对齐 与 Packed关键字

    以delphi为例:TTest = recordc1: char;i1: Integer;c2: char;c3: Char;end;这个结构如果用sizeof取其占用的内存大小,是多少呢,是1+4+ ...

  10. Microsoft 收购 Apiphany

    StevenMartinMS 2013 年 10 月 23 日上午 10:00 今天,我高兴地宣布我们收购了业界领先的 API 管理交付平台 - Apiphany. 应用程序可扩展性已经不算什么新鲜事 ...