我使用CBT钩子创建了一个DLL来挂起一些事件。它似乎只适用于启动钩子的进程创建的窗口.
我的系统是Windows7 x64,但x32上的行为也是一样的。
这是代码(对不起,我不是C++专家):
#include "windows.h"
extern "C"
{
static LRESULT CALLBACK CbtProcCb(int nCode, WPARAM wParam, LPARAM lParam);
HINSTANCE g_hDll = NULL;
HWND g_hNotifyWin = NULL;
DWORD g_uNotifyMsg = NULL;
HHOOK g_hHook = NULL;
__declspec(dllexport) HHOOK SetCbtHook(HWND hWnd, LPCWSTR lStrMsg, DWORD threadId)
{
g_hNotifyWin = hWnd;
g_uNotifyMsg = RegisterWindowMessage(lStrMsg);
g_hHook = SetWindowsHookEx(WH_CBT, (HOOKPROC)CbtProcCb, g_hDll, threadId);
return g_hHook;
}
__declspec(dllexport) int UnsetCbtHook()
{
if ( !g_hHook )
return 0;
return UnhookWindowsHookEx(g_hHook);
}
}
static LRESULT CALLBACK CbtProcCb(int nCode, WPARAM wParam, LPARAM lParam)
{
SendNotifyMessage(g_hNotifyWin, g_uNotifyMsg, nCode, wParam); // Send nCode to check the received event
return CallNextHookEx(g_hHook, nCode, wParam, lParam);
}
BOOL APIENTRY DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
{
if ( fdwReason == DLL_PROCESS_ATTACH )
g_hDll = hinstDLL;
return true;
}有什么暗示吗?
发布于 2013-12-03 21:24:52
当Windows安装globals钩子时,实现钩子函数的DLL通常加载在其他进程中。在这些过程中,g_hNotifyWin和g_uNotifyMsg全局变量为NULL。该全局变量仅在发生SetCbtHook调用的过程的上下文中不为空。
您必须有一种方法在任意进程中检索g_hNotifyWin和'g_uNotifyMsg‘的正确值。
添加:
const char * g_pszClassName = "MyClassName";
const char * g_pszRegisteredMsg = "MyMessage";并将"MyClassName“替换为g_hNotifyWin窗口的类名。请参阅EXE中的RegisterClass调用。更新也是"MyMessage“。
然后,使用以下CbtProcCb函数:
static LRESULT CALLBACK CbtProcCb(int nCode, WPARAM wParam, LPARAM lParam)
{
if ( nCode >= 0 ) {
if ( g_hNotifyWin == NULL ) g_hNotifyWin = FindWindow( g_pszClassName, NULL );
if ( g_uNotifyMsg == 0) g_uNotifyMsg = RegisterWindowMessage(g_pszRegisteredMsg);
if ( g_hNotifyWin && g_uNotifyMsg )
SendNotifyMessage(g_hNotifyWin, g_uNotifyMsg, nCode, wParam); // Send nCode to check the received event
}
return CallNextHookEx(NULL, nCode, wParam, lParam); // first arg useless see MSDN
}编辑:,正如您在注释中所指出的,g_uNotifyMsg的相同问题参见更新的函数。您确实可以在DllMain中设置这些变量。
CallNextHookEx的第一个参数可能为NULL。
发布于 2013-12-03 20:26:24
我猜您的ThreadId不是零,所以钩子只分别附加到调用进程/线程。阅读文档:http://msdn.microsoft.com/en-us/library/windows/desktop/ms644990(v=vs.85).aspx
https://stackoverflow.com/questions/20359189
复制相似问题