“跨进程子类化”的问题

时间:2010-10-16 16:34:00

标签: winapi hook global subclassing cross-process

两个问题。

1)我明白这一定是预期的结果,但也许有人可以告诉我我做错了什么;我正在尝试将所有窗口类子类化为全局钩子并且它工作,除了我无法按照我应该关闭商店,当程序最初注册钩子时注销钩子并退出,子类应用程序开始崩溃。

以下是我试图做的事情..

// stores original wndprocs. In the hook dll, outside the shared memory.
map<HWND, WNDPROC> origWndProcs;

// in an EnumWindows callback, executed for all HWND's, also in the hook dll (UWM_REMOVE_HOOK is a registered unique message)
SendMessageTimeout(hWnd, UWM_REMOVE_HOOK, 0, 0, SMTO_ABORTIFHUNG | SMTO_NORMAL, 15000, res);

// Still in the same hook, in the subclassing wndproc..
if (msg == UWM_REMOVE_HOOK) {
   if (origWndProcs.find(hwnd) != origWndProcs.end()) {
      SetWindowLongPtr(hwnd, GWL_WNDPROC, (LONG_PTR)origWndProcs[hwnd]);
   }
}

// clears the hook..
__declspec(dllexport) BOOL ClearHooks(HWND hWnd) {

    BOOL unhooked = UnhookWindowsHookEx(hook) &&
       UnhookWindowsHookEx(kb_hook) &&
       UnhookWindowsHookEx(mouse_hook) && 
       UnhookWindowsHookEx(cbt_hook);

    if(unhooked)
       hWndServer = NULL;
    return unhooked;
}

在DllMain中,我没有对DLL_PROCESS_DETACH做任何事情。相反,ClearHooks()是从最初注册钩子的程序中调用的,只有在钩子发送了一条消息后才发出信号表明它已经执行了EnumWindows操作(恢复原始的wndproc,见上文)。

我在WndProc钩子中子类化窗口;接收消息并且当前wndproc不是dll中的所有可见窗口都是子类。

基本上所有(据我所知)应用程序在退出时崩溃,尽管windows似乎确实将wndproc设置恢复到更换时的状态。任何人都知道我可能做错了什么?

2)我需要这个来拦截WM_MINMAXINFO并在窗口最大化时修改窗口maxsize。不幸的是我不能在dll中这样做,但我必须与程序交谈以获取大小信息。那么,与窗口交谈的最佳方式是什么?我需要它传回一些信息,以便我可以修改原始WM_MINMAXINFO消息附带的结构。在调用SendMessageTimeout之前,WM_COPYDATA中的结构是否会保留它的数据?

由于

1 个答案:

答案 0 :(得分:0)

这里有很多痛点。您假设没有其他代码将子类化窗口。并且这样的代码将以正确的顺序对其进行非子类化。没有正确的顺序,你的挂钩与程序的执行非常不同。

但是,解决方法很简单。您已经使用SetWindowsHookEx挂钩了,不妨再做一次。 WH_CALLWNDPROC或WH_CALLWNDPROCRET,取决于您想要做什么。