Q
何时使用调用约定
6
A
回答
12
大多数时候你不需要担心它。通常你会使用__cdecl
,但只是因为这是Visual C++中的默认值。但是,C++成员函数在默认情况下使用Visual C++
当您将回调传递给API函数(如Windows API中的函数)时,您确实需要担心调用约定的一种(相当常见的)情况:
// CALLBACK is #define'd as __stdcall
LRESULT CALLBACK MyWndProc(HWND hwnd, UINT msg
WPARAM wParam, LPARAM lParam);
// ...
windowClass.lpfnWndProc = &MyWndProc;
::RegisterClass(&windowClass);
在这里,我们声明MyWndProc()
作为具有__stdcall
约定(CALLBACK
是#define
倒是如__stdcall
)。这是因为操作系统期望lpfnWndProc
指向WNDPROC
,which uses the CALLBACK
convention。
几乎所有的Windows API,它接受一个回调函数需要回调函数使用__stdcall
惯例,而且由于__cdecl
通常是默认的,你必须更加明确,(你会使用CALLBACK
的窗口过程)。
这非常重要,因为如果操作系统尝试调用非__stdcall
函数,则可能会发生堆栈损坏。不幸的是,足够的人得到这个错误Windows will actually check for calling convention mismatch specifically for window procedures。
虽然__stdcall
需要传递给WinAPI的函数回调函数,接受的参数个数可变必须使用__cdecl
调用约定,因为只有调用者将知道如何正确地弹出可变数量的参数从堆栈功能。由于__cdecl
通常是默认值,因此您无需为接受可变数量参数的函数明确指定__cdecl
。
我个人还没有找到用于__fastcall
,虽然我确定有人有。
__clrcall
仅在您与托管代码进行交互时才有用。
相关问题
- 1. 如何使用Delphi中的“_pascal调用约定”调用dll?
- 2. ASM调用约定
- 3. 使用DLL调用约定错误
- 4. Objective C约定:何时使用For和何时使用With
- 5. 如何指定vc11 lambda调用约定
- 6. 使用套接字时函数调用约定的建议
- 7. x86 linux系统调用调用约定?
- 8. 使用调用约定fastcall的任何实际用例?
- 9. c中的调用约定
- 10. std :: sort&comp - 调用约定?
- 11. 在C++/CLI调用约定
- 12. 的Delphi thiscall调用约定
- 13. GCC cdecl调用约定
- 14. Char vs int调用约定
- 15. 调用约定错误 - C
- 16. 调用`〜`与前缀约定
- 17. 函数调用约定
- 18. Sparc程序调用约定
- 19. std :: function如何知道调用约定?
- 20. 如何使用BOOST获得函数调用约定?
- 21. 如何使用__cdecl调用约定编译boost?
- 22. API使用约定
- 23. 调试坏DLL调用约定错误
- 24. 确定何时调用使用jQuery
- 25. 使用nodejs时的JavaScript命名约定
- 26. 使用'this'和function.apply时接受约定
- 27. C++如何调用不支持的调用约定
- 28. C++自定义调用约定
- 29. 什么是自定义调用约定?
- 30. 为什么使用错误的调用约定有时会起作用?