内存管理:一个函数在栈上到底是怎样的?

函数的调用和栈是分不开的。

栈帧/活动记录

当发生函数调用时,会将函数运行需要的信息全部压入栈中,这常常被称为栈帧(Stack Frame)或活动记录(Activate Record)。
活动记录一般包含以下几个方面:

1.函数的返回地址,也就是函数执行完成后从哪里开始执行后面的代码。

```
int a, b, c;
func(1, 2);
c = a + b;
```

func()函数执行完毕后,会继续执行c = a + b;语句,那么返回地址就是该语句在内存中的地址。

2.参数和局部变量。有些编译器会通过寄存器来传递参数,而不是将参数压入栈中。

3.编译器自动生成的临时数据。例如,当函数返回值的长度较大时,会先将返回值压入栈中,然后再交给函数调用者。

当返回值的长度较小(char, int, long等)时,不会被压入栈中,而是先将返回值放入寄存器,再传递给函数调用者。

4.一些需要保存的寄存器,例如ebp,ebx等。之所以保存寄存器的值,是为了在函数退出时能够恢复到函数调用之前的场景,继续执行上层函数。

关于数据的定位

esp的值是变化的;ebp的值是固定的,数据相对ebp的偏移也是固定的,ebp + 偏移量 = 数据地址

原文地址:https://www.cnblogs.com/xiaobaizzz/p/12343362.html