
游戏插件通常分为三个级别: 主要级别是鼠标和键盘模拟,中间级别是Call游戏内部功能,读写内存,高级级别是数据包捕获,以及“离线挂起”数据包(完全模拟客户端网络数据,无需运行游戏). 用C#编写的插件很少,其中大多数是C ++. 主要原因是MS C#当前不支持内联汇编. 因此,用C ++编写基础库然后用C#调用它已成为DONET爱好者开发插件的首选.
单击此处下载演示
单击此处查看“拳皇”的“ Iori”小特效.
对于鼠标和键盘模拟的插件,许认为没有技术上的内容,因为它只不过是SendMessage或Key_event,而更高级的一点是Hook进入了程序的内部操作. 我还使用了这项技术来开发一些游戏辅助程序. 但是最近我在研究XNA时遇到了一些麻烦,这种经过实践检验的方法实际上失败了. 游戏根本不“服从”消息命令. 我们有一个问题: 它如何识别真实键盘的按键?该程序有判断力吗?
如果您忽略上述问题,请换个角度思考. 在DOS时代,您还记得经典的Debug命令来删除BIOS密码吗?原理是使用BIOS中断. 实际上,对于键盘按键,无论Windows如何打包,都会调用BIOS中断以最后识别按键. 但是,消息发送毕竟是Windows系统的事情. 无论在Windows级别上如何判断,我们只需要让BIOS下一个“神圣法令”,看看哪个游戏敢于如此傲慢! ! !
在更详细地解释该原理之前,让我们首先抓住幕后的黑手,看看哪个人在支持游戏?让它有胆量违抗Windows message命令. 是判断实际的键盘信息还是其他原因?结果,我在DirectX编程中找到了DirectInput API. 它绕过Windows的消息机制,其目的是使游戏的实时控制更好,更快. Windows消息以队列的形式出现,并且传输过程中会有延迟. 例如,格斗游戏对实时控制有很高的要求,而窗口消息机制不能满足这一要求. 而且DirectInput直接与键盘驱动程序打交道,当然,效率要高得多. 我认为大多数游戏不响应消息的真正原因是在这里,而不是故意编写反作弊系统.
现在我们知道DirectInput正在解决问题,我们应该怎么做?前面我们提到了一个小想法,所以最实用的方法是直接读写键盘端口以模拟硬件事件. 在DOS时代,每次按下一个键都会产生键盘中断,因此程序将跳至BIOS中的键盘中断以处理程序执行. 当时,我最好的X是QBasic程序. QBasic中有一个OUT函数可以将数据写入指定的端口,而INP函数可以从指定的端口读取数据. 因此,使用QBasic进行硬件级键盘模拟非常简单.
如果此键的扫描代码为0x51,则首先模拟按下此键:
OUT&H64,&HD2'将数据0xD2发送到端口0x64.
OUT&H60,&H51'将扫描代码0x51发送到端口0x60,这意味着模拟按下扫描代码0x51的键
让我们模拟一下再次释放该按钮:
OUT&H64,&HD2'将数据0xD2发送到端口0x64.
OUT&H60,(&H50 OR&H80)'或扫描代码0x50和数据0x80,这意味着释放密钥.

当然,DOS时代已经过去了,但是我只是提到了QBasic的强大功能. 如果真的使用QBasic编写模拟程序,则它可以在Win98下成功,但在Win2000之后不能成功,因为DOS只是进入NT时代后的虚拟机系统.
现在的问题非常清楚,即如何在Windows环境中执行端口操作. 由于级别较低,Windows无法让您如此轻松地成功. 通常有两种方法: 一种是使用驱动程序,而在驱动程序中还不能做些什么?第二种是使用“呼叫门”从Ring3跳到Ring0以执行相关操作. 在Internet上进行搜索应找到相关信息. 我听说Grid表示有一个名为“ Key Wizard”的VB,它看起来相当不错. 下载并研究它之后,我发现它使用了外国人的WINIO驱动程序的原理. 使用WINIO更加容易,因为我的驾驶能力确实是&* ^%$ ^&*.
因此,在WINIO的基础上,我使用C#进行了一个简单的辅助软件包,使其适合在DONET平台上使用驱动程序级按钮模拟. 我的DLL中提供了以下方法:
InitSuperKeys()安装WINIO驱动程序,通常用于在Form_Load事件中调用
CloseSuperKeys()卸载通常用于在Form_Closed事件中调用的WINIO驱动程序
KeyDown(Key)模拟普通Key键的按下.
KeyDownEx(Key)模拟按下扩展的Key键.
KeyUp(Key)模拟普通Key键的弹出窗口.
KeyUpEx(Key)模拟扩展的Key键的弹出窗口.
KeyPress(键)模拟一次正常键的按下和弹出. 按下和弹出之间的默认时间间隔为200毫秒
KeyPress(Key,Int32)模拟一次普通Key键的按下和弹出. 按下和弹出之间的时间间隔是第二个参数,以毫秒为单位.
KeyPressEx(Key)模拟扩展的按键并弹出一次. 按下和弹出之间的默认间隔为200毫秒,写入扩展键信息的间隔为100毫秒
KeyPressEx(Key,Int32)模拟一次扩展键Key的按下和弹出. 按下和弹出之间的时间间隔是第二个参数,以毫秒为单位,写入扩展键信息的间隔是100毫秒.

KeyPressEx(Key,Int32,Int32)模拟扩展的按键并弹出一次. 按下和弹出之间的间隔是第二个参数(以毫秒为单位),写入扩展键信息之间的间隔是第三个参数(以毫秒为单位).
特殊说明:
1. 在执行模拟密钥之前,必须执行InitSuperKeys()来安装驱动程序. 最好在关闭窗口后卸载驱动程序.
2. 上面方法中的参数Key是我在WinIoSys类中定义的枚举,而不是DONET系统的Key枚举.
3. 通用键是指标准键盘键,例如A,B,C和Space. 扩展键指的是诸如“方向键”之类的特殊键,在处理此类扩展键时,系统将首先有时间写入扩展键信息. 因此,没有Ex结尾的方法用于标准普通密钥,而具有Ex结尾的方法用于特殊扩展密钥. 它们全部超载,用户可以自行设置间隔. 至于按钮的详细分类,请在Google上搜索.
4. 模拟按键事件后,必须让程序进入睡眠状态数毫秒,否则下一个按键将无法正常模拟.
5. USB似乎是总线,与端口操作无关. 因此,该方法理论上不支持USB接口键盘.
6. 一些防病毒软件会提醒用户安装驱动程序或将WinIo.sys报告为病毒. 实际上,这是正常的. 如果您从事此类异常活动,防病毒软件肯定会看不起它. 请不要怀疑该程序是否包含病毒或木马,最简单的方法是关闭防病毒软件〜. 如果您不担心,请不要使用它.
现在我们有了一个如此方便的界面,让我们尝试写一点东西来看看它的功能如何. 让我们以“拳皇”为例. 该游戏声称对Window消息绝对无效.
让我们创建一个新的EXE项目并引用我的SuperKeys.dll. 定义一个全局变量
WinIoSys m_IoSys =新的WinIoSys();
在Load事件中安装驱动程序
m_IoSys.InitSuperKeys();

在Closed事件中卸载驱动程序
m_IoSys.CloseSuperKeys();
当然,我们可以编写一个全局钩子. 在游戏运行时,按一个键可以执行一系列键模拟. 但这只是一个DEMO,不需要那么正式,只需编写一个计时器即可触发它. 为了节省时间,请在每次单击按钮三秒钟后执行模拟键操作. 请记住在这三秒钟内激活拳皇游戏窗口.
首先统一键盘设置,如图所示:

我们决定模拟最简单的“ Iori”方法: 暗杀(即在地面上生火). 如果“ Iori”在左侧,则键盘操作为: ↓↘→+ A或C. 这是上图中的SDU或SDJ按钮. 以SDJ为例,在模拟此键盘时必须非常小心. 我开始像这样模拟它:
m_IoSys.KeyPress(WinIoSys.Key.VK_S);
Thread.Sleep(200);
m_IoSys.KeyPress(WinIoSys.Key.VK_D);
Thread.Sleep(200);
m_IoSys.KeyPress(WinIoSys.Key.VK_J,200);
结果不成功. 我仔细研究了. 实际上,当我们按下SDJ按钮时,我们首先按下S按钮,然后按下D按钮,然后按下S按钮,然后按下D按钮,最后按下J按钮. 然后真实的过程应该这样写:
m_IoSys.KeyDown(WinIoSys.Key.VK_S);

Thread.Sleep(100);
m_IoSys.KeyDown(WinIoSys.Key.VK_D);
Thread.Sleep(100);
m_IoSys.KeyUp(WinIoSys.Key.VK_S);
Thread.Sleep(100);
m_IoSys.KeyUp(WinIoSys.Key.VK_D);
Thread.Sleep(10); //这个地方不能相距太远,如果太大,整个动作就无法连接.
m_IoSys.KeyPress(WinIoSys.Key.VK_J,200);
测试后,成功模拟我们想要的操作. 您可以看到实际的模拟按键效果.
单击此处下载演示
单击此处查看“拳皇”的“ Iori”小特效.
该程序已在VS2008 + WinXP SP3 + WinKawaks1.48XP + KOF 2000 + P / S键盘下调试并通过.
让驱动程序级键盘模拟做更多的事情
除了编写游戏插件外,这些东西还能做什么?听说新版的QQ在键盘防盗技术方面非常出色而且功能强大.
本文来自电脑杂谈,转载请注明本文网址:
https://www.pc-fly.com/a/bofangqi/article-293340-1.html
你他喵的事看热闹不嫌事大