[CAL-20090611-1]Adobe Reader JpxDecode Memory Corruption Vulnerability

CVE ID: CVE-2009-3955
Affected Products
=================
Adobe Reader 9.2 ( last updated)
(All previous versions expected to be vulnerable)

Vulnerability Details
=====================

This vulnerability allows remote attackers to execute arbitrary code on
vulnerable installations of Adobe Acrobat and Adobe Reader. User
interaction is required to exploit this vulnerability in that the target
must visit a malicious web address or open a malicious file.

Code Audit Labs http://www.vulnhunt.com has discovered in Adobe
Acrobat/Reader.  The Adobe Acrobat/Reader products contain a memory
corruption vulnerability in the code responsible for parsing the
Jp2c stream of JpxDecode-encoded data streams within a PDF file. This
vulnerability can be exploited remotely to execute code.

Analysis
=========

during process JPC_MS_RGN stream of jp2c box, there exist a sign extern
(from 16 bits to 32bits) that cause bypass the checking, then cause
memory corruption.

piece of code from JP2KLib.dll.

.text:1003D52C
.text:1003D52C loc_1003D52C:                           ; CODE XREF: sub_1003C8ED+79j
.text:1003D52C                                         ; DATA XREF: .text:off_1003D9F9o
.text:1003D52C                 push    2               ; jumptable 1003C966 case 15
.text:1003D52E                 mov     ecx, ebx
.text:1003D530                 call    get_muti_ubyte
.text:1003D535                 sub     [ebp+var_8], 2
.text:1003D539                 push    2
.text:1003D53B                 mov     ecx, ebx
.text:1003D53D                 mov     byte ptr [edi+7], 1
.text:1003D541                 call    get_muti_ubyte
.text:1003D546                 movzx   esi, ax
.text:1003D549                 movzx   eax, si
.text:1003D54C                 push    eax
.text:1003D54D                 mov     ecx, ebx
.text:1003D54F                 call    check_len_is_ok
.text:1003D554                 test    eax, eax
.text:1003D556                 jnz     loc_1003D9E2
.text:1003D55C                 cmp     si, 5
.text:1003D560                 jnz     short loc_1003D571
.text:1003D562                 sub     [ebp+var_8], 3
.text:1003D566                 push    1
.text:1003D568                 mov     ecx, ebx
.text:1003D56A                 call    get_muti_ubyte
.text:1003D56F                 jmp     short loc_1003D588
.text:1003D571 ; ---------------------------------------------------------------------------
.text:1003D571
.text:1003D571 loc_1003D571:                           ; CODE XREF: sub_1003C8ED+C73j
.text:1003D571                 cmp     si, 6
.text:1003D575                 jnz     loc_1003D9EB
.text:1003D57B                 push    2
.text:1003D57D                 mov     ecx, ebx
.text:1003D57F                 call    get_muti_ubyte
.text:1003D584                 sub     [ebp+var_8], 4
.text:1003D588
.text:1003D588 loc_1003D588:                           ; CODE XREF: sub_1003C8ED+C82j
.text:1003D588                 movsx   eax, ax         ; sign extern to 32bits
.text:1003D58B                 cmp     eax, [edi+4Ch]
.text:1003D58E                 jge     loc_1003D9E2  ; bypass the checking
.text:1003D594                 mov     ecx, [edi+2Ch]
.text:1003D597                 mov     esi, eax
.text:1003D599                 imul    esi, 0Ch
.text:1003D59C                 mov     [esi+ecx], eax  ;//heap corruption
.text:1003D59F                 mov     eax, [edi+2Ch]
.text:1003D5A2                 push    1
.text:1003D5A4                 mov     ecx, ebx
.text:1003D5A6                 mov     byte ptr [esi+eax+8], 1;//heap corruption
.text:1003D5AB                 call    get_muti_ubyte
.text:1003D5B0                 test    al, 1
.text:1003D5B2                 jnz     loc_1003D9EB
.text:1003D5B8                 push    1
.text:1003D5BA                 mov     ecx, ebx
.text:1003D5BC                 call    get_muti_ubyte
.text:1003D5C1                 mov     ecx, [edi+2Ch]
.text:1003D5C4                 dec     [ebp+var_8]
.text:1003D5C7                 mov     [esi+ecx+4], eax ;//heap corruption
.text:1003D5CB                 jmp     loc_1003C910

EXPLOIT? high exploitable!!
==========================

as above analysis, the vulnerabiliy code like

DWORD a_heap=malloc();//from [edi+2Ch]
short len1=get_muti_ubyte(2);
int len = len1;
if ( len <0)//bypass checking
{
DWORD esi = len*0×0c; //can integer overflow again, almost, we can full control esi
*(DWORD *)(a_heap+esi)=len;  //at 1003D59C
*(char *)(a_heap+esi+8)=1;   //at 1003D5A6
*(DWORD *)(a_heap+esi+4)= get_muti_ubyte(1);  //at 1003D5C7 arbitrary a byte

}

so almostly , we can rewrite arbitrary memory with limited value.

there are two kinds method to improve exploit stability
1: muti JPC_MS_RGN streams of jp2c box which can muti rewrite different memory address.
2: using javascript heap spray

POC
===
if u want to get it, please drop a email to  code_audit_labs [ @  ]  vulnhunt.com

About Code Audit Labs:
=====================
Code Audit Labs is department of VulnHunt company which provide a
professional security testing products / services / security consulting
and training ,we sincerely hope we can help your procudes to improve code
quality and safety.
WebSite http://www.VulnHunt.com