HOOK函数(二)——全局HOOK
如果钩子函数定义于当前进程相关的线程中,则钩子函数只能处理当前进程的线程的消息,如果要想处理当前正在运行的所有进程的鼠标消息和键盘消息,那么安装钩子函数的代码必须实现在动态链接库中。所以如果想让安装的钩子过程与所有进程相关,则应该讲SetWindowsHookEx函数的第四个参数设置为0,第三个参数hMod设置为安装钩子函数的代码所在的DLL的句柄。
下面是创建全局钩子的步骤:
1 创建一个名为GloabHookMFC的MFCDLL工程。
2 在GlobalHookMFC.cpp的开头声明钩子函数句柄、DLL模块句柄和窗口句柄
#pragma data_seg(".SHARDAT")
static HHOOK m_hMouseHook = NULL; //鼠标钩子句柄
static HHOOK m_hKeyBoardHook = NULL; //键盘钩子句柄
HWND g_hWnd = NULL; //窗口句柄
#pragma data_seg()
HINSTANCE hInstanceHandle; //DLL模块句柄
当DLL被多个进程使用时,这些进程可以共享DLL的代码和数据。因此在GloabHookMFC中定义了全局句柄变量g_hWnd,这个应该是被所有进程所共享的。#pragma data_seg(".SHARDAT")是在此DLL中创建一个节,此节为共享节,将g_hWnd放入其中能让此全部变量被多进程所共享。“.SHARDAT”是这个节的名称,这个字符串的最大长度限制为8字节,如果超过8个,系统自动截断为8个。一个新节的定义的最后必须以#pragma data_seg()结束,表明新节的结尾。需要注意的是,节中的变量必须初始化。
3 在 CGlobalHookMFCApp::InitInstance()中获取当前DLL模块的句柄
//获取DLL的句柄
hInstanceHandle = AfxGetInstanceHandle();
4 实现钩子函数
//鼠标钩子函数
LRESULT CALLBACK MouseProc( int nCode, WPARAM wParam, LPARAM lParam )
{
...
} //键盘钩子函数
LRESULT CALLBACK KeyBoardProc( int nCode, WPARAM wParam, LPARAM lParam )
{
...
}
5 添加钩子
extern "C" _declspec(dllexport) BOOL SetMouseHook( )
{
if (hInstanceHandle == NULL)
return FALSE; m_hMouseHook = SetWindowsHookEx(WH_MOUSE, MouseProc, hInstanceHandle,);
if (m_hMouseHook)
return TRUE;
else
return FALSE; } extern "C" _declspec(dllexport) BOOL SetKeyboardHook()
{
if (hInstanceHandle == NULL)
return FALSE; m_hKeyBoardHook = SetWindowsHookEx(WH_KEYBOARD, KeyBoardProc, hInstanceHandle,); if (m_hKeyBoardHook)
return TRUE;
else
return FALSE;
} extern "C" _declspec(dllexport) BOOL StartAllHook(HWND hwnd)
{
g_hWnd = hwnd;
return SetMouseHook() && SetKeyboardHook();
}
6 卸载钩子
extern "C" _declspec(dllexport) BOOL StopMouseHook()
{
return UnhookWindowsHookEx( m_hMouseHook );
} extern "C" _declspec(dllexport) BOOL StopKeyHook()
{
return UnhookWindowsHookEx(m_hKeyBoardHook);
} extern "C" _declspec(dllexport) BOOL StopAllHook()
{
return StopKeyHook() && StopMouseHook();
}
7 编译生成GlobalHookMFC.DLL。
8 我们在新建一个基于对话框的MFC工程GlobalHookTestDlg。在其头文件GlobalHookTestDlg.h中加入
#pragma comment(lib, "GlobalHookMFC.lib")
extern "C" _declspec(dllimport) BOOL StopAllHook();
extern "C" _declspec(dllimport) BOOL StartAllHook( HWND hwnd);
9 在BOOL CGlobalHookTestDlg::OnInitDialog()中添加钩子
BOOL CGlobalHookTestDlg::OnInitDialog()
{
... // TODO: 在此添加额外的初始化代码
if (StartAllHook(GetSafeHwnd()))
MessageBox(_T("全局钩子启动成功"),NULL, MB_OK);
else
MessageBox(_T("全局钩子启动失败"),NULL, MB_OK); return TRUE; // 除非将焦点设置到控件,否则返回 TRUE
}
10 在CGlobalHookTestDlg::OnSysCommand()中卸载钩子
void CGlobalHookTestDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
...
StopAllHook();
}
编译运行后,当我们双击右键的时候会弹出显示当前窗口名称的对话框,当我们敲击键盘时候会弹出显示当前按下键的对话框。结束之后一定要记得卸载钩子。
最新文章
- Opencv VideoCapture实时捕捉摄像头信息
- Monk快速开发框架前期约定
- 【iOS】关联属性存取数据
- 解决Package illuminate/html is abandoned, you should avoid using it. Use laravelcollective/html instead.问题
- linux服务器默认连接数配置
- addEvent和removeEvent优化写法
- UIWebView弹出键盘按钮显示中文
- Wpf再次学习,分享给入门的朋友
- hdu 4465 Candy
- 【译】神经网络与深度学习 Ch1-Section0
- Oracle GoldenGate学习之Goldengate介绍
- boost.xml_parser中文字符问题
- intelliJ IDEA自动优化导入包设置
- 【js】项目中有关时间的问题
- html 标签学习(续)
- Spring MVC基础知识整理➣数据校验与格式化
- 【洛谷p1605】迷宫
- cobbler自动安装操作系统
- 关于ASP.NET Web API的ModelBinding杂谈
- BEGIN-4_蓝桥杯_Fibonacci数列