欢迎来到 嗅灵易学

零基础也能上手的脚本技术课,一对一答疑带你入门

【OSG】以福昕阅读器为例实现高性能Fuzz Applied high-speed in-process fuzzing: the case of Foxit Reader

【OSG】以福昕阅读器为例实现高性能Fuzz Applied high-speed in-process fuzzing: the case of Foxit Reader

原文Vitaly Nikolenko译者:Arming 校对:布兜儿
原文http://www.hdwsec.fr/en/blog/inprocessfuzzing.html

Introduction(前言)

Fuzzing现在已经很普遍了,尤其是在AFL发布以来。众所周知,性能是非常关键的,因此为了在给定时间段内尽可能多的发现bug,我们希望优化我们的Fuzzing方法。本文以Foxit Reader的一个图片转为PDF的插件为例,描述了一种通用方法。更具体地说,我们用的Foxit版本是7.3.6.321,有漏洞的插件(ConvertToPDF_x86)版本是7.3.4.308. 这个版本的插件有几个有意思的crash。这些crash是由另一位研究人员独立发现的,并且已经提交给Foxit团队(已修复并发布新版本),因此我们决定公开它们。

 

Fuzzing Method

当通过Foxit Reader打开一个图片时,插件ConvertToPDF_x86就会被加载,将转换图片为PDF并显示出来。该插件可以处理最常见的图片格式(JPEG, GIF, PNG, ...)。

ModLoad: 6cf90000 6cf96000   C:\Windows\SysWOW64\IconCodecService.dll

ModLoad: 50230000 50f61000   C:\Windows\SysWOW64\ieframe.dll

ModLoad: 53820000 53d45000   C:\Program Files (x86)\Foxit Software\Foxit Reader\Plugins\Creator\x86\ConvertToPDF_x86.dll

在我的Fuzzing测试中,我决定专注于JPEG文件格式,然后定位到了Foxit调用插件的函数:

003b96f0 533c932e kernel32!CreateFileW

003b9720 533cb136 ConvertToPDF_x86!DestorFXPDFConvertor+0x4fe

003b975c 02598c3f ConvertToPDF_x86!CreateFXPDFConvertor+0x646

003bb644 0128e6fd FoxitReader_Lib_Full!CryptUIWizExport+0x8856ff

003beac8 0128637a FoxitReader_Lib_Full+0x18e6fd

003beb18 0128691c FoxitReader_Lib_Full+0x18637a

003beed0 013aefa8 FoxitReader_Lib_Full+0x18691c

通过检查栈上的参数,我们可以看出第一个是图片文件的路径,第二个是将要写入的临时PDF文件。请注意,由于ASLR,下面显示的地址可能与上述模块列表有所不同。

0032e6f0 6a01            push    1

0032e6f2 6a00            push    0

0032e6f4 51              push    ecx                   ; path to temp PDF file

0032e6f5 8bc8            mov     ecx,eax

0032e6f7 8b4604          mov     eax,dword ptr [esi+4]

0032e6fa 52              push    edx                   ; path to JPEG image

0032e6fb ffd0            call    eax

通过在Foxit调用该方法时动态修改参数,我们可以打开任意其他图片。然后通过恢复调用之间的上下文(尤其是x86寄存器),可以快速重复地调用该转换函数。幸运的是,堆上的内容不需要每次恢复。

 

这种方法可用通过多种方式实现自动化。我们可以使用Pintool,但是为了优化我决定写一个特定的工具。

为此,我写了一个小调试器,可以通过传递一个图片作为参数来启动Foxit Reader,并且断点在ConvertToPDF_x86.dll的图片转换函数的对应调用处,以便在下一步中回放上下文。

 CONTEXT ctx;   

...

case EXCEPTION_DEBUG_EVENT:

{

    EXCEPTION_DEBUG_INFO& exception = debug_event.u.Exception;

    switch (exception.ExceptionRecord.ExceptionCode)

    {

        case STATUS_BREAKPOINT:

            ...

            if (IsMyBp())

            {

                SaveContext(&ctx);

                ...

                RunFuzzing(&ctx);

                ...

            }

    }

}

然后调试器注入一个DLLFoxit内存中(通过RunFuzzing()实现),并设置要传给被调用函数的参数。

while(TRUE)

{

    corrupt(image);

 

// call the fonction

    _asm

    {

        push 1

        push 0

        lea  edi, pdf_path

        push edi;

        lea  edi, image_path

        push edi;

        mov  edi, val_edi

        mov  esi, val_esi

        mov  ecx, val_ecx

        mov  ebx, val_ebx

        mov  eax, val_eax

        mov  edx, val_edx

        call eax

    }

}

Intel Xeon E3-1230v3 (3.3 GHz) 机器上,基于该Fuzzing方法,我们达到了150~300 份测试每秒的效果。重要的是,请注意,该Fuzzing必须在Foxit的进程中执行,手动调用该DLL插件将不会生效。

Fuzzing结果

即使是简单的位翻转,也会有很多crash快速产生,其中一些可以被利用。在进行了3天的Fuzzing后,发现了下面的这些crash

 eax=11ba0020 ebx=25000007 ecx=ec54a4e6 edx=11ba0020 esi=11544060 edi=25000007

eip=5cc76ff3 esp=003c8b10 ebp=003c8b18 iopl=0         nv up ei pl nz na po nc

cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00010202

ConvertToPDF_x86!CreateFXPDFConvertor+0x2ba793:

5cc76ff3 8a19            mov     bl,byte ptr [ecx]         ds:002b:ec54a4e6=??
eax=1e7df002 ebx=1e7df000 ecx=1e7df002 edx=1e7df000 esi=1c7bdfc0 edi=1e7e0ff8

eip=6735d9a6 esp=00399750 ebp=00399750 iopl=0         nv up ei ng nz na pe cy

cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00010287

ConvertToPDF_x86!CreateFXPDFConvertor+0x192eb6:

6735d9a6 0fb601          movzx   eax,byte ptr [ecx]         ds:002b:1e7df002=??
eax=7b2e0ee2 ebx=1c59cfc8 ecx=00000001 edx=52cf0002 esi=00000000 edi=1f20fff8

eip=67e399e8 esp=035f9854 ebp=035f985c iopl=0         nv up ei ng nz ac pe cy

cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00010297

ConvertToPDF_x86!CreateFXPDFConvertor+0x2deef8:

67e399e8 8808            mov     byte ptr [eax],cl         ds:002b:7b2e0ee2=??
eax=00000000 ebx=44436fb0 ecx=61f3dbf7 edx=431e1078 esi=00000000 edi=44438fb8

eip=620ba719 esp=00309efc ebp=00309f20 iopl=0         nv up ei pl zr na pe nc

cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00010246

ConvertToPDF_x86!CreateFXPDFConvertor+0x2dfc29:

620ba719 837e0800        cmp     dword ptr [esi+8],0  ds:002b:00000008=????????
eax=00000000 ebx=56bc8fb8 ecx=67fae147 edx=42551078 esi=00000000 edi=00000000

eip=6812b468 esp=00219788 ebp=002197b8 iopl=0         nv up ei pl zr na pe nc

cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00210246

ConvertToPDF_x86!CreateFXPDFConvertor+0x2e0978:

6812b468 397e08          cmp     dword ptr [esi+8],edi ds:002b:00000008=????????
eax=00000000 ebx=000002fa ecx=00000060 edx=44b57f7f esi=003f9d5c edi=44b57fbf

eip=69885b61 esp=003f9d08 ebp=003f9d1c iopl=0         nv up ei pl nz na pe nc

cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00210206

ConvertToPDF_x86!CreateFXPDFConvertor+0x1bb071:

69885b61 8a5c0302        mov     bl,byte ptr [ebx+eax+2]    ds:002b:000002fc=??

你可以在这里下载(http://www.hdwsec.fr/en/blog/foxit_crashes.zip

 

Conclusion(结论)

这种方法可以用于任意软件,只要在调用目标函数(或一组函数)前能够轻松地再现软件的状态。在我看来这也是需要克服的最大障碍。

ConvertToPDF_x86的例子是非常简单的,但是在许多其他情况下,需要注意内存分配、释放和全局状态的改变(或初始化程序)。针对这个目的Pintool就变得非常有用,而且很可能是一个有趣的进一步研究的方向。

请注意,我们可以通过hook插件的读/写访问来优化该Fuzzing方法,从而避免执行过程中在磁盘上写入任何文件。

 

References:

[1] American Fuzzy Lop, http://lcamtuf.coredump.cx/afl/

[2] Foxit Reader, https://www.foxitsoftware.com/products/pdf-reader/

[3] Pintool, https://software.intel.com/en-us/articles/pin-a-dynamic-binary-instrumentation-tool

 


上传的附件 044.以福昕阅读器为例实现高性能Fuzz Applied high-speed in-process fuzzing. the case of Foxit Reader.pdf

注意:上传附件及图片大小不得大于30M。

⚠️ 版权声明:
本博客所有内容(含教程、源码、工具)仅供个人技术学习与研究交流使用,严禁商用、倒卖、二次分发及非法用途
未经作者书面授权,任何组织或个人不得转载、复制或用于其他平台,违者将追究相关责任。

0 0 0 举报
复制成功