逍遥公子 发表于 2013-4-28 08:28:36

检测RING3的IAT HOOK/EAT HOOK

这两天在写一个小软件,名字叫PhoenixUnhooker,由于精力有限,现在只完成了RING3的IAT HOOK/EAT HOOK的检测,于是写下本文,一个是简单介绍一下,其次也算做个学习笔记。

    如果有任何问题,还望留言告知,本程序仅在XP SP3下测试通过。

MAIN:

    IAT、EAT就是PE里的两个函数表,对其进行修改可以实现API HOOK。要是做检测的话,就要找到当前函数地址(内存里),以及原始函数地址(文件里),从理论上讲没什么难度(实际上也没啥难度,不过其中有几个奇葩的问题)。

QUESTION1:IAT的原始地址

    一开始我还以为原始地址也保存在模块文件里,于是直接读取文件解析,可是到最后,发现取到的“真实地址”乱七八糟的,冥思苦想了半天,也不得其解。后来睡觉时突然想到,IAT里的函数地址是在导入模块加载时从导出模块的EAT里取得的,所以说,IAT的原始地址并不在导入模块的二进制文件里。知道了这一点就简单了,分别分析每个导出模块,取得导入函数的原始地址即可。

QUESTION2:EAT的各种地址(当前地址和原始地址)

    程序基本上成型了,可是很郁闷,我发现IAT里有很多钩子,祖国山河一片红,心道不好,肯定是哪里错了。可是找了半天也没发现哪里写错了,最后向Busy神牛请教,热心的Busy神牛帮我调试了半天,最后发现,EAT的函数序号表是按照1-n的顺序排列的,而第1-n个函数的序号未必就是1-n,恰恰不巧的是,EAT的函数地址表是按照函数序号排列的。也就是说,当我们从1-n迭代遍历IAT时,每个函数要先按照迭代变量i定位取得它的函数序号,再通过函数序号定位取得函数地址!悲剧……

QUESTION3:奇怪的HOOK:函数代理

    经过上述两个问题,修改之后,程序基本上就没问题了,IAT/EAT的各种地址都正确。不过,每个模块的IAT里还是有几个钩子,可是用XueTr一查,却没有找到这几个。难道我又错了?仔细观察,我发现这几个被HOOK的函数固定就是那么几个(HeadAlloc、HeapFree、GetLastError、SetLastError,等等)。

    于是我拿GetLastError下手,先定位到当前函数地址处,发现来到了RtlGetLastWin32Error处,如下图:

    很是费解,很显然这不是什么恶意的HOOK,绝大可能是WIN自己”HOOK“的,可是为什么呢?于是我又来到原始地址处,发现是一堆奇怪的Code,像是加了壳一样。再次请教Busy神牛,经过研究,我们发现,原来真正的GetLastError处并不是Code,而是Data!如图:

    尝试GetProcAddress(x, "GetLastError"),发现得到的是”当前地址“(即RtlGetLastWin32Error)而非”原始地址“。着实郁闷,MS为什么要这么做呢?望知道的神牛指点一下。我就姑且称这种函数为”代理函数“好了。而今天的作业还没写完,时间不多,还要写本文,所以没有写特殊处理这类代理函数的代码,检测时仍然会显示挂钩,以后修改一下就是了。

**** Hidden Message *****

liqiao351 发表于 2013-7-17 17:37:30

我来支持了

fgzhanhao 发表于 2013-8-28 06:03:29

我来支持了

dgann 发表于 2014-4-1 19:19:38

支持一下,鼓励分享

晓豪 发表于 2014-6-12 10:27:54

支持一下啊呵呵

qixiubanya 发表于 2014-8-11 11:51:43

鼓励分享鼓励分享

longge87 发表于 2018-10-6 21:55:01

支持楼主一波

shufu 发表于 2018-11-1 01:57:28

以后修改一下就是了。
页: [1]
查看完整版本: 检测RING3的IAT HOOK/EAT HOOK