那些年“错过”的C函数调用原理(三)

这篇是 C 函数调用原理的最终篇,如果错过前面的铺垫知识可以翻看前面两篇文章。

C 函数的返回过程是 C 函数调用过程的逆过程,所以理解了 C 函数调用过程后返回过程就比较容易理解。

步骤 1 和步骤 2 的 leave 指令做了两个任务:重置 esp 并将它指向到当前栈帧开始的地方,另一个是恢复在 ebp 中保存的值。这两个操作在逻辑上是独立的,因此,在图中将它们分开来说。

在 leave 运行后,恢复了前一个栈帧。add 函数调用唯一留下的东西就是在栈顶部的返回地址。它包含了运行完 add 函数之后在 main 函数中必须运行的指令的地址。

ret 指令用来处理它:它弹出返回地址到 eip 寄存器(32 位的指令寄存器),这个寄存器指向下一个要执行的指令。现在程序将返回到 main 函数,主要部分如下:

main 函数从 add 函数中拷贝返回值到本地变量 answer,然后,运行它自己的结语epilogue,这一点和其它的函数是一样的。最后一步执行的是,返回到 C 运行时库(libc),它将退回到操作系统中。

C 函数调用原理的讲解到此结束,至此,总算踏完了第一步,心里顿时舒畅了许多。。。

在最后说一下写这三篇文章的感受:文章本身并不花什么时间,花时间的是之前的资料收集和整理。要弄懂一个概念也需要查看很多资料,而且为了严谨需要参考很多国外的论坛博客和官方文档,对于我这个英语渣渣看得还是蛮累的(虽然有谷歌翻译减少了工作量,但是翻译准确度还有待提高)。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容