美文网首页
3. 内存管理——基础知识

3. 内存管理——基础知识

作者: 郑行_aover | 来源:发表于2018-12-18 14:32 被阅读0次

    内存管理和内存分配是操作系统需要重点考虑的问题。以下简单的的写下内存相关的知识。

    内存主要分为五个区域:静态区(.data段、.bss段)、文字常量区、代码区(.text)、堆(.heap)、栈(.stack)。

    在实际编程中,要时刻注意变量所在的内存区域,以及其生命周期,避免出现内存错误问题。

    1. 数据段-.data

    数据段属于静态分配内存

    ——有初值的全局变量、static变量

    2. bss段

    未初始化的全局变量,或者初始化为0的全局变量,此区域在程序载入时候由内核清0.属于静态分配内存

    ——未初始化的全局变量

    3. 代码段.text

    text段在内存中被映射为只读

    ——可执行代码,字符串常量

    4. heap段

    动态分配的内存,保存程序的动态变量,堆是先进先出FIFO。

    ——由malloc、calloc、realloc等函数,手动分配的内存空间

    注意:malloc申请的内存不负责初始化,而calloc申请的内存已经初始化为0. realloc可以扩充之前申请的内存。

    堆的地址空间向上生长,即堆上保存的数据越多,堆的地址就越高。

    5. stack段

    栈保存函数的局部变量,参数,以及返回值。是一种后进先出的数据结构。最后放到栈上的数据,将会是最先从栈上移走的数据。

    ——局部变量、参数、返回值。

    栈的生长方向为向下生长,当栈上保存的数据越多,栈的地址就越低。


    PS:从存储区域来看:

    ——寄存器:    速度最快,由编译器来分配。

    ——堆栈:         堆栈就是栈(stack)。是一种特别快、特别有效的数据保存方式,仅次于寄存器。

    ——堆:            手动分配固定大小的内存区域,编译器不知道其生命周期和空间大小,更灵活。但是分配存储空间会花掉时间。

    从存储方式来看:

    ——静态存储:数据存活于整个程序的生命周期。全局变量以及static数据

    ——常量存储:常数值通常置于程序代码内部。这样是十分安全的,因为text段是只读的,所以永远也不会改变。有需要保护的常数,可以将其通过const来修饰。


    那么,linux下的虚拟地址空间如何分布?

    ——只读段:         代码段、rodata段(常量字符串,#define定义的常量)

    ——数据段:        保存全局变量、静态变量的空间

    ——堆        :        动态内存,通过malloc、calloc、realloc、new等来分配的内存。堆顶的位置可以通过brk和sbrk进行动态调整

    ——文件映射区域:    动态库、共享内存等映射物理空间的内存。mmap等函数所分配的虚拟地址空间

    ——栈        :        用于维护函数调用上下文空间、一般为8M, 可以通过 ulimit -s 查看。    

    ——内核虚拟空间:用户不可见的内存区域,由内核管理(页表存放在内核空间)    

    参看此链接文章——linux环境内存分配原理 mallocinfo

    由于虚拟内存的存在,系统整理内存称为可能。即使系统内存整理调整后,虚拟内存的地址不会变,各个线程的栈内存也应该不会发生变化,只是每个内存页对应的物理内存发生变化。

    相关文章

      网友评论

          本文标题:3. 内存管理——基础知识

          本文链接:https://www.haomeiwen.com/subject/crzkkqtx.html