过DNF TP 驱动保护2

  • 格式:doc
  • 大小:1.93 MB
  • 文档页数:14

06、干掉NtReadVirtualMemory 中的InLine Hook:前面已经干掉了TP 对NtOpenProcess 以及TP对NtOpenThread 所做的Hook,这样的话,我们已经可以使用OD 或者CE 看到DNF 的游戏进程了,弄过一些游戏方面内容的朋友应该都是知道CE 的,这东西是开源的,不过是基于Delphi 的,工具做得很不错,可以通过CE 来修改一些游戏进程的内存数据,比如可以修改一些简单的游戏的血值啊之类的,但是,此时我们可以用CE 来扫描一下DNF 游戏进程的内存,你会发现根本扫描不到任何数据,其实原因也很简单,TP 对NtReadVirtualMemory 进行了浅层的InLine Hook,从而可以达到防止其他进程读取DNF 游戏进程内存的目的,而CE 的话,在Ring3 下是通过ReadProcessMemory 来读取游戏内存的,而ReadProcessMemory 进入Ring0 后又是调用的NtReadVirtualMemory,由于NtReadVirtualMemory 被TP干掉了,所以自然用CE 是扫描不出任何东西的,要干掉TP 对NtReadVirtualMemory 所作的浅层InLine Hook 其实是比较简单的,因为TP并没有对NtReadVirtualMemory 做检测,所以可以直接用SSDT 来对抗掉浅层的InLine Hook 就OK。

至于原理的话,很简单,直接用SSDT Hook 替换掉系统服务NtReadVirtualMemory,然后在SSDT Hook NtReadVirtualMemory 这个我们自己写的系统服务中判断,如果是DNF 进程的话,直接调用原来的SSDT 系统服务就好,如果不是DNF 进程的话,我就跳过TP 对NtReadVirtualMemory 所做的InLine Hook,也就是跳过前面7 个字节就OK 了。

对于这种干掉InLine Hook 的原理,堕落天才的文章讲的最清楚了,我这里就不再班门弄斧了。

对于用SSDT Hook 干掉浅层的InLine Hook 可以参考文章名称:《SSDT Hook 的妙用- 对抗Ring0 InLine Hook》。

有的初学者可能问,咱是如何知道NtReadVirtualMemory 被TP 干掉了呢?很简单,还是采用前面的做法,用Kernel Detective 就可以看到了,具体可以看下面的截图:至于如何安装SSDT Hook 或者SSDT Hook 是啥玩意来着的话,大家有兴趣的可以参考我的下面博文系列:《进程隐藏与进程保护(SSDT Hook 实现)》系列,共三篇。

/BoyXiao/archive/2011/09/03/2164574.html/BoyXiao/archive/2011/09/04/2166596.html/BoyXiao/archive/2011/09/05/2168115.html下面先贴出安装SSDT 钩子的代码,该代码用来干掉TP 对NtReadVirtualMemory 的InLine Hook:1: /*****************************************************************/2: /* 安装钩子从而过掉TP 保护所Hook 的NtReadVirtualMemory - 让TP 失效*/ 3: /* 保存NtReadVirtualMemory第4,5,6,7 个字节(就是一个ULONG 跳转地址) */ 4: /* 因为这几个字节在不同的XP上会改变,所以在SSDT Hook 之前保存下来*/ 5: /* 从而避免在此处进行硬编码6: /*********************************************************************/ 7: VOID InstallPassTPNtReadVirtualMemory()8: {9: if(g_SSDTHookNtReadVirtualMemory > 0)10: {11: /* 获得NtReadVirtualMemory 的地址*/12: ULONG uNtReadVirtualMemoryAddr =oldSysServiceAddr[g_SSDTHookNtReadVirtualMemory];13:14: /* 如果是DNF 进程,则跳到NtReadVirtualMemory 执行,即不处理,从而让DNF InLine Hook 生效*/15: uTPHookedNtReadVirtualMemoryJmpAddr = uNtReadV irtualMemoryAddr; 16: /* 如果不是DNF 进程,则跳过TP 的InLine Hook,从而使TP 失效*/ 17: uMyHookedNtReadVirtualMemoryJmpAddr = uNtReadVirtualMemoryAddr + 7;18: /* 保存下未Hook 之前的NtReadVirtualMemory 的第4,5,6,7 个字节*/ 19: uNtReadVirtualMemoryAddr_3 = *((ULONG *)(uNtReadVirtualMemoryAddr + 3));20:21: InstallSysServiceHookByIndex(g_SSDTHookNtReadVirtualMemory,SSDTHookNtReadVirtualMemory);22:23: KdPrint(("Pass TP - NtReadVirtualMemory Installed."));24: }25: }下面再给出SSDT Hook 的中继API 的实现代码:1:/************************************************************************/ 2: /* 自定义的NtReadVirtualMemory,用来实现SSDT Hook Kernel API3:/************************************************************************/ 4: NTSYSHOOKAPI VOID SSDTHookNtReadVirtualMemory()5: {6: /* 开始过滤*/7: if(V alidateCurrentProcessIsDNF() == TRUE)8: {9: __asm10: {11: /* 如果是DNF 进程调用的话,则调用已经被TP Hook 的NtReadV irtualMemory*/12: jmp uTPHookedNtReadVirtualMemoryJmpAddr13: }14: }15:16: __asm17: {18: /* 已经做了针对硬编码的处理19: 如果不是DNF 进程调用的话,则跳过TP Hook 的NtReadVirtualMemory*/20: push 0x1C21: push uNtReadVirtualMemoryAddr_322: jmp uMyHookedNtReadVirtualMemoryJmpAddr23: }24: }好,到这里就已经干掉了TP对NtReadVirtualMemory 所做的InLine Hook了,对此最直白的效果就是用CE 打开DNF 游戏进程进行内存扫描,你会发现,On Y ear,可以正常扫描到DNF 内存了。

07、干掉NtWriteVirtualMemory 中的InLine Hook:上面又干掉了TP 对NtReadVirtualMemory 的InLine Hook 了,从而实现了CE 读取DNF 进程的内存。

但是你可以试着用CE 修改DNF 进程的内存,你很快就会发现,虽然可以扫描内存,但是并不可以读取内存,而后你也肯定能够想到,既然有防止读取内存,那肯定也有防止写入内存,而后你又自然会找到NtWriteVirtualMemory 上来,等你找到NtWriteVirtualMemory 后,你又基本能够确定,搞定这个API 和搞定NtReadVirtualMemory 应该是差不多的,因为这两个API 就是一对啊,一个读,一个写,所以TP肯定也是采用相同的做法来处理这两个API,当然,你上面的猜想都是正确的,所以咱还是用SSDT 来干掉TP对NtWriteVirtualMemory 所做的InLine。

代码和上面的NtReadVirtualMemory 差不多,这里也还是贴出来一下吧,俺先放两幅截图,然后再贴代码出来:下面先贴出安装SSDT 钩子的代码,该代码用来干掉TP 对NtWriteVirtualMemory 的InLine Hook:1:/************************************************************************/ 2: /* 安装钩子从而过掉TP 保护所Hook 的NtWriteVirtualMemory - 让TP失效3: /* 保存NtWriteVirtualMemory 第4,5,6,7 个字节(其实就是一个ULONG 跳转地址)4: /* 因为这几个字节在不同的XP上会改变,所以在SSDT Hook 之前保存下来5: /* 从而避免在此处进行硬编码6:/************************************************************************/ 7: VOID InstallPassTPNtWriteVirtualMemory()8: {9: if(g_SSDTHookNtWriteVirtualMemory > 0)10: {11: /* 获得NtWriteVirtualMemory 的地址*/12: ULONG uNtWriteVirtualMemoryAddr = oldSysServiceAddr[g_SSDTHookNtWriteVirtualMemory];13:14: /* 如果是DNF 进程,则跳到NtWriteVirtualMemory 执行,即不处理,从而让DNF InLine Hook 生效*/15: uTPHookedNtWriteVirtualMemoryJmpAddr = uNtWriteVirtualMemoryAddr; 16: /* 如果不是DNF 进程,则跳过TP 的InLine Hook,从而使TP 失效*/ 17: uMyHookedNtWriteVirtualMemoryJmpAddr = uNtWriteVirtualMemoryAddr + 7;18: /* 保存下未Hook 之前的NtReadVirtualMemory 的第4,5,6,7 个字节*/ 19: uNtWriteV irtualMemoryAddr_3 = *((ULONG *)(uNtWriteVirtualMemoryAddr + 3));20:21: InstallSysServiceHookByIndex(g_SSDTHookNtWriteVirtualMemory,SSDTHookNtWriteVirtualMemory);22:23: KdPrint(("Pass TP - NtWriteV irtualMemory Installed."));24: }25: }下面再给出SSDT Hook 的中继API 的实现代码:1:/************************************************************************/ 2: /* 自定义的NtWriteVirtualMemory,用来实现SSDT Hook Kernel API3:/************************************************************************/ 4: NTSYSHOOKAPI VOID SSDTHookNtWriteVirtualMemory ()5: {6: /* 开始过滤*/7: if(V alidateCurrentProcessIsDNF() == TRUE)8: {9: __asm10: {11: /* 如果是DNF 进程调用的话,则调用已经被TP Hook 的NtWriteVirtualMemory */12: jmp uTPHookedNtWriteVirtualMemoryJmpAddr13: }14: }15:16: __asm17: {18: /* 已经做了针对硬编码的处理*/19: /* 如果不是DNF 进程调用的话,则跳过TP Hook 的NtWriteVirtualMemory */20: push 0x1C21: push uNtWriteVirtualMemoryAddr_322: jmp uMyHookedNtWriteVirtualMemoryJmpAddr23: }24: }好,到这里就已经拿下了TP对NtWriteV irtualMemory 所做的InLine Hook了,对此最直白的效果大家也都可以想象得到了,那就是直接用CE 打开DNF 游戏进程进行内存修改,你会发现,此时可以正常修改掉DNF 游戏的内存了。