使用 malloc 时,如果它生成带有错误的核心转储:

malloc(): memory corruption: ....... ***

这是否意味着 malloc 尝试分配无法自由分配的内存?如果是的话,造成这种情况的原因是什么?

有帮助吗?

解决方案

它完全取决于你的malloc实现,但通常这意味着在malloc之前的某个时刻某些东西会向malloced缓冲区写入比其大小更多的数据。

许多malloc实现将他们的一些数据与内存一起存储,换句话说:

+--------------------------------+
|14 bytes -> Padding             | 
+--------------------------------+
|2 bytes -> Internal malloc info |
+--------------------------------+
|6 bytes -> Your data            |
+--------------------------------+
|8 bytes -> Padding              |
+--------------------------------+
|2 bytes -> Internal malloc info |
+--------------------------------+

因此,如果您的某些代码或库向该6字节缓冲区写入16个字节,则会覆盖填充和内部malloc信息的2个字节。下次你调用malloc时,它会尝试遍历它的数据来查找空间,点击被覆盖的空间,因为你覆盖它会破坏堆,这将是荒谬的。

根据实施情况,这样的错误也可能是由于双重免费造成的。

其他提示

最有可能的是,这不是malloc本身的问题。相反,这是您的应用程序修改堆不应该的部分的问题。

如果您在Linux上运行,请尝试使用 Valgrind 查看哪些代码正在破坏您的堆。

通常的原因是你写了数据,malloc()没有给你写权限 - 缓冲区溢出(写入超出你给出的空间的末尾)或缓冲区欠载(写入开始之前)缓冲区)。

有时可能是由释放malloc()等未分配的指针,或者重新释放(双重释放)由malloc()分配的指针引起的。例如,释放静态缓冲区是一个坏主意;你会受到腐败。

您应该假设问题出现在您的代码中 - 它在malloc()等中极不可能出现问题,而且不太可能出现在您正在使用的任何其他库中。

堆损坏的常见原因有以下几种:

  • 超出内存分配(写入超过分配块的末尾)
  • 双重释放块
  • 释放指针后使用它
  • 当然,通过与先前分配无关的指针(“内存命中”或流氓指针)错误地写入一些内容 - 这是包括上述所有内容的一般情况。

这些问题可能很难调试,因为原因和结果通常被时间和空间(不同的代码区域)分开。因此,直到导致问题的错误执行后很久(以计算机时间计)过去,该错误才会被注意到。

使用调试堆对于调试这些问题非常有帮助。微软的编译器有一个 Crt调试堆 在调试版本中启用(但可以设置其他配置项)。我不确定 GCC 有什么现成的,但有一些我顺便熟悉的工具,例如 Valgrind 和电围栏 这可能有帮助。终于有一大堆 自行开发的堆调试库 这可能会有所帮助(谷歌周围)。

你能提供你的malloc()声明吗?

另外,我想仔细检查返回值是否为空?

除了没有开始分配的内存之外,我在使用 malloc() new 时遇到的问题类似于你提到的实际结果一个损坏的堆。我经常发现一些“有趣”的东西。程序中的其他代码执行像memcpy()这样的东西,其中包含一个字符缓冲区导致缓冲区溢出和错位的地址空间。

-bn

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top