繁体   English   中英

free() 后堆中断不会改变吗?

[英]Heap break will not change after free()?

代码:

int main() {
    printf("entering main. %p\n", sbrk(0));

    void* ptr = malloc(300 * 1024);
    memset(ptr, 0xBE, 300 * 1024);
    printf("Allocated memory. %p\n", sbrk(0));
    free(ptr);
    printf("Freed memory. %p\n", sbrk(0));

    void* ptr1 = malloc(300 * 1024);
    memset(ptr1, 0xBE, 300 * 1024);
    printf("Allocated memory. %p\n", sbrk(0));
    free(ptr1);
    printf("Freed memory. %p\n", sbrk(0));

    void* ptr2 = malloc(300 * 1024);
    memset(ptr2, 0xBE, 300 * 1024);
    printf("Allocated memory. %p\n", sbrk(0));
    free(ptr2);
    printf("Freed memory. %p\n", sbrk(0));

    printf("exiting main. %p\n", sbrk(0));
}

Output:

entering main. 0x2403000
Allocated memory. 0x2424000
Freed memory. 0x2424000
Allocated memory. 0x246f000
Freed memory. 0x246f000
Allocated memory. 0x246f000
Freed memory. 0x246f000
exiting main. 0x246f000

Strace 片段(排除的库加载):

 0.000064 [00007fc92fa32f19] brk(NULL) = 0x2403000
 0.000033 [00007fc92fa2cd34] fstat(1</dev/pts/33>, {st_dev=makedev(0, 14), st_ino=36, st_mode=S_IFCHR|0620, st_nlink=1, st_uid=60141191, st_gid=5, st_blksize=1024, st_blocks=0, st_rdev=makedev(136, 33), st_atime=2022/08/11-11:19:36.874073993, st_mtime=2022/08/11-11:19:36.874073993, st_ctime=2022/08/11-10:34:22.874073993}) = 0
 0.000084 [00007fc92fa32f19] brk(0x2424000) = 0x2424000
 0.000026 [00007fc92fa2d3c0] write(1</dev/pts/33>, "entering main. 0x2403000\n", 25) = 25
 0.000040 [00007fc92fa377ba] mmap(NULL, 311296, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fc92fead000
 0.000200 [00007fc92fa2d3c0] write(1</dev/pts/33>, "Allocated memory. 0x2424000\n", 28) = 28
 0.000034 [00007fc92fa37847] munmap(0x7fc92fead000, 311296) = 0
 0.000042 [00007fc92fa2d3c0] write(1</dev/pts/33>, "Freed memory. 0x2424000\n", 24) = 24
 0.000052 [00007fc92fa32f19] brk(0x246f000) = 0x246f000
 0.000200 [00007fc92fa2d3c0] write(1</dev/pts/33>, "Allocated memory. 0x246f000\n", 28) = 28
 0.000031 [00007fc92fa2d3c0] write(1</dev/pts/33>, "Freed memory. 0x246f000\n", 24) = 24
 0.000033 [00007fc92fa2d3c0] write(1</dev/pts/33>, "Allocated memory. 0x246f000\n", 28) = 28
 0.000043 [00007fc92fa2d3c0] write(1</dev/pts/33>, "Freed memory. 0x246f000\n", 24) = 24
 0.000030 [00007fc92fa2d3c0] write(1</dev/pts/33>, "exiting main. 0x246f000\n", 24) = 24
 0.000036 [00007fc92fa027c8] exit_group(0) = ?

正如我们所见,当 memory 被分配时,堆中断增加(strace 显示第一次分配由 mmap 完成,也由 munmap 释放,第二次分配由 brk 完成。没有第三次分配。)。

但是当调用 free() 时,我没有看到堆中断减少。

我想知道这种行为的原因。 是不是像 kernel 没有释放 memory 以防将来分配该过程?

如果是,有没有办法在任何 kernel 设置释放后强制释放堆?

不使用标准 C。 glibc 你可以使用malloc_trim function。

https://man7.org/linux/man-pages/man3/malloc_trim.3.html

您可以使用mallopt function 设置阈值。

如果您设置mallopt(M_TRIM_THRESHOLD, 0)您的程序将在您使用 free 时将 memory 释放到系统(不完全是 - 一些 memory 仍将保留)

考虑以下场景:您在酒店预订了 1 天的房间,然后在返回关键时刻后,您想再次预订房间。 现在有可能您可以预订到与前一个不同的房间。

free并不意味着下次如果您致电malloc它将为您提供旧地址。 它只是通知memory management system您不再需要之前分配的 memory。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM