Closed Bug 1274637 (CVE-2016-2837) Opened 8 years ago Closed 8 years ago

ZDI-CAN-3766: Mozilla Firefox ClearKeyDecryptor Heap Buffer Overflow Remote Code Execution Vulnerability

Categories

(Core :: Audio/Video: Playback, defect, P1)

defect

Tracking

()

RESOLVED FIXED
mozilla50
Tracking Status
firefox46 --- wontfix
firefox47 --- wontfix
firefox48 + fixed
firefox49 + fixed
firefox-esr38 --- wontfix
firefox-esr45 48+ fixed
firefox50 + fixed

People

(Reporter: abillings, Assigned: mozbugz)

References

Details

(Keywords: csectype-bounds, sec-high, Whiteboard: [adv-main48+][adv-esr45.3+])

Attachments

(2 files)

Attached file ZDI POC
We received the following report from Trending Micro's Zero Day
Initiative (ZDI):

ZDI-CAN-3766: Mozilla Firefox ClearKeyDecryptor Heap Buffer Overflow
Remote Code Execution Vulnerability

-- CVSS -----------------------------------------

6.8, AV:N/AC:M/Au:N/C:P/I:P/A:P

-- ABSTRACT -------------------------------------

Trend Micro's Zero Day Initiative has identified a vulnerability
affecting the following products:

  Mozilla Firefox


-- VULNERABILITY DETAILS ------------------------

Tested against Firefox 45.0.2 on Windows 8.1

```
(984.bac): Access violation - code c0000005 (first chance)
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
eax=0253170d ebx=0252effd ecx=0000270d edx=00002710 esi=0252f000
edi=05174ffb
eip=672af26a esp=063efab8 ebp=05174ff8 iopl=0         nv up ei pl nz ac
pe cy
cs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000
efl=00010217
clearkey!memcpy+0x2a:
672af26a f3a4            rep movs byte ptr es:[edi],byte ptr [esi]
0:004> kv
ChildEBP RetAddr  Args to Child
063efabc 672a36fb 05174ff8 0252effd 00002710 clearkey!memcpy+0x2a (FPO:
[3,0,2]) (CONV: cdecl) [f:\dd\vctools\crt\crtw32\string\i386\memcpy.asm
@ 188]
063efb04 672a366e 0252eff8 00000004 00000000
clearkey!ClearKeyDecryptor::Decrypt+0x5c (FPO: [3,10,0]) (CONV:
thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\media\gmp-clearkey\0.1\clearkeydecryptionmanager.cpp
@ 182]
063efb20 672a5e2a 02200fa8 02200fcc 063efb90
clearkey!ClearKeyDecryptionManager::Decrypt+0x3b (FPO: [2,0,4]) (CONV:
thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\media\gmp-clearkey\0.1\clearkeydecryptionmanager.cpp
@ 138]
063efb48 672ab4ec 02200fa8 5ca1ff99 03109450
clearkey!VideoDecoder::DecodeTask+0x84 (FPO: [Non-Fpo]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\media\gmp-clearkey\0.1\videodecoder.cpp
@ 167]
063efb50 5ca1ff99 03109450 5b9cfd3d 063efc88
clearkey!gmp_task_args_m_1<VideoDecoder *,void (__thiscall
VideoDecoder::*)(VideoDecoder::DecodeData *),VideoDecoder::DecodeData
*>::Run+0xe (FPO: [0,0,0]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\media\gmp-clearkey\0.1\gmp-task-utils-generated.h
@ 133]
063efb58 5b9cfd3d 063efc88 0311b8e0 063efbc0
xul!mozilla::gmp::Runnable::Run+0xb (FPO: [0,0,4]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\dom\media\gmp\gmpplatform.cpp
@ 41]
063efbc0 5b9cf5d1 063efc88 063efc88 03104b08
xul!MessageLoop::DoWork+0x19c (FPO: [Non-Fpo]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\ipc\chromium\src\base\message_loop.cc
@ 459]
063efc08 5b9cfff3 063efc88 0ff0bb96 5bca3c39
xul!base::MessagePumpDefault::Run+0x2e (FPO: [Non-Fpo]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\ipc\chromium\src\base\message_pump_default.cc
@ 35]
063efc40 5b9d0039 03104b1c 00000001 7503ef00
xul!MessageLoop::RunHandler+0x20 (FPO: [SEH]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\ipc\chromium\src\base\message_loop.cc
@ 228]
063efc60 5c026784 5bca3c39 063efd5c 03119610 xul!MessageLoop::Run+0x19
(FPO: [Non-Fpo]) (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\ipc\chromium\src\base\message_loop.cc
@ 202]
063efd44 5bca3c42 770f4198 03104b08 770f4170
xul!base::Thread::ThreadMain+0x382b3d (CONV: thiscall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\ipc\chromium\src\base\thread.cc
@ 175]
063efd48 770f4198 03104b08 770f4170 ba9c818e xul!`anonymous
namespace'::ThreadFunc+0x9 (FPO: [1,0,0]) (CONV: stdcall)
[c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\ipc\chromium\src\base\platform_thread_win.cc
@ 27]
063efd5c 77722cb1 03104b08 100f92e3 00000000
KERNEL32!BaseThreadInitThunk+0x24 (FPO: [Non-Fpo])
063efda4 77722c7f ffffffff 7774e75f 00000000
ntdll!__RtlUserThreadStart+0x2b (FPO: [SEH])
063efdb4 00000000 5bca3c39 03104b08 00000000
ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])
0:004> !lmi clearkey
Loaded Module Info: [clearkey]
         Module: clearkey
   Base Address: 672a0000
     Image Name: C:\Program Files\Mozilla
Firefox\gmp-clearkey\0.1\clearkey.dll
   Machine Type: 332 (I386)
     Time Stamp: 57070eac Thu Apr 07 18:51:40 2016
           Size: 32000
       CheckSum: 33f5d
Characteristics: 2122
Debug Data Dirs: Type  Size     VA  Pointer
             CODEVIEW    82, 297a8,   27fa8 RSDS - GUID:
{94D222EF-9D7F-45FF-81C0-C0F16ADA8872}
               Age: 2, Pdb:
c:\builds\moz2_slave\rel-m-rel-w32_bld-000000000000\build\obj-firefox\media\gmp-clearkey\0.1\clearkey.pdb
                   ??    14, 2982c,   2802c [Data not mapped]
                CLSID     4, 29840,   28040 [Data not mapped]
     Image Type: MEMORY   - Image read successfully from loaded memory.
    Symbol Type: PDB      - Symbols loaded successfully from image header.

z:\export\symbols\clearkey.pdb\94D222EF9D7F45FF81C0C0F16ADA88722\clearkey.pdb
       Compiler: Linker - front end [0.0 bld 0] - back end [12.0 bld 30723]
    Load Report: private symbols & lines, source indexed

z:\export\symbols\clearkey.pdb\94D222EF9D7F45FF81C0C0F16ADA88722\clearkey.pdb
0:004> lmvm clearkey
start    end        module name
672a0000 672d2000   clearkey   (private pdb symbols)
z:\export\symbols\clearkey.pdb\94D222EF9D7F45FF81C0C0F16ADA88722\clearkey.pdb
    Loaded symbol image file: C:\Program Files\Mozilla
Firefox\gmp-clearkey\0.1\clearkey.dll
    Image path: C:\Program Files\Mozilla
Firefox\gmp-clearkey\0.1\clearkey.dll
    Image name: clearkey.dll
    Timestamp:        Thu Apr 07 18:51:40 2016 (57070EAC)
    CheckSum:         00033F5D
    ImageSize:        00032000
    File version:     45.0.2.5941
    Product version:  45.0.2.5941
    File flags:       0 (Mask 3F)
    File OS:          4 Unknown Win32
    File type:        2.0 Dll
    File date:        00000000.00000000
    Translations:     0000.04b0
    CompanyName:      Mozilla Foundation
    ProductName:      Firefox
    InternalName:     Firefox
    OriginalFilename: clearkey.dll
    ProductVersion:   45.0.2
    FileVersion:      45.0.2
    FileDescription:  45.0.2
    LegalCopyright:   License: MPL 2
    LegalTrademarks:  Mozilla
    Comments:         Mozilla
0:004> vertarget
Windows 8 Version 9600 UP Free x86 compatible
Product: WinNt, suite: SingleUserTS
kernel32.dll version: 6.3.9600.17415 (winblue_r4.141028-1500)
Machine Name:
Debug session time: Mon Apr 18 12:07:56.520 2016 (UTC - 7:00)
System Uptime: 0 days 2:05:09.672
Process Uptime: 0 days 0:00:57.841
  Kernel time: 0 days 0:00:00.046
  User time: 0 days 0:00:00.031
```


-- CREDIT ---------------------------------------

This vulnerability was discovered by:

   Anonymous working with Trend Micro's Zero Day Initiative

----
The readme on the POC states:

Firefox 45.0.1 ClearKeyDecryptor::Decrypt() (media/gmp-clearkey/0.1/ClearKeyDecryptionManager.cpp) heap overflow.

The problem is that we fully control aBufferSize, ClearBytes and CipherBytes arrays.
To debug you will need to attach to plugin-container.exe (clearkey.dll should be loaded).

How to test:
1) copy all files from this directory to www dir
2) open index.html
3) alert will pop up, attach to plugin-container.exe
4) back to firefox, press OK to continue
Detect OOB copy attempts in clearkey decryptor.

This detects the issue quite late in the decryption process, on the child side.
Chris, should we investigate ways to prevent this issue from the parent side? (This would protect other GMPs against this attack, in case they don't check for it either.)
Assignee: nobody → gsquelart
Attachment #8756939 - Flags: review?(cpearce)
Attachment #8756939 - Flags: review?(cpearce) → review+
Comment on attachment 8756939 [details] [diff] [review]
1274637-detect-oob-copy-attempts-in-clearkey-decryptor.patch

[Security approval request comment]
How easily could an exploit be constructed based on the patch? Not that obvious (to me). The attacker would have to trace back where the parameters come from, then tailor a video file to give tricky values there. I'm not so sure there's a remote-code-execution possibility, as the target buffer is on the heap.
Also, this is in the GMP, which runs inside a sandbox, making it harder to do real harm.

Do comments in the patch, the check-in comment, or tests included in the patch paint a bulls-eye on the security problem?
The comments and code point at the reading-past-the-end issue, not about the writing part, so it's hiding the problem a bit.

Which older supported branches are affected by this flaw?
All of them (code landed in FF35, Sept 2014)

Do you have backports for the affected branches? If not, how different, hard to create, and risky will they be?
It applies cleanly to aurora and beta. Easy to rebase for release and ESRs, if needed.

How likely is this patch to cause regressions; how much testing does it need?
I'd like to say zero chance of regression, as it's a simple test followed by an early return. No special testing needed apart from checking that the POC now fails gracefully.

* One extra note though:
It is possible that the same vulnerability affects the Adobe GMP, as I believe they have based their initial code on ours, and this part could be something they have just copied blindly (the Adobe-specific changes would start a bit lower in that function).
Chris, what do you think?
Flags: needinfo?(cpearce)
Attachment #8756939 - Flags: sec-approval?
This needs a security rating before you know if it needs sec-approval to go in. https://wiki.mozilla.org/Security/Bug_Approval_Process

That said, it has missed the 47 window and, even if approved, wouldn't go in until June 21 (two weeks into the next cycle).
(In reply to Al Billings [:abillings] from comment #3)
> This needs a security rating before you know if it needs sec-approval to go
> in. https://wiki.mozilla.org/Security/Bug_Approval_Process

That wiki page says:
> For security bugs with no sec- severity rating assume the worst and follow the rules for sec-critical.
> [...]
> if the bug has a patch *and* is sec-high or sec-critical, the developer should set the sec-approval flag to '?' on the patch
And
> If you have a patch and the bug is a hidden core-security bug with no rating then either:
>   1. request sec-approval (to be safe) and wait for a rating,
And
> If developers are unsure about a bug and it has a patch ready, just mark the sec-approval flag to '?' and move on.

All this tells me I was allowed to request sec-approval before knowing the exact sec-rating. Did I misread?


If I were to rate the bug, I'd probably go with sec-high: I'm not so sure about the code execution possibility, but even if it was possible, it would be contained in a plugin in a sandbox, making it harder to cause more harm.
(In reply to Gerald Squelart [:gerald] (may be slow to respond) from comment #2)
> * One extra note though:
> It is possible that the same vulnerability affects the Adobe GMP, as I
> believe they have based their initial code on ours, and this part could be
> something they have just copied blindly (the Adobe-specific changes would
> start a bit lower in that function).
> Chris, what do you think?


I think it's unlikely that the Adobe GMP is also vulnerable to this; their DRM robustness requirements should have required them to *not* use a copy of our decrypt loop here in their own decrypt code. In fact, IIRC they don't support decrypt-only mode, so that code path shouldn't be hit even if they copied it.
Flags: needinfo?(cpearce)
(In reply to Gerald Squelart [:gerald] (PTO until 2016-06-13) from comment #4)

> All this tells me I was allowed to request sec-approval before knowing the
> exact sec-rating. Did I misread?

My bad. I'd forgotten I'd put that in there. I'll make this sec-high. 

This is too late for 47 in any case (since we're about to make final builds) so this won't be able to check in until June 21, two weeks into the next cycle.
Keywords: sec-high
Whiteboard: [checkin on 6/21]
Attachment #8756939 - Flags: sec-approval? → sec-approval+
We'll want branch patches for affected branches once it goes into trunk.
The attached patch still applies cleanly to central, aurora, beta, and esr45, so it's ready to go.
It is okay to land this now.
Keywords: checkin-needed
https://hg.mozilla.org/mozilla-central/rev/118345cddce0
Status: NEW → RESOLVED
Closed: 8 years ago
Resolution: --- → FIXED
Target Milestone: --- → mozilla50
Group: media-core-security → core-security-release
Hi Gerald, could you please nominate the patch for uplift to Beta, Aurora and ESR45? I could do it for you but I'd like to get your thoughts on risk, test coverage and whether this is easily exploitable or not. Thanks!
Flags: needinfo?(gsquelart)
Comment on attachment 8756939 [details] [diff] [review]
1274637-detect-oob-copy-attempts-in-clearkey-decryptor.patch

Approval Request Comment
[Feature/regressing bug #]: Clearkey media playback.
[User impact if declined]: Potential RCE in sandboxed plugin.
[Describe test coverage new/current, TreeHerder]: Locally tested by running the POC; landed in Nightly for a week.
[Risks and why]: I'd like to say none, this is a simple past-the-end test resulting in early function exit with an error code.
[String/UUID change made/needed]: None.


[ESR Approval Request Comment]
If this is not a sec:{high,crit} bug, please state case for ESR consideration:
User impact if declined: sec-high.
Fix Landed on Version: 50.
Risk to taking this patch (and alternatives if risky): No risks that I can see.
String or UUID changes made by this patch: None.

See https://wiki.mozilla.org/Release_Management/ESR_Landing_Process for more info.


(In reply to Ritu Kothari (:ritu) from comment #12)
> Hi Gerald, could you please nominate the patch for uplift to Beta, Aurora
> and ESR45? I could do it for you but I'd like to get your thoughts on risk,
> test coverage and whether this is easily exploitable or not. Thanks!

This patch applies as-is on Aurora, Beta, and ESR45.
As I wrote above, I personally don't see any risk with this patch.
As to the exploitability, I think it would be difficult to exploit, as the overwritten buffer is in heap space (not stack); Also it is in a plugin running in a sandbox, so should the issue be exploitable, it would (hopefully) require a lot of work to be able to cause any real harm outside of the video playback.
Flags: needinfo?(gsquelart)
Attachment #8756939 - Flags: approval-mozilla-esr45?
Attachment #8756939 - Flags: approval-mozilla-beta?
Attachment #8756939 - Flags: approval-mozilla-aurora?
Comment on attachment 8756939 [details] [diff] [review]
1274637-detect-oob-copy-attempts-in-clearkey-decryptor.patch

Sec-high issue, Aurora49+, Beta48+, ESR45+
Attachment #8756939 - Flags: approval-mozilla-esr45?
Attachment #8756939 - Flags: approval-mozilla-esr45+
Attachment #8756939 - Flags: approval-mozilla-beta?
Attachment #8756939 - Flags: approval-mozilla-beta+
Attachment #8756939 - Flags: approval-mozilla-aurora?
Attachment #8756939 - Flags: approval-mozilla-aurora+
Flags: qe-verify+
Alias: CVE-2016-2837
Whiteboard: [adv-main48+][adv-esr45.3+]
It seems that verifying this bug requires actual debugging, which is not something Manual QA does. I'm not seeing any differences between an affected and fixed build by simply running the poc (without following step 3 from Comment 0 completely).

Gerald, Matt - if you think there's some other way for QA to _manually_ confirm the fix pushed for this bug, please set the [qe-verify+] flag back and let me know.
Flags: qe-verify+
Flags: needinfo?(mwobensmith)
Flags: needinfo?(gsquelart)
Mihai, you are correct. Sorry about that. Marking qe-verify- as a result. If Gerald or anyone else has a way to verify this change without debugging, let us know.
Flags: needinfo?(mwobensmith) → qe-verify-
(In reply to Mihai Boldan, QA [:mboldan] from comment #16)
> It seems that verifying this bug requires actual debugging, which is not
> something Manual QA does. I'm not seeing any differences between an affected
> and fixed build by simply running the poc (without following step 3 from
> Comment 0 completely).
> 
> Gerald, Matt - if you think there's some other way for QA to _manually_
> confirm the fix pushed for this bug, please set the [qe-verify+] flag back
> and let me know.

I've just tried on Mac OS X, and I can see a difference:
- With an unpatched FF 47, after opening the POC's index.html and pressing OK, a drop-down notification bar says "The Clearkey plugin has crashed" (most probably due to the unchecked memory copy trying to write outside of its permitted bounds).
- With patched FF 50, 49b, and 48a, there is no such notification, the plugin does not crash.

The crash may be dependent on the OS and other environment factors. Would the QA team be able to try on different platforms?
Flags: needinfo?(gsquelart)
I managed to reproduce this issue following the STR from Comment 0, using Firefox 47.0.1 and on Windows 10 x64. 
I've tested this issue on Firefox 45.3.0 ESR, Firefox 48.0, Firefox 49.0b1, Firefox 50.0a2 (2016-08-08) and on Firefox 51.0a1 (2016-08-08), across platforms [1 ]and I confirm that the notification is no longer displayed and the plugin does not crash.

[1]Windows 10 x64, Mac OS X 10.11.1, Ubuntu 16.04x64
Group: core-security-release
Depends on: CVE-2017-5448
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: