c++++ 函数调用约定随着平台和技术的演进而发展,从 __cdecl 到 __fastcall,再到 __thiscall 和 __vectorcall。现代编译器使用 x64 调用约定,它使用寄存器和栈根据参数大小传递参数,并由调用者负责清理栈。选择函数调用约定时,应考虑性能影响,根据函数规模和参数数量确定最合适的约定。
C++ 函数调用约定的历史演变和发展趋势
C++ 语言中函数调用约定描述了函数参数是如何在调用时在栈上传递的。不同的调用约定适用于不同的系统和平台,以优化性能和兼容性。
演变历史
- cdecl (Windows):参数从右至左压栈,最右边的参数最先压栈。函数返回时,从栈中弹出参数。
- stdcall (Windows):类似于 __cdecl,但调用者负责清理栈。
- fastcall (Windows):前两个参数放在 registers 中作为隐藏参数传递,其余参数压栈。
- thiscall (C++):第一个参数始终是隐式 this 指针,调用者负责清理栈。
- __vectorcall (x86-64__):使用 SIMD 寄存器传递四个或更多参数,从而提高性能。
发展趋势
现代编译器倾向于使用 x64 调用约定,因为它提供更高的性能和效率。x64 调用约定如下:
- 整数和浮点参数使用寄存器传递。
- 大于 16 字节的参数在栈上按需分配。
- 调用者负责清理栈。
实战案例
考虑以下 C++ 代码:
void add(int a, int b, int c) { int sum = a + b + c; // ... }
以下为使用不同调用约定的代码示例:
__cdecl
int main() { add(1, 2, 3); return 0; }
__stdcall
int main() { __stdcall add(1, 2, 3); return 0; }
x64
编译器将自动使用 x64 调用约定。
性能考虑
选择函数调用约定时,需要考虑性能影响。以下是一些准则:
- 对于经常调用的小型函数,x64 可能是最佳选择。
- 对于参数较多的大型函数,__stdcall 可能效率更高。
通过了解函数调用约定,开发者可以优化代码性能并确保跨平台兼容性。
以上就是C++ 函数调用约定的历史演变和发展趋势的详细内容,更多请关注知识资源分享宝库其它相关文章!
版权声明
本站内容来源于互联网搬运,
仅限用于小范围内传播学习,请在下载后24小时内删除,
如果有侵权内容、不妥之处,请第一时间联系我们删除。敬请谅解!
E-mail:dpw1001@163.com
发表评论