gdb 杂项

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

warning: File "/home/hjj/work/customed_server/session_manager/.gdbinit"

auto-loading has been declined by your `auto-load safe-path' set to "$debugdir:$datadir/auto-load".

----------------------------------------
解决办法
gdb -iex "set auto-load safe-path /"
根本解决办法;
在家目录下编辑.gdbinit, 加上 set auto-load safe-path /
查验:
info auto-load

----------------------------------------
gdb 源码路径 ---- elf 文件的 .debug_str 节。
----------------------------------------
readelf -S /usr/local/sbin/nginx 可以看到 nginx 的很多节。
今天特别关注.debug_str 节
前面的几个是全局符号, 其中重要的有一个源代码绝对根路径
readelf  -p .debug_str /usr/local/nginx/sbin/nginx |grep hjj
  [   1c1]  /home/hjj/Downloads/nginx-1.7.6

后面是属于不同文件的符号表, 由相对文件名称来引领。
符号可以是变量名称,函数名称,类型名称等等..
方括号括住的是该符号相对于符号表的地址偏移
[/pts/1@hjj ~]$ readelf  -p .debug_str /usr/local/nginx/sbin/nginx
  [   27e]  src/core/nginx.c
  [   28f]  ngx_prefix
  [   29a]  valid_info
  [   2a5]  ngx_uid_t
  [   2af]  ngx_write_fd
  [   2bc]  wdata
  [   2c2]  long long unsigned int
  ...
  [   cc4]  src/core/ngx_log.c
  ...
  [   f68]  src/core/ngx_palloc.c
  ...
  [   fff]  src/core/ngx_array.c
  ...

有了debug_str 节,就可以找到bin文件对应的源文件,

注意: .debug_str 节只有.c,.cpp 源文件信息,.h 文件则不在此处包含

其实,当你废了很大劲时,才发现由更好的方法达到目的, 要查看绝对路径,在gdb中用下面命令:

(gdb) info source
Current source file is src/core/nginx.c
Compilation directory is /home/hjj/Downloads/nginx-1.7.6
Located in /home/hjj/Downloads/nginx-1.7.6/src/core/nginx.c
Contains 1363 lines.
Source language is c.
Compiled with DWARF 2 debugging format.
Does not include preprocessor macro info.

(gdb) info sources

将更加详细的列出所有.c, .h 源文件

.....

------------------------------------------------------------
gdb 扩展: 打印qt的 QString 变量和QByteArray 变量

可以把它放大gdbinit 中,  用source gdbinit 来加载

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

for QT4
define pqstring
    set $i=0
    while $i < $arg0.d->size
        set $c=$arg0.d->data[$i++]
        if $c < 32 || $c > 127
                printf "0x%04x", $c
        else
                printf "%c", (char)$c
        end
    end
    printf "\n"
end

For QT5
define pqs
    printf "(QString)0x%x (length=%i, offset=%i, ref=%x): \"",&$arg0,$arg0.d->size,$arg0.d->offset,&$arg0.d->ref
    set $i=0
    set $off=$arg0.d->offset
    set $base=(void*)(&$arg0.d->ref) + $off
    while $i < $arg0.d->size
        set $c=((short*)$base)[$i++]
        if $c < 32 || $c > 127
                printf "\\u0x%04x", $c
        else
                printf "%c", (char)$c
        end
    end
    printf "\"\n"
end


print QByteArray.
.ex:
p bytes.d->data

define pqbytearray
    set $i=0
    while $i < $arg0.d->size
        set $c = $arg0.d->data[$i++]
        printf "%02x", $c
    end
    printf "\n"
end


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

gdb 中关闭下面的提示信息

---Type <return> to continue, or q <return> to quit---
 

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

set pagination off 即可.

这样,当你help all 时, 所有信息都会输出到屏幕, 方便你copy成文件再阅读!

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

gdb 输出定向到文件

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

1. 利用tee 命令全程跟踪记录gdb 的屏幕输出

 gdb test | tee 1.log

2. 临时向文件输出信息, 例如想把info function 信息输出到文件.

set logging on

info functions

set logging off


------------------------------------------------------------
有关debug版, release版及调试信息,符号信息
------------------------------------------------------------
前言:
1. gcc -g 编译选项,生成debug 版, 有调试信息,
   无-g, 生成release版, 无调试信息
2. strip -g 可以删除debug 信息
3. strip 默认删除所有与运行无关信息, 包括符号表,字符串表,调试相关信息

甲. 删除符号表信息和debug 信息为执行文件瘦身
    $ strip testdbg

乙. 提取debug 信息(下面任何一种均可), 提取的dbg文件仍然是个可执行elf文件
    $ objcopy --only-keep-debug testdbg strip.dbg
    $ strip --only-keep-debug testdbg -o strip.dbg

丙. debug 信息的使用
1:命令行参数指定
a. 载入debug信息文件分析coredump
b. 载入debug信息文件调试程序, 两种指明文件方式可以混用.
$ gdb -e test-striped -c core -s strip.dbg
$ gdb -exec=test-striped -core=core -symbol=strip.dbg

2 还可以动态加载符号表文件:
(gdb) add-symbol-file FILE ADDR
(gdb) h add-symbol-file有更详细介绍.
使用稍微麻烦一点, 还要指定 .text 段地址ADDR, 也有可能需要指定其它段地址.


------------------------------------------------------------
gdb 使用相关
------------------------------------------------------------
查询调试文件信息及函数信息 (需要debug 信息)
(gdb) info source
Current source file is ioputs.c
Compilation directory is /build/eglibc-SvCtMH/eglibc-2.19/libio
Source language is c.
Compiled with DWARF 2 debugging format.
Does not include preprocessor macro info.

(gdb) info sources (glibc 加debug后, 有大量源文件信息!!!)

(gdb) info functions (glibc 加debug后, 有大量函数信息!!!)

设置GDB 代码搜索路径
(gdb) set substitute-path /build/eglibc-SvCtMH/ /build/buildd/
(gdb) show substitute-path

(gdb) dir bak
./a.cpp变成了./bak/a.cpp
(gdb) show dir

多个源文件,gdb时如何在指定的某个文件中设置断点
(gdb) break [<file-name>:]<func-name>
(gdb) break [<file-name>:]<line-num>

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

如何关闭gdb的彩色输出

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

set style enabled off

只所以有这个需求, 是因为我用vim下gdb插件调试,其彩色输出被vim窗口显示成ascii 码,

如下图, 严重影响显示效果. 而关掉彩色输出, 世界就干净了!

    qp_table_buf = ^[[34m0x0^[[m,
    hw_frames_ctx = ^[[34m0x0^[[m,
    opaque_ref = ^[[34m0x0^[[m,

但如果在控制台下使用gdb, 则带彩色会很好.

--------------------------------------------------------------------
将gdb调试限制为一次只能调试一个线程的处理方法
--------------------------------------------------------------------

需求:
我有多个线程,但我想调试一个线程,同时保持其它线程停止。 这样我能够观察这一个线程的表现(单步,下一步)

set scheduler-locking on

--------------------------------------------------------------------
跳过断点N次后再中断
--------------------------------------------------------------------

(gdb) h ignore
  Set ignore-count of breakpoint number N to COUNT.
  Usage is `ignore N COUNT'.

例如: 忽略6号断点100次

ignore 6 100

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

gdb 查看加载的共享库信息

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

(gdb) info sharedlibrary

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

gdb 查看当前的pc值

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

(gdb) p $pc

$pc 是与cpu无关的通用名称。

在x86_64cpu上,也可以用 p $rip

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

gdb 脚本中的注释, 用 # 来注释.

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

Make breakpoint pending on future shared library load? (y or [n]) [answered N; input not from terminal ]

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

我们在脚本里下的断点很可能最开始还没载入,会出现找不到的情况. 此时gdb 默认给我们回答了No, 怎样让GDB 默认回答Yes 呢? 就是加载动态库后,在动态库设置断点 ?

set breakpoint pending on

在设置断点前加上以上设置即可!

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

set style enabled off      //关闭gdb彩色输出
set max-value-size unlimited  //设置gdb打印变量的最大尺寸无限制

set print elements ulimited   // 设置gdb 打印字符串的长度无限制

set breakpoint pending on   //设置gdb断点可以推迟加载

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

常用而又记不住的命令, 留此备份

#set detach-on-fork off       //多进程处理
#set follow-fork-mode child   //多进程 跟踪哪个
#set scheduler-locking on     //多线程其它线程的处理

#set break pending on   //未来断点

#set print elements 0   //设置显示字符串的长度为不限制,  默认是200个字符

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值