【问题标题】:GDB: how to see what memory addresses are accessible?GDB:如何查看可以访问的内存地址?
【发布时间】:2010-09-21 11:30:29
【问题描述】:

假设,在调试会话中,我有一个地址不幸指向一些垃圾。我想检查它周围的记忆,看看附近有什么。不出所料,出现以下错误:

(gdb) x/64 $t5
0x842da7ac:     Cannot access memory at address 0x842da7ac

所以,问题是:有没有办法读取地址范围,其中一些是无效的?

(更准确地说,我怎么知道在上面的示例中$t5+n 是某些0 < n <= 64 的有效地址?)

【问题讨论】:

    标签: debugging memory assembly gdb postmortem-debugging


    【解决方案1】:

    您无法读取无效地址(显然)。

    在某些操作系统上,您可以在 GDB 中停止进程时向操作系统查询有效地址。例如,在 Linux 上,cat /proc/<pid>/maps 将为您提供有关哪些地址有效(以及它们有效的访问模式)的信息。其他操作系统可能有类似的机制。

    由于您标记了您的问题post-mortem,因此您不能使用上述机制;但是你必须有一个core 文件。在 Linux(和其他 ELF 系统)上,readelf -l core 会告诉您哪些内存区域已写入内核,这通常可以让您很好地了解崩溃时哪些内存是有效的。但是,只读映射通常不会写入core,因此您可能在readelf 输出中看不到此类映射。

    所有现代操作系统都使用分页,并且页面至少为1K(尽管4K 更常见),因此您可以看出最接近$t5 的可能有效的内存是0x842da800,并且所以n >= 84(字节)。

    最后,如果你让 GDB 检查 64 个单词,而 GDB 不能检查第一个,它就会停止。

    但是,如果您使用的是 GDB-7.x,您可以让 GDB 在 Python 中一次检查一个单词,如果 GDB 无法检查该特定单词,它将抛出 Python 异常。但是由于您可以捕获 Python 异常,因此编写一个脚本来实现“检查接下来的 N 个单词,忽略任何不可读的单词”在 Python 中是微不足道的(我相信这可以回答您的“如何做到这一点”的问题)。

    【讨论】:

    • 在gdb内部,可以使用maintenance info sections,而不是cat /proc/<pid>/maps
    • 不,你不能:/proc//maps 显示区域,例如 sbrk 和 mmap,它们属于 GDB 知道的任何部分。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-09-08
    • 1970-01-01
    • 1970-01-01
    • 2013-10-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多