即使我超越分配的内存限制也没有错误?

7 c

我可能是愚蠢的,在这种情况下你需要原谅我...但我不明白这一点.我正在分配一个16个字符的缓冲区然后(在一个for循环中)放入23个(!?)随机字符,然后打印出那些东西.

我没有得到的是如何将23个字符放入一个malloc为16个字符的缓冲区...当我将循环更改为24个字符时,我得到一个错误(至少在Linux中使用gcc)... .但为什么不"更早"(17个字符应该打破它......不?)

这是我的示例代码:

#include <stdio.h>
#include <stdlib.h>

int main()
{
    int n;
    char *buf;

    buf = malloc(16 * sizeof(*buf));
    if(buf == NULL) exit(1);

    for(n = 0; n < 22; n++)
    {
        buf[n] = rand()%26+'a';
    }
    buf[n]='\0';

    printf("Random string: %s\n", buf);

    free(buf);
    buf = NULL;

    getchar();
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

Mic*_*urr 6

你正在产生一个错误,但像许多错误一样,它恰好不会被注意到.这里的所有都是它的.

这可能是由于以下几个原因之一 - 可能是免费存储的结构方式,分配之间存在松弛的空间,因为系统需要(或希望)保持可分配块的地址在某些边界上对齐.因此,稍微写一下你分配的块不要干扰免费存储数据结构,但是它们会更进一步.

很可能你的bug确实破坏了免费商店经理正在使用的东西,但它恰好没有在你的简单程序中实际使用,所以错误没有被注意到(尚未).

  • 为了澄清 - OP可能用于更高级别的语言,这些错误被捕获.C故意不安全,C中的这种行为被标准称为"未定义行为",这意味着代码可以做任何事情.大多数时候,它会做最简单的事情,也就是忽略了这样一个事实:你不能写入那个空间并且无论如何都要这么做.这是C很难的主要原因 - 当你做错事时,没有什么可以检查你. (5认同)

Joh*_*ler 3

大多数内存分配策略都会将 malloc 请求舍入到某个量化值。通常为 16 或 32 字节。这种量化通常发生在分配器添加其开销(用于跟踪分配的块)之后,因此通常会发现您可以使 malloc 溢出一些少量的字节,而不会对堆造成任何实际损坏,尤其是当分配大小为奇数时。

当然,这不是您想要依赖的东西,它是 c 运行时库的实现细节,如有更改,恕不另行通知。