前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >gdb调式程序

gdb调式程序

作者头像
黄规速
发布2022-04-14 20:12:31
4770
发布2022-04-14 20:12:31
举报

gdb调式程序

最近要调试PHP源代码,使用工具GDB.

1. GDB简介

GDB是Linux/Unix下一个GNU调试程序,是用来调试C与C++程序的强力调试器。能够让用户在程序运行时观察程序的内部结构和内存的使用情况。

作用:

1)按照自定义的方式启动运行需要调试的程序。

2)可以使用指定位置和条件表达式的方式来设置断点。

3)程序暂停时的值的监视。

4)动态改变程序的执行环境。

2. 基本操作命令:

这里只介绍常用命令的简单用法,如需读者想更加深入的了解,还请读者参照gdb手册。也可以使用--help查看。

基本命令列表:

命令

解释

简写

file

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

list

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

l

next

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

n

step

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

s

run

执行当前被调试的程序

r

continue

继续执行程序

c

quit

终止GDB

q

print

输出当前指定变量的值

p

break

在代码里设置断点

b

info break

查看设置断点的信息

i b

delete

删除设置的断点

d

watch

监视一个变量的值,一旦值有变化,程序停住

wa

help

GDB中的帮助命令

h

3,编程实例

创建c文件:test.c

代码语言:javascript
复制
#include<stdio.h>
#include<string.h>
void prints(int i)
{
   printf("hello %d\n", i);
}
void main ()

{
  int i =0;
  for(i=1;i<6;i++){
     prints(i);
  }

}

编译,其目标文件为test

代码语言:javascript
复制
gcc -o test test.c

这个程序执行

代码语言:javascript
复制
./test 

时显示如下结果:

hello 1 hello 2 hello 3 hello 4 hello 5

4 gdb调试程序

如果需要使用gdb调试

在编译test.c的时候,并把调试选项打开:

代码语言:javascript
复制
gcc -o -ggdb test test.c

(调试选项资料:

调试选项(DEBUGGING OPTION)

GNU CC拥有许多特别选项,既可以调试用户的程序,也可以对GCC排错: -g 以操作系统的本地格式(stabs, COFF, XCOFF,或DWARF).产生调试信息. GDB能够使用这些调试信息. 在大多数使用stabs格式的系统上, `-g'选项启动只有GDB才使用的额外调试信息;这些信息使GDB 调试效果更好,但是有可能导致其他调试器崩溃,或拒绝读入程序.如果你确定要控制是否生成额外的信息, 使用`-gstabs+', `-gstabs', `-gxcoff+', `-gxcoff', `-gdwarf+',或`-gdwarf' (见下文). 和大多数C编译器不同, GNU CC允许结合使用`-g'和`-O'选项.优化的代码偶尔制造 一些惊异的结果:某些声明过的变量根本不存在;控制流程直接跑到没有预料到的地方;某些语句因为计算结果是常量或已经确定而 没有执行;某些语句在其他地方执行,因为他们被移到循环外面了. 然而它证明了调试优化的输出是可能的.对可能含有错误的程序使用优化器是合理的. 如果GNU CC支持输出多种调试信息,下面的选项则非常有用. -ggdb

以本地格式(如果支持)输出调试信息,尽可能包括GDB扩展.

1)启动

2)载入文件:file命令

file test

结果:

代码语言:javascript
复制
gcc -o -ggdb test test.c

也可以通过直接启动的方式载入文件:

代码语言:javascript
复制
root@ubuntu:/opt/c++# gdb test
GNU gdb (Ubuntu/Linaro 7.2-1ubuntu11) 7.2
Copyright (C) 2010 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 /opt/c++/test...done.

3)list命令

也可以过回车查看源代码

代码语言:javascript
复制
(gdb) list
1	#include<stdio.h>
2	#include<string.h>
3	void prints(int i)
4	{
5	   printf("hello %d\n", i);
6	}
7	void main ()
8	
9	{
10	  int i =0;
(gdb) 

一次只列10行,如果要从11行开始继续列源代码可以输入

代码语言:javascript
复制
(gdb) list

也可以什么都不输直接敲回车,gdb提供了一个很方便的功能,在提示符下直接敲回车表示用适当的参数重复上一条命令

回车:

代码语言:javascript
复制
(gdb) list
1	#include<stdio.h>
2	#include<string.h>
3	void prints(int i)
4	{
5	   printf("hello %d\n", i);
6	}
7	void main ()
8	
9	{
10	  int i =0;
(gdb) 
11	  for(i=1;i<6;i++){
12	     prints(i);
13	  }
14	
15	}
16	
(gdb) 

4)单步逐条执行 next

首先用start命令开始执行程序:

代码语言:javascript
复制
(gdb) start
Temporary breakpoint 1 at 0x80483e9: file test1.c, line 10.
Starting program: /opt/c++/test1 

Temporary breakpoint 1, main () at test1.c:10
10	  int i =0;
(gdb) 

这表示停在main函数中变量定义之后的第一条语句处等待我们发命令,gdb列出这条语句表示它还没执行,并且马上要执行

我们可以用next命令(简写为n)控制这些语句一条一条地执行:

代码语言:javascript
复制
(gdb) next
11	  for(i=1;i<6;i++){
(gdb) (直接回车)
12	     prints(i);
(gdb) 

hello 1
11	  for(i=1;i<6;i++){
(gdb) 
12	     prints(i);
(gdb) 
hello 2
11	  for(i=1;i<6;i++){
(gdb) 
12	     prints(i);
(gdb) 
hello 3
11	  for(i=1;i<6;i++){
(gdb) 
12	     prints(i);
(gdb) 
hello 4
11	  for(i=1;i<6;i++){
(gdb) 
12	     prints(i);
(gdb) 
hello 5
11	  for(i=1;i<6;i++){
(gdb) 
15	}
(gdb) 

5)逐条执行并进入函数:

用start命令重新来过,step命令(简写为s)进入 函数中去执行:

代码语言:javascript
复制
(gdb) start
Temporary breakpoint 2 at 0x80483e9: file test1.c, line 10.
Starting program: /opt/c++/test1 

Temporary breakpoint 2, main () at test1.c:10
10	  int i =0;
(gdb) next
11	  for(i=1;i<6;i++){
(gdb) next
12	     prints(i);
(gdb) step
prints (i=1) at test1.c:5
5	   printf("hello %d\n", i);
(gdb) 

进入到了函数 prints

在函数中有几种查看状态的办法,backtrace命令(简写为bt)可以查看函数调用的栈帧:

代码语言:javascript
复制
(gdb) bt
#0  prints (i=1) at test1.c:5
#1  0x08048407 in main () at test1.c:12
(gdb) 

main传进来的参数是i=1。main函数的栈帧编号为1,prints的栈帧编号为0。

6)在可以用info命令(简写为i)查看局部变量

代码语言:javascript
复制
i  locals

如果想查看main函数当前局部变量的值也可以做到,先用frame命令(简写为f)选择1号栈帧然后再查看局部变量:

代码语言:javascript
复制
(gdb) f 1
#1  0x08048407 in main () at test1.c:12
12	     prints(i);
(gdb) 

7)输出当前指定变量的值 print

代码语言:javascript
复制
(gdb) p i
$1 = 1
(gdb) 
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2012-04-09 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 1. GDB简介
  • 2. 基本操作命令:
  • 3,编程实例
  • 4 gdb调试程序
    • 1)启动
      • 2)载入文件:file命令
        • 3)list命令
          • 4)单步逐条执行 next
            • 5)逐条执行并进入函数:
              • 6)在可以用info命令(简写为i)查看局部变量
                • 7)输出当前指定变量的值 print
                领券
                问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档