GNU 工具链调试信息分离和挂载:支持 GDB 调试 RELEASE 版本程序

GNU 工具链调试信息分离和挂载:支持 GDB 调试 RELEASE 版本程序

一般地,release 版本的程序都不带调试信息,无法使用 gdb 调试。

GNU 编译工具链和二进制工具链做法如下:

  1. gcc/g++ 使用 -g 编译得到目标程序:gcc hello.c -g
  2. objcopy 复制目标程序中的调试信息:objcopy --only-keep-debug a.out a.debug
  3. strip/objcopy 去除目标程序中的调试信息: strip --strip-unneeded --strip-debug a.out 或者 objcopy --strip-debug a.out
  4. gdb 调试目标程序时加载分离的调试信息:gdb -s a.debug -e a.out 或着 objcopy --add-gnu-debuglink=a.debug a.out 再 gdb a.out

GNU 工具链调试信息分离和挂载:支持 GDB 调试 RELEASE 版本程序_第1张图片

通过上面图片可以看到,gdb是从 a.debug 中读取的符号信息。

另外,通过 readlef 读取 a.out 和 a.debug 各个段信息如下:

a.out 的段信息:

There are 31 section headers, starting at offset 0x3908:

Section Headers:
  [Nr] Name              Type             Address           Offset
       Size              EntSize          Flags  Link  Info  Align
  [ 0]                   NULL             0000000000000000  00000000
       0000000000000000  0000000000000000           0     0     0
  [ 1] .interp           PROGBITS         0000000000000318  00000318
       000000000000001c  0000000000000000   A       0     0     1
  [ 2] .note.gnu.propert NOTE             0000000000000338  00000338
       0000000000000020  0000000000000000   A       0     0     8
  [ 3] .note.gnu.build-i NOTE             0000000000000358  00000358
       0000000000000024  0000000000000000   A       0     0     4
  [ 4] .note.ABI-tag     NOTE             000000000000037c  0000037c
       0000000000000020  0000000000000000   A       0     0     4
  [ 5] .gnu.hash         GNU_HASH         00000000000003a0  000003a0
       0000000000000024  0000000000000000   A       6     0     8
  [ 6] .dynsym           DYNSYM           00000000000003c8  000003c8
       00000000000000a8  0000000000000018   A       7     1     8
  [ 7] .dynstr           STRTAB           0000000000000470  00000470
       0000000000000084  0000000000000000   A       0     0     1
  [ 8] .gnu.version      VERSYM           00000000000004f4  000004f4
       000000000000000e  0000000000000002   A       6     0     2
  [ 9] .gnu.version_r    VERNEED          0000000000000508  00000508
       0000000000000020  0000000000000000   A       7     1     8
  [10] .rela.dyn         RELA             0000000000000528  00000528
       00000000000000c0  0000000000000018   A       6     0     8
  [11] .rela.plt         RELA             00000000000005e8  000005e8
       0000000000000018  0000000000000018  AI       6    24     8
  [12] .init             PROGBITS         0000000000001000  00001000
       000000000000001b  0000000000000000  AX       0     0     4
  [13] .plt              PROGBITS         0000000000001020  00001020
       0000000000000020  0000000000000010  AX       0     0     16
  [14] .plt.got          PROGBITS         0000000000001040  00001040
       0000000000000010  0000000000000010  AX       0     0     16
  [15] .plt.sec          PROGBITS         0000000000001050  00001050
       0000000000000010  0000000000000010  AX       0     0     16
  [16] .text             PROGBITS         0000000000001060  00001060
       0000000000000225  0000000000000000  AX       0     0     16
  [17] .fini             PROGBITS         0000000000001288  00001288
       000000000000000d  0000000000000000  AX       0     0     4
  [18] .rodata           PROGBITS         0000000000002000  00002000
       0000000000000018  0000000000000000   A       0     0     8
  [19] .eh_frame_hdr     PROGBITS         0000000000002018  00002018
       0000000000000044  0000000000000000   A       0     0     4
  [20] .eh_frame         PROGBITS         0000000000002060  00002060
       0000000000000108  0000000000000000   A       0     0     8
  [21] .init_array       INIT_ARRAY       0000000000003db8  00002db8
       0000000000000008  0000000000000008  WA       0     0     8
  [22] .fini_array       FINI_ARRAY       0000000000003dc0  00002dc0
       0000000000000008  0000000000000008  WA       0     0     8
  [23] .dynamic          DYNAMIC          0000000000003dc8  00002dc8
       00000000000001f0  0000000000000010  WA       7     0     8
  [24] .got              PROGBITS         0000000000003fb8  00002fb8
       0000000000000048  0000000000000008  WA       0     0     8
  [25] .data             PROGBITS         0000000000004000  00003000
       0000000000000010  0000000000000000  WA       0     0     8
  [26] .bss              NOBITS           0000000000004010  00003010
       0000000000000008  0000000000000000  WA       0     0     1
  [27] .comment          PROGBITS         0000000000000000  00003010
       000000000000002b  0000000000000001  MS       0     0     1
  [28] .symtab           SYMTAB           0000000000000000  00003040
       00000000000005b8  0000000000000018          29    42     8
  [29] .strtab           STRTAB           0000000000000000  000035f8
       00000000000001f2  0000000000000000           0     0     1
  [30] .shstrtab         STRTAB           0000000000000000  000037ea
       000000000000011a  0000000000000000           0     0     1

a.debug 的段信息:

There are 36 section headers, starting at offset 0x1668:

Section Headers:
  [Nr] Name              Type             Address           Offset
       Size              EntSize          Flags  Link  Info  Align
  [ 0]                   NULL             0000000000000000  00000000
       0000000000000000  0000000000000000           0     0     0
  [ 1] .interp           NOBITS           0000000000000318  00000318
       000000000000001c  0000000000000000   A       0     0     1
  [ 2] .note.gnu.propert NOTE             0000000000000338  00000338
       0000000000000020  0000000000000000   A       0     0     8
  [ 3] .note.gnu.build-i NOTE             0000000000000358  00000358
       0000000000000024  0000000000000000   A       0     0     4
  [ 4] .note.ABI-tag     NOTE             000000000000037c  0000037c
       0000000000000020  0000000000000000   A       0     0     4
  [ 5] .gnu.hash         NOBITS           00000000000003a0  0000039c
       0000000000000024  0000000000000000   A       6     0     8
  [ 6] .dynsym           NOBITS           00000000000003c8  0000039c
       00000000000000a8  0000000000000018   A       7     1     8
  [ 7] .dynstr           NOBITS           0000000000000470  0000039c
       0000000000000084  0000000000000000   A       0     0     1
  [ 8] .gnu.version      NOBITS           00000000000004f4  0000039c
       000000000000000e  0000000000000002   A       6     0     2
  [ 9] .gnu.version_r    NOBITS           0000000000000508  0000039c
       0000000000000020  0000000000000000   A       7     1     8
  [10] .rela.dyn         NOBITS           0000000000000528  0000039c
       00000000000000c0  0000000000000018   A       6     0     8
  [11] .rela.plt         NOBITS           00000000000005e8  0000039c
       0000000000000018  0000000000000018   A       6    24     8
  [12] .init             NOBITS           0000000000001000  00001000
       000000000000001b  0000000000000000  AX       0     0     4
  [13] .plt              NOBITS           0000000000001020  00001000
       0000000000000020  0000000000000010  AX       0     0     16
  [14] .plt.got          NOBITS           0000000000001040  00001000
       0000000000000010  0000000000000010  AX       0     0     16
  [15] .plt.sec          NOBITS           0000000000001050  00001000
       0000000000000010  0000000000000010  AX       0     0     16
  [16] .text             NOBITS           0000000000001060  00001000
       0000000000000225  0000000000000000  AX       0     0     16
  [17] .fini             NOBITS           0000000000001288  00001000
       000000000000000d  0000000000000000  AX       0     0     4
  [18] .rodata           NOBITS           0000000000002000  00001000
       0000000000000018  0000000000000000   A       0     0     8
  [19] .eh_frame_hdr     NOBITS           0000000000002018  00001000
       0000000000000044  0000000000000000   A       0     0     4
  [20] .eh_frame         NOBITS           0000000000002060  00001000
       0000000000000108  0000000000000000   A       0     0     8
  [21] .init_array       NOBITS           0000000000003db8  00000db8
       0000000000000008  0000000000000008  WA       0     0     8
  [22] .fini_array       NOBITS           0000000000003dc0  00000db8
       0000000000000008  0000000000000008  WA       0     0     8
  [23] .dynamic          NOBITS           0000000000003dc8  00000db8
       00000000000001f0  0000000000000010  WA       7     0     8
  [24] .got              NOBITS           0000000000003fb8  00000db8
       0000000000000048  0000000000000008  WA       0     0     8
  [25] .data             NOBITS           0000000000004000  00000db8
       0000000000000010  0000000000000000  WA       0     0     8
  [26] .bss              NOBITS           0000000000004010  00000db8
       0000000000000008  0000000000000000  WA       0     0     1
  [27] .comment          PROGBITS         0000000000000000  0000039c
       000000000000002b  0000000000000001  MS       0     0     1
  [28] .debug_aranges    PROGBITS         0000000000000000  000003c7
       0000000000000030  0000000000000000           0     0     1
  [29] .debug_info       PROGBITS         0000000000000000  000003f7
       000000000000038a  0000000000000000           0     0     1
  [30] .debug_abbrev     PROGBITS         0000000000000000  00000781
       00000000000000e8  0000000000000000           0     0     1
  [31] .debug_line       PROGBITS         0000000000000000  00000869
       0000000000000162  0000000000000000           0     0     1
  [32] .debug_str        PROGBITS         0000000000000000  000009cb
       00000000000002a8  0000000000000001  MS       0     0     1
  [33] .symtab           SYMTAB           0000000000000000  00000c78
       0000000000000690  0000000000000018          34    51     8
  [34] .strtab           STRTAB           0000000000000000  00001308
       0000000000000205  0000000000000000           0     0     1
  [35] .shstrtab         STRTAB           0000000000000000  0000150d
       000000000000015a  0000000000000000           0     0     1

根据二者段信息看见:

  • a.out 中不包含调试信息
  • a.debug 包含调试信息,并且其他段的属性都为 NOBITS,即没有内容。

这种方式可以借鉴用来版本发布,编译时候带上调试信息,发布的版本去除调试信息,调试时候加载分离式的调试信息。其他芯片公司也可以参考GNU的做法设计编译工具链和二进制工具。

你可能感兴趣的:(GDB,编译工具链,开发调试工具,gnu,二进制工具,gdb)