我可以挂钩任何其他函数,但不能挂起ExitProcess。
以下是演示此内容的代码:http://pastebin.com/EzHGMe8K
它调用了hooked函数,但是当NewExitProcess返回时,我得到了一个访问冲突。对Sleep的调用很好,就像除ExitProcess之外的任何钩子函数一样。
编辑:我在挂钩ExitThread时遇到了同样的问题。
答案 0 :(得分:-1)
查找ExitProcess的函数声明时,您会发现类似这样的内容:
WINBASEAPI
DECLSPEC_NORETURN
VOID
WINAPI
ExitProcess(
_In_ UINT uExitCode
);
有趣的部分是DECLSPEC_NORETURN
,定义为__declspec(noreturn)
。它也是ExitThread
函数使用的属性,也会导致崩溃。 Looking up on the docs,我们发现:
此__declspec属性告诉编译器函数不返回。因此,编译器知道调用__declspec(noreturn)函数后的代码无法访问。
根据您的发现,它不仅用于禁用编译器警告,还用于优化。这也解释了为什么它可以在调试模式下工作。
我无法想到一个很好的解决方案,因为你正在与优化器作斗争。您在评论中写的解决方案对我不起作用(VS2013,发布模式,/ O2)。我想出了一些有点傻的东西,但它似乎为我做了这个工作:
int *ptr = (int*)&ExitProcess;
ptr++;
ptr--;
((VOID (WINAPI*)(UINT))ptr)(0);
一般情况下,挂起另一个未知程序的ExitProcess应该总是退出当前线程,因为它可能被编译为没有任何代码可以返回。