堆栈帧的组织——C/C++内存管理必须掌握
程序栈
说到堆栈帧,你得先说说程序栈。
记忆功能程序堆栈区是支持操作,通常共享堆。
程序栈通常占领内存区域的下部,而堆用的是上部。
程序栈存放栈帧,栈帧有时候也称为活跃记录或活跃帧。栈帧存放函数參数和局部变量。堆存放动态内存。
调用函数时,函数的栈帧被推到栈上。栈向上长出一个栈帧。
当函数终止时,其栈帧从程序栈上弹出。
栈帧所使用的内存不会被清理,可是终于可能会被推到程序栈上的还有一个栈帧覆盖。
动态分配的内存来自堆。堆向下生长。随着内存的分配与释放。堆中会布满碎片。
虽然堆是向下生长的,可是这仅仅是大体方向,实际内存可能位于堆上的任何位置。
栈帧的组织
栈帧由以下几个元素组成:
返回地址:函数完毕后要返回的程序内部地址
局部数据存储:为局部变量分配的内存
參数存储:为函数參数分配的内存
栈指针和基指针:执行时系统用来管理栈的指针
栈指针通常指向栈顶部。基指针通常存在并指向栈帧内部的地址,比方返回地址,用来协调訪问栈帧内部的元素。
这两个指针都不是C指针,他们是执行时系统管理程序栈的地址。
以下这个函数给出实例:
float average(int *arr, int size){
int sum;
printf("arr: %p\n",&arr);
printf("size: %p\n",&size);
priintf("sum: %p\n",&sum);
for(int i = 0;i < size;i ++){
sum +=arr[i];
}
return (sum *1.0f) / size;
}
//output
//arr: 0x500
//size: 0x504
//sum: 0x480
当中參数地址和局部变量之间的空档。保存的是执行时系统管理栈所需的其它栈帧元素。
系统在创建栈帧时,将參数以跟声明时相反的顺序推到栈上,最后推入局部变量。在这个样例中,size在arr之后被推入。通常,接下来会推入函数调用的返回地址。然后是局部变量。推入它们的顺序和在代码中的顺序相反!
从原理上说,本例中的栈向上生长。只是栈帧的參数和局部变量以及新栈帧被加入到了低内存地址。
栈的实际生长方向和实际相关。
for语句中的i没有包括在栈帧中。这是由于C语言中把块语句当成“微型”函数。
将栈帧推到程序栈上时,系统可能会耗尽内存,这样的情况叫做栈溢出,一般会导致程序非正常终止。要牢记住每个线程都有自己的程序栈,一个或多个线程访问存储器中的同一个对象可能会造成冲突。
版权声明:本文博客原创文章,博客,未经同意,不得转载。
堆栈帧的组织——C/C++内存管理必须掌握的更多相关文章
- 深入C#内存管理来分析值类型&引用类型,装箱&拆箱,堆栈几个概念组合之间的区别
C#初学者经常被问的几道辨析题,值类型与引用类型,装箱与拆箱,堆栈,这几个概念组合之间区别,看完此篇应该可以解惑. 俗话说,用思想编程的是文艺程序猿,用经验编程的是普通程序猿,用复制粘贴编程的是2B程 ...
- C++ 内存管理与堆栈
/*内存管理与堆栈: * # 一个由C/C++编译的程序占用的内存分为以下几个部分 * 1.栈区:由编译器自动分配释放,数据先进后出 * 2.堆区:由程序员手动分配释放,数据先进先出, * new 和 ...
- JMM内存管理
原文地址http://www.cnblogs.com/BangQ/p/4045954.html 原本准备把内存模型单独放到某一篇文章的某个章节里面讲解,后来查阅了国外很多文档才发现其实JVM内存模型的 ...
- How Javascript works (Javascript工作原理) (三) 内存管理及如何处理 4 类常见的内存泄漏问题
个人总结: 1.两种垃圾回收机制: 1)引用标记算法:如果检测到一个对象没有被引用了,就清除它. ***这种算法不能处理循环引用的情况*** 2)标记—清除算法:从根(全局变量)开始向后代变量检测,任 ...
- JavaScript 工作原理之三-内存管理及如何处理 4 类常见的内存泄漏问题(译)
原文请查阅这里,本文有进行删减,文后增了些经验总结. 本系列持续更新中,Github 地址请查阅这里. 这是 JavaScript 工作原理的第三章. 我们将会讨论日常使用中另一个被开发者越来越忽略的 ...
- Linux堆内存管理深入分析(上)
Linux堆内存管理深入分析(上半部) 作者:走位@阿里聚安全 0 前言 近年来,漏洞挖掘越来越火,各种漏洞挖掘.利用的分析文章层出不穷.从大方向来看,主要有基于栈溢出的漏洞利用和基于堆溢出的漏洞 ...
- 深入了解C#系列:谈谈C#中垃圾回收与内存管理机制
今天抽空来讨论一下.Net的垃圾回收与内存管理机制,也算是完成上个<WCF分布式开发必备知识>系列后的一次休息吧.以前被别人面试的时候问过我GC工作原理的问题,我现在面试新人的时候偶尔也会 ...
- 简单的例子 关于Java内存管理的讲解
我想做的是,逐行读取文件,然后用该行的电影名去获取电影信息.因为源文件较大,readlines()不能完全读取所有电影名,所以我们逐行读取. 就这段代码,我想要在位置二处使用base64,然后结果呢? ...
- Erlang 虚拟机 BEAM 指令集之内存管理相关的指令
翻看 BEAM 虚拟机指令集的时候(在编译器源码目录下:lib/compiler/src/genop.tab),会发现有一些和内存分配/解除分配相关的指令,如下所示: allocate StackNe ...
随机推荐
- 关于Smartforms换页的
smartforms中有系统变量SFSY-PAGE是总页码,SFSY-FORMPAGES是当前页,可以最后的窗体中做个判断 1.把窗体设置成最终窗体 2.新增一个命令,当前页等于最后一页才输出改内容, ...
- TCP/IP笔记 二.网络层(1)
1. IP 1.1 配套协议 IP 是 TCP/IP 体系中两个最主要的协议之一 . 与 IP 协议配套使用的还有四个协议: (1)ARP (Address Resolution Protocol ...
- WordPress数据备份
服务器钱用光了要关了或者是服务器想要搬家,需要备份各种数据. 今天简单的备份了一下在服务器上面wordpress各种文件和资源. wordpress的数据主要分两个部分,一个是文字部分的:一个是附件部 ...
- 深入研究Clang(四) Clang编译器的简单分析
作者:史宁宁(snsn1984) 首先我们确定下Clang编译器的详细内容和涵盖范围.之前在<LLVM每日谈之二十 Everything && Clang driver>中 ...
- Linux经常使用命令(十一) - more
more命令,功能类似 cat ,cat命令是整个文件的内容从上到下显示在屏幕上. more会以一页一页的显示方便使用者逐页阅读,而最主要的指令就是按空白键(space)就往下一页显示,按 b 键就会 ...
- String,StringBuffer与StringBuilder差异??
String 字符串常量StringBuffer 字符串变量(线程安全)StringBuilder 字符串变量(非线程安全) 简要地, String 类型和 StringBuffer 类型的主要性能差 ...
- android binder机制之——(创建binder服务)
Binder机制编程 前面的几篇文章具体介绍了android中binder机制的方方面面,相信你对binder机制已经有了较深刻的理解.俗话说得好"学以致用",以下我们就通过在 ...
- [C#基础] 类
类成员 字段和方法是最重要的类成员类型,字段是数据成员,方法是函数成员 字段 字段是隶属于类的变量 它可以是任何类型,无论是预定义类型还是用户定义类型 和所有变量一样,字段用来保存数据 它们可以被写入 ...
- C语言函数调用约定
在C语言中,假设我们有这样的一个函数: int function(int a,int b) 调用时只要用result = function(1,2)这样的方式就可以使用这个函数.但是,当高级语言被编译 ...
- QT 4.2.2的安装(安装完还要再编译,注意设置Windows Path)
(安装篇)前奏: 提到C++的GUI Framework估计大多数人都会想到MFC.VCL,因为在十年前的COM时代,这两个大家伙几乎垄断了整个C++ windows平台上应用程序的开发市场, 但是最 ...