Closed Bug 802902 (CVE-2012-4217) Opened 12 years ago Closed 12 years ago

Heap-use-after-free in nsViewManager::ProcessPendingUpdates

Categories

(Core :: Layout, defect)

x86_64
All
defect
Not set
critical

Tracking

()

RESOLVED FIXED
mozilla19
Tracking Status
firefox16 --- wontfix
firefox17 + fixed
firefox18 + fixed
firefox19 + fixed
firefox-esr10 --- unaffected

People

(Reporter: inferno, Assigned: MatsPalmgren_bugz)

References

Details

(5 keywords, Whiteboard: [asan][adv-track-main17+])

Attachments

(3 files)

Attached file Testcase (deleted) —
Reproduces on trunk. ================================================================= ==12412== ERROR: AddressSanitizer heap-use-after-free on address 0x7fdd01d75fa8 at pc 0x7fdd18f484cc bp 0x7fffb2f66e10 sp 0x7fffb2f66e08 READ of size 8 at 0x7fdd01d75fa8 thread T0 #0 0x7fdd18f484cb in nsViewManager::ProcessPendingUpdates() view/src/nsViewManager.cpp:1212 #1 0x7fdd1ae3e36b in nsTimerImpl::Fire() xpcom/threads/nsTimerImpl.cpp:475 #2 0x7fdd1ae3e9d6 in nsTimerEvent::Run() xpcom/threads/nsTimerImpl.cpp:555 #3 0x7fdd1ad6baf3 in NS_ProcessNextEvent_P(nsIThread*, bool) objdir-ff-asan/xpcom/build/nsThreadUtils.cpp:220 #4 0x7fdd1a92b6b0 in mozilla::ipc::MessagePump::Run(base::MessagePump::Delegate*) ipc/glue/MessagePump.cpp:82 #5 0x7fdd1aec3bdb in MessageLoop::RunInternal() ipc/chromium/src/base/message_loop.cc:215 #6 0x7fdd1a624ebd in nsBaseAppShell::Run() widget/xpwidgets/nsBaseAppShell.cpp:163 #7 0x7fdd17891a44 in XREMain::XRE_main(int, char**, nsXREAppData const*) toolkit/xre/nsAppRunner.cpp:3858 #8 0x7fdd17892b1a in XRE_main toolkit/xre/nsAppRunner.cpp:3933 #9 0x408d75 in do_main(int, char**) browser/app/nsBrowserApp.cpp:174 #10 0x7fdd219e876c in __libc_start_main /build/buildd/eglibc-2.15/csu/libc-start.c:226 0x7fdd01d75fa8 is located 40 bytes inside of 64-byte region [0x7fdd01d75f80,0x7fdd01d75fc0) freed by thread T0 here: #0 0x432e00 in free #1 0x7fdd18f3ebac in nsViewManager::Release() view/src/nsViewManager.cpp:125 #2 0x7fdd19eaf9d8 in nsDocShell::Destroy() docshell/base/nsDocShell.cpp:4897 #3 0x7fdd19eaff5c in non-virtual thunk to nsDocShell::Destroy() :0 #4 0x7fdd1a06e13d in nsWebShellWindow::Destroy() xpfe/appshell/src/nsWebShellWindow.cpp:750 #5 0x7fdd18ff4fec in nsGlobalWindow::ReallyCloseWindow() dom/base/nsGlobalWindow.cpp:6734 #6 0x7fdd18ff433f in nsGlobalWindow::FinalClose() dom/base/nsGlobalWindow.cpp:6681 #7 0x7fdd18ff3ca2 in nsGlobalWindow::Close() dom/base/nsGlobalWindow.cpp:6624 #8 0x7fdd18ff3811 in nsGlobalWindow::Close() dom/base/nsGlobalWindow.cpp:6559 #9 0x7fdd1ae734a9 in NS_InvokeByIndex_P xpcom/reflect/xptcall/src/md/unix/xptcinvoke_x86_64_unix.cpp:162 #10 0x7fdd19bee7c9 in CallMethodHelper::Invoke() js/xpconnect/src/XPCWrappedNative.cpp:3108 #11 0x7fdd19c02dc8 in XPC_WN_CallMethod(JSContext*, unsigned int, JS::Value*) js/xpconnect/src/XPCWrappedNativeJSOps.cpp:1488 #12 0x7fdd1c0e3148 in JSFunction::native() const js/src/jscntxtinlines.h:364 #13 0x7fdd1c0e40b7 in js::Invoke(JSContext*, js::InvokeArgsGuard&, js::MaybeConstruct) js/src/jsinterp.h:109 #14 0x7fdd1c1c8527 in js::IndirectProxyHandler::call(JSContext*, JSObject*, unsigned int, JS::Value*) js/src/jsproxy.cpp:450 #15 0x7fdd1c32730d in js::DirectWrapper::call(JSContext*, JSObject*, unsigned int, JS::Value*) js/src/jswrapper.cpp:390 #16 0x7fdd1c327639 in non-virtual thunk to js::CrossCompartmentWrapper::call(JSContext*, JSObject*, unsigned int, JS::Value*) #17 0x7fdd1c0e3289 in js::CallJSNative(JSContext*, int (*)(JSContext*, unsigned int, JS::Value*), JS::CallArgs const&) js/src/jscntxtinlines.h:364 #18 0x7fdd1c0d30d9 in js::Interpret(JSContext*, js::StackFrame*, js::InterpMode) js/src/jsinterp.cpp:2370 #19 0x7fdd1c0bdf33 in js::RunScript(JSContext*, JS::Handle<JSScript*>, js::StackFrame*) js/src/jsinterp.cpp:324 #20 0x7fdd1c0e3038 in js::InvokeKernel(JSContext*, JS::CallArgs, js::MaybeConstruct) js/src/jsinterp.cpp:378 #21 0x7fdd1c040be0 in js::Invoke(JSContext*, js::InvokeArgsGuard&, js::MaybeConstruct) js/src/jsinterp.h:109 #22 0x7fdd1c0e3148 in JSFunction::native() const js/src/jscntxtinlines.h:364 #23 0x7fdd1c0d30d9 in js::Interpret(JSContext*, js::StackFrame*, js::InterpMode) js/src/jsinterp.cpp:2370 #24 0x7fdd1c0bdf33 in js::RunScript(JSContext*, JS::Handle<JSScript*>, js::StackFrame*) js/src/jsinterp.cpp:324 #25 0x7fdd1c0e3038 in js::InvokeKernel(JSContext*, JS::CallArgs, js::MaybeConstruct) js/src/jsinterp.cpp:378 #26 0x7fdd1c0e40b7 in js::Invoke(JSContext*, js::InvokeArgsGuard&, js::MaybeConstruct) js/src/jsinterp.h:109 #27 0x7fdd1c1c8527 in js::IndirectProxyHandler::call(JSContext*, JSObject*, unsigned int, JS::Value*) js/src/jsproxy.cpp:450 #28 0x7fdd1c32730d in js::DirectWrapper::call(JSContext*, JSObject*, unsigned int, JS::Value*) js/src/jswrapper.cpp:390 #29 0x7fdd1c327639 in non-virtual thunk to js::CrossCompartmentWrapper::call(JSContext*, JSObject*, unsigned int, JS::Value*) previously allocated by thread T0 here: #0 0x432ec0 in __interceptor_malloc #1 0x7fdd1ee8d228 in moz_xmalloc memory/mozalloc/mozalloc.cpp:57 Shadow byte and word: 0x1ffba03aebf5: fd 0x1ffba03aebf0: fd fd fd fd fd fd fd fd More shadow bytes: 0x1ffba03aebd0: 00 00 00 01 fb fb fb fb 0x1ffba03aebd8: fb fb fb fb fb fb fb fb 0x1ffba03aebe0: fa fa fa fa fa fa fa fa 0x1ffba03aebe8: fa fa fa fa fa fa fa fa =>0x1ffba03aebf0: fd fd fd fd fd fd fd fd 0x1ffba03aebf8: fd fd fd fd fd fd fd fd 0x1ffba03aec00: fa fa fa fa fa fa fa fa 0x1ffba03aec08: fa fa fa fa fa fa fa fa 0x1ffba03aec10: fd fd fd fd fd fd fd fd Stats: 289M malloced (302M for red zones) by 407162 calls Stats: 35M realloced by 20307 calls Stats: 252M freed by 260279 calls Stats: 121M really freed by 107074 calls Stats: 500M (128096 full pages) mmaped in 125 calls mmaps by size class: 8:262128; 9:32764; 10:12285; 11:12282; 12:3072; 13:2048; 14:1280; 15:256; 16:576; 17:1280; 18:288; 19:40; 20:32; 21:4; mallocs by size class: 8:326930; 9:43810; 10:12490; 11:13674; 12:3072; 13:2374; 14:1671; 15:339; 16:815; 17:1616; 18:297; 19:40; 20:31; 21:3; frees by size class: 8:201346; 9:31687; 10:7929; 11:10578; 12:2184; 13:2179; 14:1470; 15:284; 16:725; 17:1600; 18:228; 19:39; 20:27; 21:3; rfrees by size class: 8:79435; 9:13591; 10:2500; 11:7030; 12:870; 13:866; 14:1033; 15:156; 16:460; 17:1116; 18:11; 19:5; 20:1; Stats: malloc large: 1987 small slow: 2137
Managed to get a crash. Um, few bugs here. http://mxr.mozilla.org/mozilla-central/source/layout/base/nsRefreshDriver.cpp?rev=3de1ec1e38cf&mark=431-431#425 doesn't ensure the viewmanager stays alive. nsViewManager::ProcessPendingUpdates() is all scary. CallWillPaintOnObservers(true); flushes, so things which aren't kept explicitly alive can be dead. And in this case for some reason mRootView is deleted http://mxr.mozilla.org/mozilla-central/source/view/src/nsViewManager.cpp?rev=eaccb5bb50c0&mark=1213-1213#1199 (Could be that the viewmanager itself is dead at that point)
Oh, right, I got the crash when shutting down the browser. So it is the top level presshell and its viewmanager which are dead.
Severity: normal → critical
Component: General → Layout
Product: Firefox → Core
Whiteboard: [asan]
Thanks for the quick triage! Assigning to Mats, please reassign as necessary. Any help marking status tracking (FF versions affected) appreciated.
Assignee: nobody → matspal
Attached file stacks (deleted) —
1st stack: Destroy of the shell involved in RefreshDriver::Notify in stack frame #61 2nd stack: ~nsViewManager of the view manager involved in same RefreshDriver::Notify 3rd stack: ASAN error when touching mRootView of that dead view manager
I strongly suspect it's a regression from bug 598482 which added this code in RefreshDriver: http://hg.mozilla.org/mozilla-central/rev/2d5e31af7e3e If so, it affects all branches except esr10.
Attached patch fix (deleted) — Splinter Review
The fix is the strong ref in RefreshDriver. I added strong refs for the WillPaintWindow and DidPaintWindow calls as well, just in case.
Attachment #673110 - Flags: review?(roc)
Comment on attachment 673110 [details] [diff] [review] fix The fix is very low risk. We should take this on all branches where it applies.
Attachment #673110 - Flags: sec-approval?
Attachment #673110 - Flags: approval-mozilla-beta?
Attachment #673110 - Flags: approval-mozilla-aurora?
Comment on attachment 673110 [details] [diff] [review] fix sec-approval+
Attachment #673110 - Flags: sec-approval? → sec-approval+
Status: NEW → RESOLVED
Closed: 12 years ago
Resolution: --- → FIXED
Target Milestone: --- → mozilla19
Attachment #673110 - Flags: approval-mozilla-beta?
Attachment #673110 - Flags: approval-mozilla-beta+
Attachment #673110 - Flags: approval-mozilla-aurora?
Attachment #673110 - Flags: approval-mozilla-aurora+
Whiteboard: [asan] → [asan][adv-track-main17+]
Keywords: verifyme
Alias: CVE-2012-4217
Flags: sec-bounty?
This bug qualifies for a security bug bounty.
Flags: sec-bounty? → sec-bounty+
Attachment #683338 - Attachment description: Bug Bounty Awarded $3000 → Bug Bounty Awarded $3000 [paid]
Group: core-security
Flags: in-testsuite? → in-testsuite+
mass remove verifyme requests greater than 4 months old
Keywords: verifyme
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Creator:
Created:
Updated:
Size: