Sin*_*ame 1 c winapi pointers function
我正在尝试编写一个函数,该函数从我传递给它的结构指针中获取 MessageBoxA 的地址,然后使用该地址调用 MessageBoxA。问题是我尝试用这种方法调用 MessageBoxA 5 次,但我的程序总是在 3 次后崩溃,我不知道为什么。
void code(struct ShellD * s)
{
    s->pMsgBox(NULL,"s","s",MB_OK);
    s->pMsgBox(NULL,"s","s",MB_OK);
    s->pMsgBox(NULL,"s","s",MB_OK);
    s->pMsgBox(NULL,"s","s",MB_OK);
    s->pMsgBox(NULL,"s","s",MB_OK);
}
int main(int argc, char **argv)
{
struct ShellD SD;
SD.pMsgBox = GetProcAddress(LoadLibraryA("user32.dll"),"MessageBoxA");
code(&SD);
}
pMsgBox 定义为 int (*pMsgBox)(HWND,LPCSTR,LPCSTR,UINT);
您已经WINAPI从 的声明中删除了MessageBoxA:
int
WINAPI // <--
MessageBoxA(
    __in_opt HWND hWnd,
    __in_opt LPCSTR lpText,
    __in_opt LPCSTR lpCaption,
    __in UINT uType);
pMsgBox 应该是这样的:
int (WINAPI *pMsgBox)(HWND,LPCSTR,LPCSTR,UINT)
有什么不同?
Windows API 函数使用stdcall调用约定(也称为 Pascal 调用约定)。stdcall函数的特性之一是它们会清理传入的任何参数所使用的堆栈空间。
相比之下,在默认的cdecl调用约定中,调用代码会为它传入的任何参数清理堆栈空间。
通过在 的声明中使用错误的调用约定,您pMsgBox的code()函数和MessageBoxA()函数都在移动堆栈指针以删除传递的参数,并且在几次之后您可能已经将堆栈指针移出当前堆栈帧,然后被覆盖堆栈上的其他东西,例如返回函数指针。这可能是导致崩溃的原因。
| 归档时间: | 
 | 
| 查看次数: | 78 次 | 
| 最近记录: |