程序对内存的分配(部分内容)

一.理论讲解(针对32位操作系统)

  •  内存具体分配

  1. 32位操作系统,每个操作系统都有2^32字节的虚拟地址空间,即4G的虚拟地址空间。这4G的虚拟地址空间分为两个大部分:每个进程独立的3G的用户空间(栈、堆、静态存储区、代码段),和所有进程共享的1G的内核空间。

  2. 图上呈现出来的内容的地址是逻辑地址(虚拟地址),若要对应真正内存中物理地址,需要使用MMU(内存管理单元,可将逻辑地址映射为物理地址),利用分页式、分段式存储方式的运算进行转化。

  • 栈区

  1. 是存放函数调用时临时信息的结构,包括函数调用时传递参数,函数返回地址,函数局部变量
  2. 存放自动变量(int a = 3),用时自动申请,用完自动释放 -----各种类型变量,int,char,指针类型等
  3. 先进后出
  • 堆区

  • 静态存储区

  1. 静态存储区分为3个部分:bbs,rwdata,rodata
  2. bbs:存放未初始化的静态局部变量和未初始化的全局变量(也可以认为未初始化的全局变量放在rwdate中
  3. rwdata(可读可写数据段):存放初始化后的全局变量(其实也可以认为存放全局变量,未初始化的全局变量其实被系统默认为初始化为0,与初始化为0的全局变量一样)、初始化后的静态局部变量、初始化后的静态全局变量
  4. rodata(只读数据段):存放字符串常量(但不止)
  • 代码段text

  1. 只读,存放程序执行代码

二.代码验证

建议在Linux环境下运行

代码

#include <stdio.h>

int g_init = 100;
int g_uninit;
static int sg_init = 200;
static int sg_uninit;

void fun()
{
    int l_init = 100;
    int l_uninit;
    static int sl_init = 200;
    static int sl_uninit;

    printf("l_init:   %-8p\n", &l_init);//初始化局部变量
    printf("l_uninit: %-8p\n", &l_uninit);//未初始化局部变量

    printf("g_init:   %-8p\n", &g_init);//初始化全局变量
    printf("sg_init:  %-8p\n", &sg_init);//初始化静态全局变量
    printf("sg_uninit:%-8p\n", &sg_uninit);//未初始化静态全局变量
    printf("g_uninit: %-8p\n", &g_uninit);//未初始化全局变量

    printf("sl_init:  %-8p\n", &sl_init);//初始化静态局部变量
    printf("sl_uninit:%-8p\n", &sl_uninit);//未初始化静态局部变量

    printf("rodata    %-8p\n", "helloworld");//字符串常量
    printf("text      %-8p\n", fun);//函数代码段
}

int main()
{
    fun();
    return 0;
}

运行结果

猜你喜欢

转载自blog.csdn.net/qq_42420263/article/details/86574970