2

我越来越

*** 检测到 glibc *** (/my/program/...): malloc(): 内存损坏: 0xf28000fa ***

我在 valgrind 下运行过,它报告了已释放的读取内存的情况,但没有非法内存写入的情况。

读取释放的内存会导致内存损坏吗?如果没有,还有什么建议可以超越 valgrind 输出?

4

6 回答 6

5

您可以使用 GDB 来观察此内存地址中的每次写入,如下所示:

(gdb) watch *((int*)0xf28000fa)

然后就可以调试问题出在哪里了。

读取不会导致内存损坏,但是在很多情况下您甚至都无法想象这可能是造成这种情况的原因,而且 Valgrind 并不是一个完美的工具。

在此处查看有关调试内存问题的更多信息。

于 2010-07-03T18:26:49.350 回答
2

它不会破坏您读取的内存,但不会对您的程序的工作产生奇迹。

于 2010-07-03T18:21:46.903 回答
1

读取释放的内存也被认为是内存损坏。

您还可以查看http://en.wikipedia.org/wiki/Memory_corruption

于 2010-07-03T18:28:40.047 回答
1

不,读取无效位置不可能导致您看到的错误。如果该位置在您的地址空间中有效,那么您将只是在阅读垃圾邮件,否则,您将遇到分段错误。

检查 valgrind 的输出以查看无效读取的来源 - 这将为您提供真正错误所在的提示。一旦你找到这个,我很确定真正的罪魁祸首不会很远,而且很可能是无效写入。

于 2010-07-03T18:37:22.050 回答
1

它在当前处理器上不应该那么常见,但我曾在甚至读取操作都可以发挥作用的平台上工作。在特定的 6502 处理器中映射了 I/O,因此具有 I/O 映射地址的常规“读取”指令可以做令人惊讶的事情。

大约 30 年前,我被它所困扰,因为我的错误读取引发了内存库切换(即内存的每个字节,包括包含代码的区域,在该指令之后得到一个新的不同值)。有趣的是,它并不是真正的“无意”错误阅读……即使我知道这将是垃圾,我也确实阅读了,因为这为我节省了一些汇编指令……这不是一个聪明的举动。

于 2010-07-03T19:11:39.683 回答
0

真正会发生的是,free 可以使用 madvise(MADV_DONTNEED) 系统调用告诉内核“我不需要这个页面,删除它”(参见 madvise(2) 手册页)。如果该页面真的被释放并且您从中读取任何内容,内核将默默地提供全新的页面,将其归零 - 从而导致您的应用程序遇到完全意外的数据!

于 2010-07-03T19:23:56.120 回答