GDB手动加载符号表文件调试

1 测试程序源代码

// file a.c
#include <stdio.h>
#include <unistd.h>

int f()
{
    printf("f() @ %p\n", f);
}

extern int f2();

int main()
{
    while(1)
    {
        f();
        f2();
        sleep(1);
    }
    return 0;
}
// file b.c
#include <stdio.h>

int f2()
{
    printf("f2() @ %p\n", f2);
}

2 编译生成测试文件

编译动态库libb.so

gcc -g -shared -fPIC b.c -o libb.so
objcopy --only-keep-debug libb.so libb.so.debug
strip libb.so

编译可执行文件a.out

gcc -g a.c -o a.out -L. -lb                  # 生成带调试信息的可执行文件
objcopy --only-keep-debug a.out a.out.debug  # 将符号表从程序中剥离出来
strip a.out                                  # 去除可执行文件中的符号表

3 GDB手动加载符号表调试

3.1 运行测试文件

user@host:~/mpt/c/hello$ LD_LIBRARY_PATH+=. ./a.out
f() @ 0x56268ccbd79a
f2() @ 0x7fde6134d62a
f() @ 0x56268ccbd79a
f2() @ 0x7fde6134d62a
f() @ 0x56268ccbd79a
f2() @ 0x7fde6134d62a
f() @ 0x56268ccbd79a
f2() @ 0x7fde6134d62a
...

3.2 使用GDB调试

1 - 启动GDB

user@host:~/mpt/c/hello$ sudo gdb
(gdb)

2 - 获取要调试程序的进程号

(gdb) shell ps -u user | grep a.out
18997 pts/42   00:00:00 a.out

3 - attach

(gdb) attach 18997
Attaching to process 18997
Reading symbols from /home/user/mpt/c/hello/a.out...(no debugging symbols found)...done.
Reading symbols from ./libb.so...(no debugging symbols found)...done.
Reading symbols from /lib/x86_64-linux-gnu/libc.so.6...Reading symbols from /usr/lib/debug//lib/x86_64-linux-gnu/libc-2.27.so...done.
done.
Reading symbols from /lib64/ld-linux-x86-64.so.2...Reading symbols from /usr/lib/debug//lib/x86_64-linux-gnu/ld-2.27.so...done.
done.
0x00007fde61040654 in __GI___nanosleep (requested_time=requested_time@entry=0x7fff323b0800, remaining=remaining@entry=0x7fff323b0800)
    at ../sysdeps/unix/sysv/linux/nanosleep.c:28
28      ../sysdeps/unix/sysv/linux/nanosleep.c: No such file or directory.

3 - 查看进程文件地址绑定信息

(gdb) info files
Symbols from "/home/user/mpt/c/hello/a.out".
Native process:
        Using the running image of attached process 18997.
        While running this, GDB does not access memory from...
Local exec file:
        `/home/user/mpt/c/hello/a.out', file type elf64-x86-64.
        Entry point: 0x56268ccbd690
        0x000056268ccbd238 - 0x000056268ccbd254 is .interp
        0x000056268ccbd254 - 0x000056268ccbd274 is .note.ABI-tag
        0x000056268ccbd274 - 0x000056268ccbd298 is .note.gnu.build-id
        0x000056268ccbd298 - 0x000056268ccbd2d0 is .gnu.hash
        0x000056268ccbd2d0 - 0x000056268ccbd420 is .dynsym
        0x000056268ccbd420 - 0x000056268ccbd4d9 is .dynstr
        0x000056268ccbd4da - 0x000056268ccbd4f6 is .gnu.version
        0x000056268ccbd4f8 - 0x000056268ccbd518 is .gnu.version_r
        0x000056268ccbd518 - 0x000056268ccbd5d8 is .rela.dyn
        0x000056268ccbd5d8 - 0x000056268ccbd620 is .rela.plt
        0x000056268ccbd620 - 0x000056268ccbd637 is .init
        0x000056268ccbd640 - 0x000056268ccbd680 is .plt
        0x000056268ccbd680 - 0x000056268ccbd688 is .plt.got
        0x000056268ccbd690 - 0x000056268ccbd852 is .text
        0x000056268ccbd854 - 0x000056268ccbd85d is .fini
        0x000056268ccbd860 - 0x000056268ccbd86e is .rodata
        0x000056268ccbd870 - 0x000056268ccbd8b4 is .eh_frame_hdr
        0x000056268ccbd8b8 - 0x000056268ccbd9e0 is .eh_frame
        0x000056268cebdd98 - 0x000056268cebdda0 is .init_array
        0x000056268cebdda0 - 0x000056268cebdda8 is .fini_array
        0x000056268cebdda8 - 0x000056268cebdfa8 is .dynamic
        0x000056268cebdfa8 - 0x000056268cebe000 is .got
        0x000056268cebe000 - 0x000056268cebe010 is .data
        0x000056268cebe010 - 0x000056268cebe018 is .bss
        0x00007fde6134d1c8 - 0x00007fde6134d1ec is .note.gnu.build-id in ./libb.so
        0x00007fde6134d1f0 - 0x00007fde6134d22c is .gnu.hash in ./libb.so
        0x00007fde6134d230 - 0x00007fde6134d350 is .dynsym in ./libb.so
        0x00007fde6134d350 - 0x00007fde6134d3e9 is .dynstr in ./libb.so
        0x00007fde6134d3ea - 0x00007fde6134d402 is .gnu.version in ./libb.so
        0x00007fde6134d408 - 0x00007fde6134d428 is .gnu.version_r in ./libb.so
        0x00007fde6134d428 - 0x00007fde6134d4e8 is .rela.dyn in ./libb.so
        0x00007fde6134d4e8 - 0x00007fde6134d500 is .rela.plt in ./libb.so
        0x00007fde6134d500 - 0x00007fde6134d517 is .init in ./libb.so
        0x00007fde6134d520 - 0x00007fde6134d540 is .plt in ./libb.so
        0x00007fde6134d540 - 0x00007fde6134d548 is .plt.got in ./libb.so
        0x00007fde6134d550 - 0x00007fde6134d64c is .text in ./libb.so
        0x00007fde6134d64c - 0x00007fde6134d655 is .fini in ./libb.so
        0x00007fde6134d655 - 0x00007fde6134d660 is .rodata in ./libb.so
        0x00007fde6134d660 - 0x00007fde6134d684 is .eh_frame_hdr in ./libb.so
---Type <return> to continue, or q <return> to quit---q
Quit

4 - 加载符号表调试

从上一步中获取a.out文件的.text段在内存中的实际地址0x000056268ccbd690

(gdb) add-symbol-file a.out.debug 0x000056268ccbd690
add symbol table from file "a.out.debug" at
        .text_addr = 0x56268ccbd690
(y or n) y
Reading symbols from a.out.debug...done.

从上一步中获取libb.so文件的.text段在内存中的实际地址0x00007fde6134d550

(gdb) add-symbol-file libb.so.debug 0x00007fde6134d550
add symbol table from file "libb.so.debug" at
        .text_addr = 0x7fde6134d550
(y or n) y
Reading symbols from libb.so.debug...done.

5 - 可以正常使用GDB断点调试,符号表被正确加载,符号能正确解析

(gdb) b f
Breakpoint 1 at 0x56268ccbd79e: file a.c, line 6.
(gdb) b f2
Breakpoint 2 at 0x7fde6134d62e: file b.c, line 5.
(gdb) c
Continuing.

Breakpoint 1, f () at a.c:6
6           printf("f() @ %p\n", f);
(gdb) c
Continuing.

Breakpoint 2, f2 () at b.c:5
5           printf("f2() @ %p\n", f2);
(gdb) c
Continuing.

Breakpoint 1, f () at a.c:6
6           printf("f() @ %p\n", f);
(gdb) c
Continuing.

Breakpoint 2, f2 () at b.c:5
5           printf("f2() @ %p\n", f2);
(gdb) c
Continuing.

Breakpoint 1, f () at a.c:6
6           printf("f() @ %p\n", f);
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值