为无源码的数据批量处理软件添加功能
软件简介
chrep.exe是一款用于对文件进行数据批量查找,处理,替换的工具,它的主界面如下图所示:

使用PE分析工具DIE 对其进行分析,发现它是一个使用Visual C/C++编写的程序,使用了MFC静态库,链接器版本为7.10,是一款年代比较久远的软件。

需求
当我们搜索需要处理的字符串以后,统计一栏会展示出我们选中的文件当中,有多少匹配的字符串。
我们的需求是为它增加一个排序的功能,当点击它的列名 ”统计“ 时,它可以按照匹配字符串的数量进行排序。

思路
观察该软件的主界面,很容易可以发现它使用了列表控件,而点击列表控件的列标题,列表控件会向主窗口发送一个WM_NOTIFY消息,我们可以修改该窗口的消息处理函数为自己实现的消息处理函数,对WM_NOTIFY消息做判断,如果是我们想要的消息,就获取列表控件并按照对应字段对其进行排序即可。
于是现在的问题转变为我们如何修改窗口的消息处理函数。我们需要做到在该进程当中执行代码,于是很自然的想到可以加载一个dll到该程序当中,然后在dll当中执行代码。
至于如何加载dll,我们有以下几个思路:
- dll劫持
dll劫持是一项很流行的技术,它通过利用微软优先加载当前目录的dll的机制,从而做到将自己的dll加载到目标程序进程中,为了不影响程序的功能,需要将程序从被劫持dll导入的函数全部转发到原先的dll。
但是该方法并不是一个通用的方法,由于系统对HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\KnownDLLs注册表项下的dll会优先从系统目录加载,所以如果该程序除了系统dll以外,没有其它依赖的dll的话,就会无法劫持,如果dll导入的函数较多的话,转发起来也会比较麻烦,需要通过写工具来完成。
通过CFF explorer工具查看该程序的导入表,发现确实有dll不在系统的白名单中,且导入的函数也不多,适合劫持:

- 修改导入表dll对应的模块名称
当操作系统加载程序时,会遍历其导入表,并将其中记录的每一个dll也加载进内存,可以通过修改某个导入表项对应的dll名称,然后系统就会加载修改名称后的dll,然后劫持的dll也导出原先程序导入的那些函数,然后在那些函数中调用修改前dll对应的函数,这样也不影响程序的使用。这也是一种劫持的思路,而且优势在于它不受系统白名单的限制。

- 加一个导入表项
可以考虑直接在原先导入表的基础上加入一项,然后填写需要加载的dll的信息,这样也就实现了dll的注入,这种方法也被称为导入表注入,它相对来说比较稳定,也没有什么明显的缺点。硬要说缺点的话,就是通常都没有足够的位置加一项导入表,需要添加节并将导入表整体挪动位置,比较麻烦。
目前的思路就是上面的三种,我选择的方法是第三种,加一个导入项,毕竟前几天刚刚学习了导入表的结构以及添加节的手法,正好可以派上用场。
到这里,已经可以加载dll到目标程序的进程了,现在的问题是在什么时机修改窗口过程函数呢?因为在加载dll时,窗口还没有被创建,所以显然无法直接在dllmain函数中修改,可以考虑的方法是创建一个线程并不断循环查找目标窗口,直到窗口创建完成,查找到对应的窗口后修改过程函数,也可以hook原程序的IAT表,然后在hook的函数中修改,因为到那个时候,窗口肯定已经创建完成了,可以直接找到窗口,而且IAT Hook也是一种比较稳定的hook方式,不存在Inline Hook的种种问题。考虑到刚在科锐学习了导入表的结构,所以考虑写一个IAT Hook,刚好可以加深对导入表的理解。
总体流程
这下,添加功能的总体流程就确定了:
- 修改原程序的导入表,增加一项来注入我们的dll
- 在我们的dll中Hook原程序的IAT表
- 在hook函数中修改窗口过程函数
- 窗口过程函数中处理WM_NOTIFY消息,对列表控件的Item进行排序
具体步骤
添加导入表项
首先通过数据目录找到其导入表位置:

导入表每一项有20个字节,它必须要以一个全零的导入表结构作为结尾,所以该软件当前的位置很显然不够再添加一项,于是只能将原导入表整体搬到另一个位置,然后再添加项。但是很难确定别处的数据是否会被使用,所以最为稳定的办法就是为其添加一个节,然后将原先导入表全都挪过去。
添加节,首先需要将文件头中的NumberOfSections字段加一,然后添加一个节表。如果原先头部空间不够添加一个节表,还需要扩大头部空间,然后修改SizeOfHeaders字段,并将所有节数据往后移,然后修正所有节表中每个节的文件偏移,也就是PointerToRawData字段。手工操作的话是很麻烦的,可以考虑将该功能工具化,有些PE工具也提供了这个功能。
幸运的是该软件的头部空间足够添加一个节表,所以直接为其添加,并且由于是存放导入信息,所以我为其取名为myidata节。
[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课
最后于 2024-3-5 15:28
被kanxue编辑
,原因: