栈:
栈用于维护函数调用的上下文,离开了栈,函数调用就无法实现,栈向低地址增长。在整个栈帧的调用过程中,栈顶由称为esp的寄存器定位,栈底由ebp进行定位
栈帧一般包括下面几方面的内容:
- 函数返回地址的参数
- 临时变量
- 保存上下文–包括函数调用前需要保存不变的寄存器
- 把参数压入栈中
- 把当前指令的下一条地址压入栈中
- 跳转到函数体执行
- 把ebp压入栈(push ebp)
- 让ebp指向栈顶(mov ebp,esp)
- 恢复ebp同时回收局部变量空间(mov ebp,esp)
- 从栈中恢复保存的ebp的值(pop ebp)
- 从栈中取回返回地址,并跳转到该位置(ret)
我们通过一段简单的c语言程序 ,来简要的分析一下函数调用栈的详细情况:
#include<stdio.h>
int Add(int x,int y)
{
int z = 0;
z = x + y;
return z;
}
int main()
{
int a = 10;
int b = 20;
int ret = Add(a,b);
return 0;
}
在VC6.0编译器下,对代码进行反汇编,下面是整个过程的记录和解析:
建议在新标签页打开查看清晰图片