sbrk,malloc - 可以分配的最大内存

时间:2014-11-02 12:34:45

标签: c linux

我试图弄清楚可以使用malloc()为进程分配多少最大内存。

所以要点是:

start = sbrk(0);
malloc(1); /* so space is given to the data segment */
end = sbrk(0); /* start != end at this point */

/* Try to allocate in chunks as much as possible. */
while (end == sbrk(0)) {
    malloc(1048576);

    if (end == sbrk(0)){
        maxMemory = maxMemory + 1048576;
    }
}

return maxMemory;

所以我不明白的是:

如果你这样做:

start = sbrk(0);
malloc(1);
end = sbrk(0);

好的,结束!=开始

但是:

start = sbrk(0);
malloc(1048576);
end = sbrk(0);

开始==结束

因此,基本上,程序中断(sbrk(0))不会移动较大的值。因此给定的while会持续很长时间,直到sbrk(0)被移动并且我得到一个非常大的Max值~68gb。

我希望任何malloc最初会移动数据段,但它不会。有人可以解释为什么它没有(那么它在哪里分配?)和/或我做错了什么?

1 个答案:

答案 0 :(得分:3)

glibc malloc implementation使用mmap()为更大的块分配:

  

通常,malloc()从堆中分配内存,并调整   使用sbrk(2)根据需要填充堆的大小。分配块时   内存大于MMAP_THRESHOLD字节,glibc malloc()   实现将内存分配为私有匿名映射   使用mmap(2)。 MMAP_THRESHOLD默认为128 kB,但可以调整   使用mallopt(3)。使用mmap(2)执行的分配不受影响   通过RLIMIT_DATA资源限制(参见getrlimit(2))。

可以使用mallopt()设置M_MMAP_THRESHOLD来调整此阈值,但请注意,默认情况下,较新版本的库会动态调整此阈值:

  

注意:现在,glibc默认使用动态mmap阈值。该   阈值的初始值是128 * 1024,但是当块更大时   比当前阈值小于或等于   释放DEFAULT_MMAP_THRESHOLD_MAX,向上调整阈值   到释放块的大小。当动态mmap阈值处于。时   效果,修剪堆的阈值也是动态的   调整为动态mmap阈值的两倍。动态调整   如果任何M_TRIM_THRESHOLD,则禁用mmap阈值,   设置了M_TOP_PAD,M_MMAP_THRESHOLD或M_MMAP_MAX参数。