free()之后内存会怎样?

问题描述 投票:7回答:4

我知道在硬盘驱动器上,如果删除文件,数据不会(立即)消失。数据仍然存在,直到被覆盖。我想知道内存中是否存在类似的概念。假设我为一个字符串分配了256个字节,在free()之后,该字符串是否仍在内存中浮动,直到被覆盖为止?

c memory dynamic-memory-allocation free
4个回答
5
投票

通常,它确实存在,除非您在free之前显式覆盖字符串(就像人们有时使用密码一样)。一些库的实现会自动覆盖释放的内存以捕获对其的访问,但是在释放模式下不会这样做。


6
投票

您的类比是正确的。内存中的数据不会消失或类似的东西;尽管尝试从已释放的内存中进行读取是未定义的行为,但free()之后的值实际上确实仍然存在。


4
投票

答案在很大程度上取决于实现。在一个好的实现中,很可能至少内存的开始(或结尾?)会被簿记信息覆盖,以跟踪空闲的内存块,这些内存块稍后可以重用。但是细节会有所不同。如果您的程序具有任何级别的并发性/线程(甚至在您可能看不到的库实现中),那么此类内存可能会被异步破坏,甚至可能甚至读取它也是危险的。当然,free的实现可能会完全从程序的虚拟地址空间中取消映射地址范围,在这种情况下,尝试对其执行任何操作都会使程序崩溃。

[从应用程序作者的角度出发,您应该仅根据规范对待free,并且永远不要访问释放的内存。但是从系统实现者或集成者的角度来看,了解(或设计)实现可能会很有用,在这种情况下,您的问题就很有趣。


2
投票

如果要验证实现的行为,下面的简单程序将为您完成此操作。

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

/* The number of memory bytes to test */
#define MEM_TEST_SIZE 256

void outputMem(unsigned char *mem, int length)
{
    int i;

    for (i = 0; i < length; i++) {
        printf("[%02d]", mem[i] );
    }   
}

int bytesChanged(unsigned char *mem, int length)
{
    int i;
    int count = 0;

    for (i = 0; i < MEM_TEST_SIZE; i++) {
        if (mem[i] != i % 256)
            count++;
    }
    return count;
}

main(void)
{
    int i;
    unsigned char *mem = (unsigned char *)malloc(MEM_TEST_SIZE);

    /* Fill memory with bytes */
    for (i = 0; i < MEM_TEST_SIZE; i++) {
        mem[i] = i % 256;
    }

    printf("After malloc and copy to new mem location\n");
    printf("mem = %ld\n", mem );
    printf("Contents of mem: ");
    outputMem(mem, MEM_TEST_SIZE);

    free(mem);
    printf("\n\nAfter free()\n");
    printf("mem = %ld\n", mem );
    printf("Bytes changed in memory = %d\n", bytesChanged(mem, MEM_TEST_SIZE) );
    printf("Contents of mem: ");
    outputMem(mem, MEM_TEST_SIZE);


}
© www.soinside.com 2019 - 2024. All rights reserved.