黑客防线2012合订本
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

计算机网络安全之DLL劫持漏洞详解

前置知识:无

关键词:DLL劫持

图/文 刘晓明

近期网络机房电脑大范围中毒,病毒文件为“USP10.DLL”,该病毒繁殖能力强,很容易复发。在分析此病毒后,发现该病毒利用的漏洞正是被业界称为“末日漏洞”的DllHijack漏洞(DLL劫持漏洞),此漏洞影响较大,很多病毒都采取这种技术攻击用户电脑,让广大网管员们头痛不已。本文深入分析了该漏洞的形成原理并通过编写攻击文件验证此漏洞的危害,最后提出应对方案,希望对朋友们有所帮助。

一、DLL劫持漏洞原理与攻击文件构造

1.原理分析

当一个可执行文件运行时,Windows加载器将可执行模块映射到进程的地址空间中,加载器分析可执行模块的输入表,并设法找出任何需要的DLL,并将它们映射到进程的地址空间中。

由于输入表中只包含DLL名而没有它的路径名,因此加载程序必须在磁盘上搜索DLL文件。而这里DLL文件的搜索遵循以下顺序。

(1)可执行程序加载的目录。

(2)系统目录。

(3)16位系统目录。

(4)Windows目录。

(5)文档运行目录。

(6)PATH环境变量中列出的目录。

这个就是Windows系统的目录优先权。利用这一特点,攻击者先伪造一个与系统同名的DLL,提供同样的输出表,每个输出函数转向真正的系统DLL。程序调用系统DLL时会先调用当前目录下伪造的DLL,完成相关功能(恶意代码或程序补丁)后,再跳到系统DLL同名函数里执行。这个过程用个形象的词来描述就是系统DLL被劫持(Hijack)了。

2.攻击文件构造

了解了DLL劫持具体原理后,就让我们来动手编写攻击文件,再现USP10.DLL病毒。

测试环境:Windows XP SP3 5.1.2600 Service Pack 3 Build 2600。

编程环境:Delphi 2007。

工具软件:ViewDLL,进程查看器。

(1)用Delphi 2007新建一个DLL工程,命名为USP10。

(2)运行ViewDLL软件,加载系统目录下的正常USP10.DLL文件,记下该DLL文件的所有导出函数名,如图1所示。

图1 ViewDLL界面

(3)用Delphi 2007编写代码,构造与真正USP10.DLL文件相同的导出表,完成所有导出函数的转发,编写攻击代码。

这里只是做演示,所以攻击代码只是简单地运行一个程序。

        WinExec('notepad.exe',sw_normal);  //运行记事本程序

由于篇幅原因以下只列出关键代码。

        //定义转发目标指针:
        var
        POldLpkPresent: Pointer;
        POldScriptApplyDigitSubstitution: Pointer;
        POldScriptApplyLogicalWidth: Pointer;
        //填充转发指针:
        ModHandle:=
      LoadLibrary('C:\WINDOWS\system32\usp10.dll');
        if ModHandle > 0 then
        begin
          POldLpkPresent:= GetProcAddress(ModHandle,
      'LpkPresent');
          POldScriptApplyDigitSubstitution:=
      GetProcAddress(ModHandle,'ScriptApplyDigitSubstitution');
          POldScriptApplyLogicalWidth:=
      GetProcAddress(ModHandle,'ScriptApplyLogicalWidth');
        //完成转发过程:
        procedure LpkPresent; asm jmp POldLpkPresent end;
        procedure ScriptApplyDigitSubstitution; asm jmp
      POldScriptApplyDigitSubstitution end;
        procedure ScriptApplyLogicalWidth; asm jmp
      POldScriptApplyLogicalWidth end;
        ...
        //构造导出表:
        exports
        LpkPresent,
        ScriptApplyDigitSubstitution,
        ScriptApplyLogicalWidth,
        ...

完成整个模板编写后就可以把攻击代码加入执行过程完成测试文件的构造了。

这里要注意的是在调用函数完成攻击过程时不可用到所劫持DLL导出的函数,也就是如果要劫持USP10.DLL文件,那就不能用USP10.DLL所提供的任何函数。

(4)测试攻击效果。测试EXE文件选用系统自带的计算器程序CALC.EXE,把编译好的USP10.DLL文件复制到和CALC.EXE同一目录下,运行CALC.EXE,这时会发现不光是运行了计算器程序,记事本程序也同时运行起来了,如图2所示。

图2 测试效果

用进程查看器查看CALC.EXE进程,如图3所示。

图3 进程加载的模块

发现计算器程序确实先加载了我们构造好的USP10.DLL,然后由伪装后的USP10.DLL加载了真正的USP10.DLL。

通过以上测试,我们发现DLL劫持漏洞确确实实存在,而且造成的后果非常严重,但是此漏洞仅仅存在于Windows操作系统内部吗?答案是否定的!

二、新型DLL劫持漏洞原理与攻击文件构造

2010年8月24日,微软发布安全公告2269637,提到三方软件编程不安全,存在一个DLL劫持的缺陷可以导致远程攻击。

2010年8月24日,流行的漏洞信息共享网站exploit-db马上就爆出多个DLL劫持漏洞,涉及的软件有:Wireshark(免费嗅探器)、Windows Live email(邮箱客户端)、Microsoft MovieMaker(视频编辑处理)、Firefox(网页浏览器)、uTorrent(BT下载工具)、PowerPoint 2010(办公软件)等。

2010年8月25~26日,漏洞信息共享网站exploit-db继续爆出Winamp、Google Earth、Photoshop等软件存在DLL劫持漏洞。

在安全组织exploit-db公布的存在DLL劫持漏洞的软件列表中,AutoCAD 2007、Daemon tools、Winamp、Media Player Classic、Mozilla Thunderbird、Microsoft Office、Adobe Photoshop 、Adobe Dreamweaver CS5、Skype、Safari、WinDVD、Opera、Firefox等都位列其中。安装了上述软件的电脑,当用户在打开一个图片、音乐、视频、BT种子、网页文件时都有可能感染病毒。当攻击者利用DLL劫持漏洞构造一个特殊的DLL文件,将这个DLL文件打包到一些JPG、PPT、MP3、MPG、Html文件中分发,用户解压后双击打开这些文档,病毒即被立即触发。

1.新型DLL劫持漏洞形成原理

应用程序为了扩展或者兼容等目的需要加载相应的DLL文件,但是因为某些原因导致这个DLL文件默认不存在于当前系统,此时就会尝试加载文档所在目录下的恶意DLL文件,从而达到破坏的作用。这里运行的文档(如mp3)相当于触发者,根据文件关联它会启动一个应用程序去播放mp3文件。而因为应用程序存在DLL劫持漏洞(如Winamp),此时Winamp就会因为设计上的不足导致其成为恶意DLL的加载器。新型DLL劫持漏洞构成的危害简直达到了只要运行图片或音频文件就会执行恶意代码的地步。

2.攻击文件构造

为了更好地说明新型DLL漏洞的危害性,我们来具体演示一下,这里选取的软件为Microsoft Office 2007中的Word软件。

测试环境:Windows 7 6.1.7601 Service Pack 1 Build 7601。

编程环境:Delphi 2007。

工具软件:漏洞检测软件。

(1)用漏洞检测软件检测Word 2007,发现存在DLL劫持漏洞,检测报告如下。

        Application: WINWORD.EXE
        Version: 12.0.6211.1000
        Company Name: Microsoft Corporation
        Product Name: 2007 Microsoft Office system
        File Date: 28-08-2007
       Detailed Report:

从以上报告可以看到Word 2007在打开DOC或DOCX文档时引发了DLL劫持漏洞,漏洞文件为IM****.DLL(为了安全,这里将具体文件名隐去,请谅解)。

(2)用Delphi 2007软件编写代码。这里我们只写攻击代码即可,不用再完全按照原DLL构造导出表了(会引起软件崩溃,只是测试)。

具体代码如下。

        library im****;
        uses
        windows;
        begin
        MessageBox(0,'测试成功,存在漏洞!','DLL劫持漏洞测
      试',MB_OK);  //弹窗测试
        end.

(3)测试攻击效果。在任意目录下新建DOC(DOCX)文档,将编译好的伪造IM****.DLL复制到同一目录下,运行DOC(DOCX)文档,如图4所示。

图4 Word 2007漏洞测试

可以看到Word 2007确实存在DLL劫持漏洞,造成的结果是,你在打开一个Word文档的时候病毒却已在后台监视你的一举一动!

同时给出常用软件Photoshop CS3的漏洞测试截图,如图5所示。

图5 Photoshop CS3漏洞测试

新型DLL劫持漏洞造成的影响比老式DLL劫持漏洞更广泛,而面对如此严重的漏洞,微软没有提供有效的免疫方案可以使用,只能靠使用者小心为妙了。

三、应对DLL劫持

DLL劫持利用系统未知DLL的搜索路径方式,使得程序加载当前目录下的系统同名DLL。所以可以首先告诉系统DLL的位置,改变加载系统DLL的顺序不是当前目录,而是直接到系统目录下查找。这个想法可以通过修改注册表实现。键值“HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\KnownDLLs”是调用系统DLL的首要查找目录。例如,里面有RE_SZ类型的“ntdll”=“ntdll.dll”项,则系统载入“ntdll”时会直接从系统目录加载。因此,添加“usp10”=“usp10.dll”即可防止USP10.DLL被劫持,同理可以阻止一些其他DLL被劫持。在Windows XP系统下默认只有少数关键DLL在此键值中,Windows 7下面此键值已经相当齐全,在Windows 7系统下发生DLL劫持的概率要比XP小很多,因此可以考虑升级操作系统到Windows 7。

对于新型DLL劫持,因为没有十分有效的应对方式,所以用户要养成运行文档(图片、音乐、视频、网页文件等)前检查目录下文件的习惯,开启显示隐藏文件和显示系统文件选项,防止通过应用程序加载恶意DLL。

本文通过USP10.DLL病毒引入了DLL劫持漏洞的概念,从原理上分析漏洞形成的原因、利用方法和解决方案。希望对从事相关工作的朋友有所帮助,如对本文有不同看法或是需要相关资料可以与本人联系。