——————————————————————————————————————————————————————————————————————————————————

本系列的最后一篇演示如何通过调试手段摘除 QQ 过滤驱动设置的事件通知 CallBack。

内核中有几个全局的数组用来存放这些事件通知 CallBack 的指针,第一个就是 nt!PspCreateProcessNotifyRoutine,

当有进程被创建时,该数组中的函数指针就会依次被调用,与此类似,当有线程被创建时,nt!PspCreateThreadNotifyRoutine

数组中的函数指针就被调用;nt!PspLoadImageNotifyRoutine 中的回调则是在有内核模块加载时被调用。

驱动程序通过向这些数组中加入 CallBack 指针,就能够监控相应的事件。

首先来看下哪些驱动程序正在监控系统范围的进程创建事件:

 r @$t0=poi(nt!PspCreateProcessNotifyRoutineCount);
r @$t1=nt!PspCreateProcessNotifyRoutine;
.for(r @$t2=; @$t2<@$t0; r @$t2=@$t2+){dds (poi(@$t1+@$t2*)^)+ l1;}

从上图您可以看到,QQFrmMgr.sys 中有一个例程正在监视着进程创建事件。除此之外的其它内核模块都是合法的,比如

“avkmgr”与“avdevprot”是安装德国小红伞反病毒软件时,附带安装的两个内核模式驱动程序,它们注册了各自的回调在

监控着进程创建事件,这是实现 Real-Time Protection 用到的系统底层机制之一;“tcpip”不用我说各位也知道,它是

Windows 内核网络栈的主要实现模块之一:

注意,系统最多支持注册 8 枚事件回调指针,nt!PspCreateProcessNotifyRoutineCount 存储当前注册的回调指针数量,如下图,

这个全局变量的值与第一张图片中的事件回调指针枚数一致:

现在,我们尝试从中摘除 QQFrmMgr.sys 的监控例程:

使用类似的手段,检查 QQFrmMgr.sys 有没有监控线程创建与内核模块加载事件:

 r @$t0=poi(nt!PspCreateThreadNotifyRoutineCount);
r @$t1=nt!PspCreateThreadNotifyRoutine;
.for(r @$t2=; @$t2<@$t0; r @$t2=@$t2+){dds (poi(@$t1+@$t2*)^)+ l1;} r @$t0=poi(nt!PspLoadImageNotifyRoutineCount);
r @$t1=nt!PspLoadImageNotifyRoutine;
.for(r @$t2=; @$t2<@$t0; r @$t2=@$t2+){dds (poi(@$t1+@$t2*)^)+ l1;}

您看,这家伙监控的地方还真不少,为的就是保护它自己免受其它恶意软件攻击!或许你会好奇:图中的“XLGuard”是啥东

东?

它就是在安装“迅雷”(一种基于 BitTorrent 协议的 P2P 下载/分享软件)时,一并安装的内核模式驱动程序之一,如下图:

从名称中的“Guard”来看,应该也是用来保护迅雷自身组件的——现在的软件都比女性还懂得怎么保护自己呢!

你可以使用前述的方法来阻止 QQFrmMgr.sys 监控线程创建与内核模块加载事件——就布置成家庭作业吧!

———————————————————————————————————————————————————

写到这里,本系列算是大致功德圆满了。。。。还记得上一篇我抱怨说“!chkimg”调试器扩展命令不能用吗?

折腾的这几天总算找出问题所在了——从 MSDN 网站下载的 Windows 7 零售版符号包中的 ntoskrnl.exe 版本问题——我听信

该站点的建议下载了 Windows 7 Service Pack 1 x86 零售符号,结果其中的 ntoskrnl.exe 内核映像版本被最新版的

WinDbg 排斥,所以我换用了 Windows 8.1 x86 32 位零售符号,以便双机物理调试环境中检查目标机器上的 Windows 8.1

内核工作情况,也证实了 QQ 驱动没有采取反虚拟机技术,它的行为模式与在真实机器上的表现一致(至少在写作本文的时间点上

是如此,以后就难说了,搞不好也会引入反调试技术。。。),如下图:

最后贴上在 32 位 Windows 8.1 上利用“!chkimg”自动检查并恢复 SSDT 的过程,以飨读者:

NND,为啥前面手工检查 SSDT 能够发现的 QQ hooks,通过“!chkimg”自动检查却探测不到,只识别了 inline hook ?

阅读一下该扩展命令的官方文档,原来是需要指定一个特殊的选项:

正如图中红框部分所讲的那样:Hal.dll 与 Ntoskrnl.exe 中的某些特定地址不会被检查,因为当这些部分被载入时,会发生某些改变。

包含 -nospec 选项则可以检查这些地址。事实上,这就是我在前一篇谈到的——每次系统启动时都随机创建 SSDT 的基址,所以

“!chkimg”就忽略了这些“随机”的部分,偏偏给 QQ 驱动留下了可乘之机。。。。添加 -nospec 选项后,我们成功地

分析出 SSDT 中的所有 hooks,下面我仅截取了输出的前三个 hooks,它们对应于前面有一张“dps”命令解析图中的三个 hooks:

以上图中的黄框部分为例,第一个 hook 是从 8151b3a8 到 8151b3aa 的三个字节修改;冒号左边是磁盘文件中的原始字节

序列,冒号右边是内存映像中的已修改字节序列,该项 hook 距离 nt!KiServiceTable 起始地址的偏移量为 0xC。

让我们看看前三个 hook 的受害例程(原始系统服务)是什么?

原来 QQFrmMgr.sys hook 了 NtWriteVirtualMemory()(写入任意进程的虚拟内存)、NtUnmapViewOfSection()(取消

映射 section 的视图;Windows 内存管理器中用来实现共享内存和映射文件的底层原语就叫做 "section 对象" ;合法的驱动

程序程序应该仅使用 ZwOpenSection(),ZwMapViewOfSection(),以及 ZwUnmapViewOfSection() 等函数操纵 section

对象;于是 hook 该系统服务的用意在于监视映射文件与查看其中部分内容的请求)、

以及 NtTerminateProcess()(终止进程),这与我前一篇的手工分析一致。

最后,让我们用“!chkimg”的“-f”开关,自动修正内存映像中的错误:

————————————————————————————————————————————————————————
小结:本篇讨论了摘除恶意事件通知回调函数的相关技巧,并演示自动修复关键系统设施的方法,文中介绍的调试技术只是

内核攻防中的冰山一角,而且这些方法随着内核与恶意软件的不断进化也正面临着挑战!

持续研究与探索不同内核驱动/rootkit 的行为模式仍旧是必要的!
————————————————————————————————————————————————————————

------- 软件调试——注销 QQ 过滤驱动设置的事件通知 CallBack (完)-------的更多相关文章

  1. ------- 软件调试——还原 QQ 过滤驱动对关键内核设施所做的修改 -------

    -------------------------------------------------------------------------------- 在前一篇博文中,我们已经处理完最棘手的 ...

  2. ------- 软件调试——挫败 QQ.exe 的内核模式保护机制 -------

    ------------------------------------------------------------------------ QQ 是一款热门的即时通信(IM)类工具,在安装时刻会 ...

  3. (转)支持 PS/2 与 USB 的键盘过滤驱动(可卸载)

    Author:  sinisterEmail:   sinister@whitecell.orgHomepage:http://www.whitecell.org Date:    2007-02-2 ...

  4. Windbg对过滤驱动DriverEntry函数下断点技巧

    方法1: 1> 先用DeviceTree.exe查看指定的过滤驱动的Load Address(加载地址) 2> 再用LordPE.EXE查看指定过滤驱动文件的入口点地址 3> 计算过 ...

  5. File System Minifilter Drivers(文件系统微型过滤驱动)入门

    问题: 公司之前有一套文件过滤驱动,但是在实施过程中经常出现问题,现在交由我维护.于是在边看代码的过程中,一边查看官方资料,进行整理. 这套文件过滤驱动的目的只要是根据应用层下发的策略来控制对某些特定 ...

  6. <读书笔记>软件调试之道 :从大局看调试-发现代码存在问题

    声明:本文档的内容主要来源于书籍<软件调试修炼之道>作者Paul Butcher,属于读书笔记.欢迎转载! ---------------------------------------- ...

  7. <读书笔记>软件调试之道 :问题的核心-如何修复缺陷

    声明:本文档的内容主要来源于书籍<软件调试修炼之道>作者Paul Butcher,属于读书笔记.欢迎转载! 修复缺陷 对于一个好的修复来说,不仅仅是让软件运行正确,还需要为将来奠定基础.一 ...

  8. 软件调试之INT 3讲解

    第4章断点和单步执行 断点和单步执行是两个经常使用的调试功能,也是调试器的核心功能.本章我们将介绍IA-32 CPU是如何支持断点和单步执行功能的.前两节将分别介绍软件断点和硬件断点,第4.3节介绍用 ...

  9. 文件过滤驱动实现目录重定向(一)good

    文件过滤驱动拦截的IRP主要包括以下几个:IRP_MJ_CREATE,文件创建操作,文件的任何操作,都是从这里开始的.IRP_MJ_CLEANUP,文件的HANDLE句柄全部关闭会触发这个消息IRP_ ...

随机推荐

  1. Spring Boot实战:静态资源处理

    前两章我们分享了Spring boot对Restful 的支持,不过Restful的接口通常仅仅返回数据.而做web开发的时候,我们往往会有很多静态资源,如html.图片.css等.那如何向前端返回静 ...

  2. Winform & Devexpress Chart使用入门

    一.Chart(Winform) 使用图表控件(chart)首先要理解图表区域(ChartArea).XY轴(AxisX.AxisY).数据点(Series).标题(Title).图例(Legend) ...

  3. MLlib--保序回归

    转载请标明出处http://www.cnblogs.com/haozhengfei/p/24cb3f38b55e5d7516d8059f9f105eb6.html 保序回归 1.线性回归VS保序回归 ...

  4. dede list列表页和文章页分别使用if else

    标签: dede 2015-01-25 19:33 755人阅读 评论(0) 收藏 举报 分类: [ Dede ](20) 版权声明:本文为博主原创文章,未经博主允许不得转载. list列表页中使用i ...

  5. Python3 的列表

    1:列表: Python的列表比C语言的数组强大的多,数组只能存放相同类型的数据,而列表则像一个大集装箱可以存放整形.浮点型.字符串.对象等 2:创建列表的方法 #创建一个普通列表 list1=[1, ...

  6. vue 入门第一课

    windows安装git 安装淘宝镜像 npm install -g cnpm --registry=https://registry.npm.taobao.org 全局安装vue cnpm inst ...

  7. Java数据库基础(JDBC)

    JDBC(Java Data Base Connectivity):SUN公司为了简化统一对数据库的操作,定义了一套Java操作数据库的规范,称之为JDBC: 这样应用程序就不需要关注数据库底层的详细 ...

  8. 半透明边框与background-clip

    在开始本章之前,我们要先简单介绍CSS中的半透明颜色.自2009年后,网页工作者们开始使用半透明颜色,如rgba().hsla().前者相信大家都很熟悉,不难理解其中将有四个参数,第四个参数则为透明度 ...

  9. CCF系列之最大的矩形(201312-3)

    试题名称: 最大的矩形 时间限制: 1.0s 内存限制: 256.0MB 问题描述: 问题描述 在横轴上放了n个相邻的矩形,每个矩形的宽度是1,而第i(1 ≤ i ≤ n)个矩形的高度是hi.这n个矩 ...

  10. 【笔记】BFC 模型知识整理

    网上看了很多 BFC 的概念,发现都说得不是很完整和深入,刚好最近看了一些视频教程说到了 BFC 概念所以记录一下. BFC 的概念: BFC 全称:Block format context 块级格式 ...