调用函数时使用栈空间保存各类信息。其过程大致如下:
①保存调用函数(function caller)的程序的运行状态和返回地址,将其压入栈内。
②将函数实参(引用除外)复制为副本(copy)后压入栈内,以便顶替形参来参加函数的运行。同时将各寄存器内容压入栈内。
③执行被调用函数的函数体内的语句。
④如有返回值,将该返回值(引用除外)复制为副本并压入栈内。接着传递给调用函数的程序。
⑤将各寄存器内容弹出栈,恢复调用函数的程序的运行状态,从而释放被占栈空间。
⑥按照返回地址将控制权交还给调用函数。 可见,调用函数时将增加时间开销和小量空间开销。
——————————————————————————————————————————
一、函数调用的基本步骤
函数调用大致包括以下几个步骤。
(1)参数入栈:将参数从右向左依次压入系统栈中。
(2)返回地址入栈:将当前代码区调用指令的下一条指令地址压入栈中,供函数返回时继续执行。
(3)代码区跳转:处理器从当前代码区跳转到被调用函数的入口处。
(4)栈帧调整:具体包括:
保存当前栈帧状态值,已备后面恢复本栈帧时使用(EBP入栈)。
将当前栈帧切换到新栈帧(将ESP值装入EBP,更新栈帧底部)。
给新栈帧分配空间(把ESP减去所需空间的大小,抬高栈顶)。