Unix中C程序内存布局

C程序在进程中分为代码片段(text segment)、初始化数据片段(initialized data segment)、未初始化数据片段(uninitialized data segment)、栈(stack)以及堆(heap)。其内存分布如图1所示

图1.  C程序运行时内存布局

  • 代码片段往往是只读内容,为进程运行提供必要的操作步骤。
  • 初始化数据片段包含C代码中明确初始化了的变量值。
  • 未初始化数据片段(又称为bss段),包含C代码中未明确初始化的变量,该片段中数据在程序启动时被全部重置为0(按位全部填充为0)。
  • 栈用于存储程序运行时的自动局部变量(automatic variables)、函数调用信息等。由于函数调用栈中表现为向低地址增长函数链,当出现递归调用时,函数链被拉长,自动局部变量被存储为一个新的变量,因此,递归调用从内存分布上来说产生了一个新的函数,函数中的变量不会相互干扰。
  • 堆用于存储在程序运行时动态申请内存空间的变量。

ISO C标准中有三种方式可以动态申请内存空间(在堆中):

  • 调用malloc函数,指明申请空间大小。申请后将不进行初始化操作,因此使用malloc函数申请到的内存片段中值为未知量。
  • 调用calloc函数,指明申请单元大小及申请单元个数。申请后将对该内存片段按位形式赋0。
  • 调用realloc函数,扩大或缩小已动态申请过的内存片段大小。

当不再使用该内存片段时,需要使用free函数对该内存片段予以释放,以免造成内存泄,降低程序性能。其函数原型为

#include <stdlib.h>

void *malloc( size_t size );
void *calloc( size_t nobj, size_t size );
void *realloc( void *ptr, size_t newsize );

void free( void *ptr );

 

使用realloc函数增加内存片段时,如果没有适当的空闲内存片段与之相邻,系统会将申请一个新内存片段,并把原有内存片段中的数据复制到新片段中,将原有内存片段释放,返回新地址。如果原有内存片段地址呗其他变量保存,并在realloc调用后使用,将引起内存调用错误(内存地址被改变)。

posted @ 2012-07-09 15:56  o0慢节奏0o  阅读(427)  评论(1编辑  收藏  举报