malloc与free
malloc与free是C语言标准库中的函数,用于动态内存分配与释放。
malloc
C语言中的标准库函数,存在于头文件<stdlib.h>中。
函数声明为: void* malloc(size_t size)。
作用:为开辟一块size大小的内存空间,如果分配成功则返回指向这块空间的指针,分配失败则返回空指针NULL。
free
也是C语言中的标准库函数,存在与头文件<stdlib.h>中。
函数声明为: void free(void *ptr)。
作用:将分配给指针ptr指向区域的内存空间进行回收。
这里的ptr必须已经被malloc或者realloc,calloc类型的函数调用过,否则会产生未定义行为。
如果free(ptr)已经被调用过,重复调用也会产生未定义行为。
如果ptr为NULL,不执行任何操作。
实现原理
malloc以及free可以有多种实现方式,并且没有一种方法是完美的,因为我们需要在速度,开销和避免碎片/空间有效性之间做出折衷。
简单来说,我们把进程中一个从x到y的内存区域称为「堆」。所有malloc函数分配的内存会存在这个区域中。malloc会维护一个数据结构,我们干脆简化为一个链表,其中含有内存块的「元信息」,以及真正存放数据的「内存块区域」。当我们调用malloc的时候,它会遍历这个列表寻找有没有合适大小的未分配的内存块,如果有的话,将其指针返回,并且标记这块内存已经被分配了;如果没有的话,它会使用sbrk()这个系统调用来扩大堆区域,也就是说增加y的值(注意这里sbrk一定是一个系统调用,我们不可能从用户空间去改变堆的大小)。并且,这里的y是不能无限制增长的,在Linux中有一个变量RLIMIT_DATA用来限制进程中数据区(data segment,包括初始化数据,未初始化数据以及堆)的最大值。当堆区增长到最大限度后,再调用sbrk就会报ENOMEM错误。
|