c - malloc() 和堆内存

标签 c memory

我在以下 C 代码中得到了一个奇怪的结果。

int main()
{
    int *p = (int *) malloc(100);
    p[120] = 5;
    printf("\n %d", p[120]);
}

因为我只分配了 100 个字节,这段代码应该会导致段错误。但是,它会打印“5”并且不会给出任何运行时错误。谁能解释一下原因?

最佳答案

不,代码不应(必然)出现段错误。当您尝试访问未分配给您的进程的虚拟内存页面时,会发生段错误。

“堆”或“自由存储”是您的进程拥有的虚拟内存页面区域。 malloc() API 将该区域 segmentation 为 block 并返回指向该 block 的指针。

如果您的地址超出了您拥有指针的 block 的末尾,您通常会访问属于堆的一部分的内存,而不是您分配的 block 的一部分。通过这种方式,您可以破坏其他堆 block 甚至 malloc() 用于定义堆的数据结构。

有关堆损坏的更多信息,以及在代码的调试版本中检测它的方法,这是一本很棒的书:

Writing Solid Code: Microsoft's Techniques for Developing Bug-Free C Programs by Steve Maguire alt text

Nerd 的补充:在极少数情况下,通过访问堆 block 末尾以外的内存,您可能会访问不属于堆的内存。在这些情况下,您可能会遇到预期的段错误。您可能还会破坏堆之外的其他一些数据结构。这真的是一个机会问题。但是,与典型的堆 block 相比,堆本身非常大,因此 99% 的时间代码(例如您的示例)都会损坏堆。您提供的示例属于 99% 的情况。

关于c - malloc() 和堆内存,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1751322/

相关文章:

将 uint8_t 数组复制到结构

c - 在 C 的 OpenSSL 中以 DER 格式打印 DH 参数

arrays - 从函数返回字符串时需要澄清

c - 解引用迭代器性能

linux - ptrace suid 进程(在它放弃特权之后)

memory - cudaMemcpy 传输种类 : Default vs HostToDevice/DeviceToHost

c - 2d-array- arr[][0] 是什么意思?

c - 多进程多线程的同步问题

c - 是什么导致服务器一遍又一遍地读取客户端的最后一条消息?

calloc -- 清零内存的用处