blog

枪手亨利

博客园 首页 新随笔 联系 订阅 管理

系统勾子的编程实例
   编写系统勾子与编写线程勾子的步骤相似,不过必须把勾子函数放在DLL中。因此,读者需要了解编写动态链接库的基础知识。这里的例子实现一个系统级的键盘勾子,监视系统中所有应用的键盘输入消息并记录在文件中。这样需要两个工程,一个是主程序,一个是动态链接库。

  (1)在DLL中定义键盘勾子函数。

  在VC++6.0中利用MFC APPWizard(DLL)生动态链接库工程keyhook。然后选择DLL 的类型为使用共享MFC DLL的常规DLL。打开 keyhook.cpp文件,加入全局说明:

#pragma data_seg(“SharedVar")
//DLL输出的全局变量
extern "C" __declspec(dllexport) HHOOK hHook=NULL;
#pragma data_seg()
// DLL 自用的全局变量
char buffer=0;
FILE *fl;
定义全局的键盘勾子函数:
//DLL输出的勾子函数
extern "C" __declspec(dllexport)
LRESULT CALLBACK KeyboardProc(
  int nCode,      
  WPARAM wParam,  //虚键代码
  LPARAM lParam   // 击键消息的信息
)
{
 if(lParam&0x80000000) 
 {//如果某键按下
 buffer=MapVirtualKey(wParam,2);
    // 把虚键代码变为字符
 //输出到文件
 fl=fopen( “keyfile.txt", “a+" );
 fwrite(&buffer, sizeof(char), 1, fl);
 fclose(fl);
 }
 return CallNextHookEx(hHook,nCode,wParam,lParam);
}

  编译得到keyhook.dll和库文件keyhook.lib 。使用 keyhook.lib是为了让主程序可以方便地隐式调用DLL中的输出函数。

   (2)在VC++6.0中利用MFC APPWizard(EXE)生成一个不使用文档/视结构单文档应用getkey。打开MainFrm.cpp文件。加入全局的输入变量和函数的说明:

//要从DLL中输入的变量和函数
extern "C" __declspec(dllimport) HHOOK hHook;//
extern "C" __declspec(dllimport)
LRESULT CALLBACK  KeyboardProc
(int nCode, WPARAM wParam, LPARAM lParam);

  (3)在CMainFrame类的构造函数中安装勾子。

CMainFrame::CMainFrame()
{
 hHook=SetWindowsHookEx(WH_KEYBOARD,
 KeyboardProc,
 GetModuleHandle(“keyhook.dll"),
 0);
}

  (4)在CMainFrame类的析构函数中卸载勾子。
CMainFrame::~CMainFrame()
{
    if(hHook)
      UnhookWindowsHookEx(hHook);
}

  编译这个工程的时候,注意包含第一步得到的库文件 keyhook.lib。keyhook.dll和getkey.exe应放在同一目录下运行。  

posted on 2006-01-03 21:57  henry  阅读(3345)  评论(0)    收藏  举报