后台开发核心技术(六)Linux内存空间布局

Linux运行中的C程序的内存空间布局
典型内存空间布局

  1. 代码段(.text segment)
    存放程序执行代码的一块内存区域,该区域大小在程序运行前就已经确定,通常属于只读。

  2. 初始化数据段(.data segment) (图中有误)
    通常用来存放已初始化的全局变量的一块内存区域。数据段属于静态内存分配。

  3. 未初始化的数据段(.bss segment)
    通常用来存放未初始化的全局变量的一块内存区域。

  4. 堆(heap)
    用来存放进程运行中被动态分配的内存段,大小并不固定。当进程调用malloc/free等函数分配内存时,新分配的内存就被动态添加到堆上或释放的内存从堆中被剔除。

  5. 栈(stack)
    又称堆栈,存放程序的局部变量(但不包括static声明的变量,static在数据段中存放变量)。除此之外,函数被调用时,栈用来传递参数和返回值。由于栈FILO特点,所以栈特别方便用于保存/恢复调用现场。

堆栈的区别

  1. 申请方式不同
    栈:由系统自动分配。
    堆:需要程序员自己申请,并指明大小。注意动态分配的指针本身在栈中,但是分配的区域在堆内。

  2. 申请后系统的相应不同
    栈:只要栈剩余空间大于申请空间,系统将提供内存,否则报异常,提示栈溢出。
    堆:OS有一个记录空闲内存地址的链表,当系统收到程序申请时会遍历该链表,寻找第一个空间中大于所申请空间的堆结点,将其从空闲链表中删除,并分配给程序。在这块内存空间中的首地址处记录本次分配的大小,这样delete才能正确释放。最后,由于找到的堆结点大小不一定等于申请大小,系统会自动将多余部分重新放回空闲链表中。

  3. 申请大小的限制不同
    栈:栈是向低地址扩展的数据结构,是一块连续的内存区域。用ulmit -a命令可以看到栈大小的限制。可以通过ulimit -s修改栈的大小。
    堆:堆是向高地址扩展的数据结构,是不连续的内存区域。这是由于系统是用链表来存储的空闲内存地址,而链表的遍历方向是由低地址向高地址。

  4. 申请效率不同
    栈:栈由系统自动分配,速度较快,但程序员无法控制。
    堆:堆由new分配,速度比较慢,容易产生内存碎片。

  5. 存储内容不同
    栈:在大多数的C编译器中,在函数调用时,第一个进栈的是当前函数后面的下一条指令的地址,然后是函数的各个参数(参数从右往左入栈,这是为了快速恢复),然后是函数中的局部变量。静态变量不入栈。当本次函数调用结束后,局部变量、参数、函数下一条指令依次出栈,程序由该点继续运行。
    堆:一般在堆头部用一个字节存放堆的大小,具体内容由程序员安排。

实例说明内存空间布局
源代码:
源代码1
源代码2
程序运行结果:
运行结果1
运行结果2

  1. 先分析全局变量的存储情况
    按照调用的顺序为全局变量g1,g2,g3,main中静态变量s1,s2,s3,以及max中静态变量n1_max,n2_max,n3_max。依次进行连续的静态内存分配,由低地址向高地址:
    全局变量
    main静态
    max静态
  2. 分析局部变量 的存储情况
    首先是main函数,在函数调用时,依次将函数地址,参数地址,以及变量入栈。需要注意的是,由于栈是向下扩展的,栈顶在上,栈底在下,新进来的数据地址逐渐变小:

参数地址
局部变量地址
然后是max函数:
参数地址
局部变量地址
通过比较main函数以及max函数也可以发现它们在栈中的相对位置。
需要特别注意栈是向低地址扩展的:堆栈向下扩展的说明(注意该博客中的图内存与本博客中相反)

  1. 动态内存的分配:
    与数据段中向高地址分配的方式类似。
    main中堆分配
    max中堆分配
  2. 函数运行代码的分配
    函数的地址相当于代码段,根据源码的顺序进行分配,因此也是向高地址扩展的。
    max地址
    main地址
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
后台开发核心技术与应用实践 作者:徐晓鑫 著 出版日期:2016年08月06日 封面宣传语:腾讯云平台技术总监黄世飞、Facebook对外支付项目主程张子兴、微软软件工程师彭可竞、阿里巴巴资深算法工程师周乐、百度大数据高级测试工程师畅晋联袂推荐;围绕后台开发需要掌握的核心技术,从多个方面、多个角度进行了阐述,覆盖了该领域的几乎所有内容;充分抓住本质并结合实践,文字通俗易懂,可操作性强 出版书名:后台开发核心技术与应用实践 作者:徐晓鑫 著 封底文字 专家评价 后台开发是一个“历史悠久”的领域,同时也是一个沉淀深厚,高技术价值的领域。本书清晰、严谨、务实的风格显示出晓鑫对该领域知识的深刻理解。 ——张子兴 Facebook对外支付项目主程,美国加州MenloPark 每一位从事后台开发的专业人士都需要一本后台开发指南。对每一位想要认真从事该领域工作的人来说,本书是一本绝对必读的书籍。 ——彭可竞 微软软件工程师,美国华盛顿州Redmond 本书是作者多年后台开发、架构和研究的精华。书中用通俗的文字、详尽的示例代码,结合实际工作中的案例,讲述了后台开发方方面面的知识,内容丰富。对于从事后台开发的人员,这是一本很好的由浅入深的学习书籍。 ——周乐 阿里巴巴资深算法工程师,北京望京 使用C++语言进行后台开发有一定的门槛,本书可以很好地帮助你跨过这个“门槛”。 ——畅晋 百度大数据高级测试工程师,北京上地 前勒口 互联网网民日益剧增,各种应用层出不穷,各项技术更新不断。单是游戏行业,近几年就经历了从端游、页游到手游的巨大变迁,客户端更新迭代之快,始料未及。而后台开发中使用到的技术,却变化不是很大。让服务性能更高、处理能力更强、安全性更好,是后台开发工程师永恒的主题。 后台开发中用到的技术,深而广,需要读的“大部头”很多,光是Richard Stevens的APUE,UNP,TCP/IP详解就够读个半年以上。读者通过阅读本书,可以从实践出发,快速由浅入深地进入后台开发领域。在读完本书,有了实践的经验之后,再去阅读大师们的著作,会更有体会,更懂得如何欣赏。 读书的最高境界莫过于“把书读薄,把书读厚”。本书文字通俗易懂,让你更快地“读薄”,同时又涉及较多的核心知识点,顺着这些知识点,读着读着也发觉“读厚”了。 后勒口 徐晓鑫,腾讯资深软件研发工程师,先后在腾讯游戏之洛克王国、QQ会员、QQ秀等项目工作,精通后台开发各种技术,实战经验丰富。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值