进程探寻之内存分布

来源:互联网 发布:java io read write 编辑:程序博客网 时间:2024/06/05 05:20

UNIX系统中进程都会占用4G虚拟内存。4G虚拟内存又被分成不同的内存区域,用于完成不同的程序功能。本文将详细介绍进程中不同区域的功能,既内存分布情况。
用户空间与内核空间
4G虚拟内存可分为两大部分——用户空间与内核空间。用户空间占用3G内存空间,是0x00000000到0xbfffffff的内存区域。内核空间占用1G内存空间,是0xc0000000到0xffffffff的内存区域。内核空间保存内核的代码与数据。这是用户不可操作的区域,任何对其的读取与写入操作都会导致程序的崩溃。尽管用户不可以直接操作内核空间,但可以通过系统调用间接操作内核空间。内核空间包含了大量指令,这其中包含了一系列有用的函数。这些函数可以完成各种不同的系统任务。这些函数便是系统调用对应的内核函数。调用系统调用便是调用对应的函数。用户空间保存了程序的代码与数据,是用户可以操作的内存区域。用户空间又可详细区分为代码段,数据段,堆,栈。

#include <stdio.h>int main(int argc,char **argv){    char *p=(char *)0xc0000000;    char ch=*p;    printf("ch = %d\n",ch);    return 0;}

代码段
程序的所有指令都保存在代码段中,代码段不仅可以看成是指令的集合,也可以看成是函数的集合。代码段是可读,可执行的,但不能写入。

数据段
全局变量和静态变量全都保存在数据段中。数据段又可分为初始化数据段和未初始化数据段。数据段可读,可写。


栈是函数调用的基本,是非常重要的内存区域。
在UNIX中,栈默认占用8M内存空间。当栈使用超出8M内存时,将导致程序崩溃。我们可以使用setrlimit系统调用调整栈的默认大小。
每个进程初始化时,操作系统都会将命令行参数和环境变量添加到栈中。(参考execve系统调用)内核会申请128KB的内存存放命令行参数和环境变量。内核按照图一的方式在栈中存放命令行参数和环境 。存放完成后,栈顶指针指向argc的内存区域。

这里写图片描述


在数据段与栈之间存在着一块非常巨大的内存区域——堆。堆主要用于动态分配内存。malloc和free函数便是使用该内存区域。

0 0
原创粉丝点击