C/C++函数调用过程

为了更好的分析,举一个简单的例子,即在main函数中调用add函数

int add(int a,int b){
return a+b;
}

int main(){
int a=1;
int b=2;
int c=add(a,b);
d=3;
}

将函数进行反汇编可以得到

 add():
        push    rbp
        mov     rbp, rsp
        .....
        pop     rbp
        ret
main():
        push    rbp
        mov     rbp, rsp
        .....
        call    add()
        nop
        pop     rbp
        ret

要弄懂这段汇编程序,必须先明白两个寄存器的含义:
在这里插入图片描述
然后需要弄清楚栈的结构,即栈低位于高地址部分,栈顶位于低地址部分,栈是向下生长的。如下图所示:
在这里插入图片描述

 add():
        push    rbp
        mov     rbp, rsp
        .....
        pop     rbp
        ret
main():
        push    rbp
        mov     rbp, rsp
        .....
        call    add()
        nop
        pop     rbp
        ret

下面,我将一条一条指令的执行:
push rbp:
1.现将rsp中的值减去2个字节
2.将上一个栈帧的栈底基地址保存到新的栈帧中。
保存调用函数的rbp的原因:
1.rbp需要存储新的栈帧的基地址
2.记住上一个栈帧的基地址,用于后续恢复

mov rbp,rsp
1.将rsp中的地址赋值给rbp,使得rbp=rsp。
2.rbp中现在存储main函数栈帧的栈底基地址

call add()
1.将rip指向下一条指令
2.将rip指向的指令的内存地址入栈,即call指令的返回地址
3.rip指令指向被调用方法add的第一条指令

pop rbp
1.将rbp设置为它当前指向内存中的地址,退回到上一个栈帧的栈底基地址
2.rsp往回退一个元素

ret指令
1.将rip设置为rsp指向的内容,即指main函数中add指令的下一条d=3这条指令。

详细请观看B站up主-资深程序员老汤-的视频
函数调用如何实现?

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值