gdb 为裸机程序转储整个内存

gdb dump entire memory for bare metal program

我有一个简单的C程序如下:

int a = 10;
int b = 20;
int sum = 0;

void add() { sum = a + b; }

int main() {
  add();
  return 0;
}

我使用以下命令为 risc-v 编译它并指定 .text 段应从 0x1000.

开始
riscv32-unknown-elf-gcc -static -T elf32lriscv.x -Wl,-Ttext-segment=0x1000 -Wl,-Map=add.elf.map -o add.elf add.c

如果我使用 gdb 打印文件的信息,我会看到以下内容:

(gdb) i files
Symbols from "/home/mango/myp/risc-v/prog/add.elf".
Local exec file:
        `/home/mango/myp/risc-v/prog/add.elf', file type elf32-littleriscv.
        Entry point: 0x108c
        0x00001074 - 0x0000159c is .text
        0x0000259c - 0x000025a0 is .eh_frame
        0x000025a0 - 0x000025a8 is .init_array
        0x000025a8 - 0x000025ac is .fini_array
        0x000025b0 - 0x000029d8 is .data
        0x000029d8 - 0x000029ec is .sdata
        0x000029ec - 0x000029f0 is .sbss
        0x000029f0 - 0x00002a0c is .bss

有没有简单的方法可以转储从0x10740x2a0c的内存?

dump memory 命令需要一个开始和结束地址,但由于这会根据程序而变化,我更希望能够自动转储该值。此外,这在 gdb 中很明显可以访问,有没有办法自动获取它?

我的最终目标是为 gdb 创建一个命令文件并按如下方式传递它以自动进行内存转储:

gdb --command=gdb_commands <filename>

GDB Python API 中似乎没有公开部分。

您可以按照 readelf -WS foo.elf | grep .bss 的行编写一个简单的 shell 脚本来提取结束地址并为您编写 gdb_commands 文件。

更好:让脚本为您找出结束地址和 运行 GDB,不需要 gdb_commandsgdb -ex 'dump binary memory $dump_filename $start $end' $elf

最好提取 PT_LOAD 段而不是将此脚本基于部分,以便更稳健地防止部分重新排序。

更新:

我猜你不关心部分,但关心段。

that's very helpful. It shows me which part of the memory is writable. But it seems like it only includes data and sdata and not bss and sbss. Here is the output from gdb and from readelf: http://pastebin.com/HdW12MzS

Local exec file:
        `/home/mango/myp/risc-v/prog/add.elf', file type elf32-littleriscv.
        Entry point: 0x108c
        0x00001074 - 0x0000159c is .text
        0x0000259c - 0x000025a0 is .eh_frame
        0x000025a0 - 0x000025a8 is .init_array
        0x000025a8 - 0x000025ac is .fini_array
        0x000025b0 - 0x000029d8 is .data
        0x000029d8 - 0x000029ec is .sdata
        0x000029ec - 0x000029f0 is .sbss
        0x000029f0 - 0x00002a0c is .bss

readelf -Wl add.elf
...
Program Headers:
  Type           Offset   VirtAddr   PhysAddr   FileSiz MemSiz  Flg Align
  LOAD           0x000000 0x00001000 0x00001000 0x0059c 0x0059c R E 0x1000
  LOAD           0x00059c 0x0000259c 0x0000259c 0x00450 0x00470 RW  0x1000
 
 Section to Segment mapping:
  Segment Sections...
   00     .text 
   01     .eh_frame .init_array .fini_array .data .sdata .sbss .bss 

输出清楚地表明,您关心的所有部分包含在第二个加载段中。

.bss 的结尾在 0x2a0c

如果我使用内存中 大小的第二段,我会得到 0x259c + 0x470 == 0x2a0c -- 完全 你的答案寻求.