SetWindowsHookEx 用法的区别
Posted
技术标签:
【中文标题】SetWindowsHookEx 用法的区别【英文标题】:The Difference between to usages of SetWindowsHookEx 【发布时间】:2016-04-12 08:36:08 【问题描述】:首先:我在 Windows XP - 32 位上使用 Visual Studio 2010。
现在我正在尝试编写一个 DLL,该 DLL 将使另一个应用程序能够使用低级键盘挂钩。
即使我让它工作了 - 我现在想知道为什么。
非工作代码:
#include <Windows.h>
#include <stdio.h>
static HINSTANCE hinst;
static HHOOK kbdHook = NULL;
LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPARAM lParam)
printf(":"); fflush(stdout);
return CallNextHookEx(NULL, nCode, wParam, lParam);
DWORD WINAPI ThreadProc(LPVOID lpParameter)
MSG msg;
while (GetMessage(&msg, NULL, 0, 0))
TranslateMessage(&msg);
DispatchMessage(&msg);
return 0;
BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
switch (fdwReason)
case DLL_PROCESS_ATTACH:
hinst = hinstDLL;
CreateThread(NULL, 0, ThreadProc, NULL, 0, NULL);
kbdHook = SetWindowsHookEx(WH_KEYBOARD_LL, LowLevelKeyboardProc, hinst, 0);
break;
case DLL_PROCESS_DETACH:
UnhookWindowsHookEx(kbdHook);
break;
default:
break;
return TRUE;
工作代码:
#include <Windows.h>
#include <stdio.h>
static HINSTANCE hinst;
static HHOOK kbdHook = NULL;
LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPARAM lParam)
printf(":"); fflush(stdout);
return CallNextHookEx(NULL, nCode, wParam, lParam);
DWORD WINAPI ThreadProc(LPVOID lpParameter)
MSG msg;
kbdHook = SetWindowsHookEx(WH_KEYBOARD_LL, LowLevelKeyboardProc, GetModuleHandle(NULL), 0);
while (GetMessage(&msg, NULL, 0, 0))
TranslateMessage(&msg);
DispatchMessage(&msg);
return 0;
BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
switch (fdwReason)
case DLL_PROCESS_ATTACH:
hinst = hinstDLL;
CreateThread(NULL, 0, ThreadProc, NULL, 0, NULL);
break;
case DLL_PROCESS_DETACH:
UnhookWindowsHookEx(kbdHook);
break;
default:
break;
return TRUE;
唯一的区别是我将SetWindowsHookEx
-call 从DllMain
移到了ThreadProc
。
问题:为什么 这 会有所不同?
【问题讨论】:
***.com/questions/13874324/what-is-a-loader-lock 【参考方案1】:这在LowLevelKeyboardProc callback function的文档中都有解释:
这个钩子在安装它的线程的上下文中被调用。通过向安装钩子的线程发送消息来进行调用。 因此,安装钩子的线程必须有消息循环。
您的非工作代码将钩子安装在不运行消息循环的线程上。
【讨论】:
以上是关于SetWindowsHookEx 用法的区别的主要内容,如果未能解决你的问题,请参考以下文章