Closed Bug 1765343 Opened 3 years ago Closed 3 years ago

AddressSanitizer: use-after-poison [@ GetTenuredGCThingZone] with READ of size 8

Categories

(Core :: DOM: Streams, defect, P1)

x86_64
Linux
defect

Tracking

()

RESOLVED FIXED
101 Branch
Tracking Status
firefox-esr91 --- unaffected
firefox99 --- unaffected
firefox100 + fixed
firefox101 + fixed

People

(Reporter: jkratzer, Assigned: mgaudet)

References

(Blocks 1 open bug, Regression)

Details

(4 keywords, Whiteboard: [bugmon:confirm])

Attachments

(2 files)

Found while fuzzing mozilla-central rev 61d8c578d367 (built with: --enable-address-sanitizer --enable-fuzzing).

I've seen a number of crashes like this recently that occur in garbage collection after cleaning up a writable stream. I don't currently have a reliable testcase, nor have I been able to get a pernosco session but, I will attach it here if one is found.

AddressSanitizer: use-after-poison [@ GetTenuredGCThingZone] with READ of size 8

    =================================================================
    ==332==ERROR: AddressSanitizer: use-after-poison on address 0x176ca48bf008 at pc 0x7fc56e041493 bp 0x7ffddb0fa400 sp 0x7ffddb0fa3f8
    READ of size 8 at 0x176ca48bf008 thread T0 (Isolated Web Co)
        #0 0x7fc56e041492 in GetTenuredGCThingZone /builds/worker/workspace/obj-build/dist/include/js/HeapAPI.h:533:10
        #1 0x7fc56e041492 in GetTenuredGCThingZone /builds/worker/workspace/obj-build/dist/include/js/HeapAPI.h:648:10
        #2 0x7fc56e041492 in ExposeGCThingToActiveJS /builds/worker/workspace/obj-build/dist/include/js/HeapAPI.h:764:39
        #3 0x7fc56e041492 in ExposeValueToActiveJS /builds/worker/workspace/obj-build/dist/include/js/Value.h:1000:5
        #4 0x7fc56e041492 in js::BarrierMethods<JS::Value, void>::exposeToJS(JS::Value const&) /builds/worker/workspace/obj-build/dist/include/js/Value.h:1191:48
        #5 0x7fc574402614 in exposeToActiveJS /builds/worker/workspace/obj-build/dist/include/js/RootingAPI.h:345:35
        #6 0x7fc574402614 in get /builds/worker/workspace/obj-build/dist/include/js/RootingAPI.h:348:5
        #7 0x7fc574402614 in operator const JS::Value & /builds/worker/workspace/obj-build/dist/include/js/RootingAPI.h:340:3
        #8 0x7fc574402614 in void mozilla::dom::DequeueValue<mozilla::dom::WritableStreamDefaultController*>(mozilla::dom::WritableStreamDefaultController*, JS::MutableHandle<JS::Value>) /builds/worker/workspace/obj-build/dist/include/mozilla/dom/QueueWithSizes.h:101:20
        #9 0x7fc57440326a in operator() /gecko/dom/streams/WritableStreamDefaultController.cpp:334:13
        #10 0x7fc57440326a in operator() /builds/worker/workspace/obj-build/dist/include/mozilla/dom/Promise-inl.h:313:5
        #11 0x7fc57440326a in CallCallback<(lambda at /builds/worker/workspace/obj-build/dist/include/mozilla/dom/Promise-inl.h:311:7), 0UL> /builds/worker/workspace/obj-build/dist/include/mozilla/dom/Promise-inl.h:207:12
        #12 0x7fc57440326a in CallCallback<(lambda at /builds/worker/workspace/obj-build/dist/include/mozilla/dom/Promise-inl.h:311:7)> /builds/worker/workspace/obj-build/dist/include/mozilla/dom/Promise-inl.h:216:12
        #13 0x7fc57440326a in mozilla::dom::(anonymous namespace)::NativeThenHandler<void mozilla::dom::Promise::AddCallbacksWithCycleCollectedArgs<mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_6, mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_7, RefPtr<mozilla::dom::WritableStreamDefaultController> >(mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_6&&, mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_7&&, RefPtr<mozilla::dom::WritableStreamDefaultController>&&)::'lambda'(JSContext*, JS::Handle<JS::Value>, mozilla::ErrorResult&, RefPtr<mozilla::dom::WritableStreamDefaultController>&&), void mozilla::dom::Promise::AddCallbacksWithCycleCollectedArgs<mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_6, mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_7, RefPtr<mozilla::dom::WritableStreamDefaultController> >(mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_6&&, mozilla::dom::WritableStreamDefaultControllerProcessWrite(JSContext*, mozilla::dom::WritableStreamDefaultController*, JS::Handle<JS::Value>, mozilla::ErrorResult&)::$_7&&, RefPtr<mozilla::dom::WritableStreamDefaultController>&&)::'lambda0'(JSContext*, JS::Handle<JS::Value>, mozilla::ErrorResult&, RefPtr<mozilla::dom::WritableStreamDefaultController>&&), std::tuple<RefPtr<mozilla::dom::WritableStreamDefaultController> >, std::tuple<> >::CallResolveCallback(JSContext*, JS::Handle<JS::Value>, mozilla::ErrorResult&) /builds/worker/workspace/obj-build/dist/include/mozilla/dom/Promise-inl.h:185:12
        #14 0x7fc57435bf77 in mozilla::dom::PromiseNativeThenHandlerBase::ResolvedCallback(JSContext*, JS::Handle<JS::Value>, mozilla::ErrorResult&) /gecko/dom/promise/Promise.cpp:256:29
        #15 0x7fc574366a50 in mozilla::dom::(anonymous namespace)::PromiseNativeHandlerShim::ResolvedCallback(JSContext*, JS::Handle<JS::Value>, mozilla::ErrorResult&) /gecko/dom/promise/Promise.cpp:412:12
        #16 0x7fc5743671e8 in mozilla::dom::NativeHandlerCallback(JSContext*, unsigned int, JS::Value*) /gecko/dom/promise/Promise.cpp
        #17 0x7fc57b6f8034 in CallJSNative /gecko/js/src/vm/Interpreter.cpp:420:13
        #18 0x7fc57b6f8034 in js::InternalCallOrConstruct(JSContext*, JS::CallArgs const&, js::MaybeConstruct, js::CallReason) /gecko/js/src/vm/Interpreter.cpp:507:12
        #19 0x7fc57b6f9d5b in js::Call(JSContext*, JS::Handle<JS::Value>, JS::Handle<JS::Value>, js::AnyInvokeArgs const&, JS::MutableHandle<JS::Value>, js::CallReason) /gecko/js/src/vm/Interpreter.cpp:584:8
        #20 0x7fc57a0d107a in Call /gecko/js/src/vm/Interpreter.h:105:10
        #21 0x7fc57a0d107a in PromiseReactionJob(JSContext*, unsigned int, JS::Value*) /gecko/js/src/builtin/Promise.cpp:2067:10
        #22 0x7fc57b6f8034 in CallJSNative /gecko/js/src/vm/Interpreter.cpp:420:13
        #23 0x7fc57b6f8034 in js::InternalCallOrConstruct(JSContext*, JS::CallArgs const&, js::MaybeConstruct, js::CallReason) /gecko/js/src/vm/Interpreter.cpp:507:12
        #24 0x7fc57b6f9d5b in js::Call(JSContext*, JS::Handle<JS::Value>, JS::Handle<JS::Value>, js::AnyInvokeArgs const&, JS::MutableHandle<JS::Value>, js::CallReason) /gecko/js/src/vm/Interpreter.cpp:584:8
        #25 0x7fc579e41dfd in JS::Call(JSContext*, JS::Handle<JS::Value>, JS::Handle<JS::Value>, JS::HandleValueArray const&, JS::MutableHandle<JS::Value>) /gecko/js/src/vm/CallAndConstruct.cpp:117:10
        #26 0x7fc5704b69dc in mozilla::dom::PromiseJobCallback::Call(mozilla::dom::BindingCallContext&, JS::Handle<JS::Value>, mozilla::ErrorResult&) /builds/worker/workspace/obj-build/dom/bindings/PromiseBinding.cpp:35:8
        #27 0x7fc56c503907 in Call /builds/worker/workspace/obj-build/dist/include/mozilla/dom/PromiseBinding.h:89:12
        #28 0x7fc56c503907 in Call /builds/worker/workspace/obj-build/dist/include/mozilla/dom/PromiseBinding.h:102:12
        #29 0x7fc56c503907 in mozilla::PromiseJobRunnable::Run(mozilla::AutoSlowOperation&) /gecko/xpcom/base/CycleCollectedJSContext.cpp:213:18
        #30 0x7fc56c4e2c17 in mozilla::CycleCollectedJSContext::PerformMicroTaskCheckPoint(bool) /gecko/xpcom/base/CycleCollectedJSContext.cpp:674:17
        #31 0x7fc56c4e3bff in mozilla::CycleCollectedJSContext::AfterProcessTask(unsigned int) /gecko/xpcom/base/CycleCollectedJSContext.cpp:463:3
        #32 0x7fc56e111e66 in XPCJSContext::AfterProcessTask(unsigned int) /gecko/js/xpconnect/src/XPCJSContext.cpp:1483:28
        #33 0x7fc56c727848 in nsThread::ProcessNextEvent(bool, bool*) /gecko/xpcom/threads/nsThread.cpp:1217:24
        #34 0x7fc56c73105c in NS_ProcessNextEvent(nsIThread*, bool) /gecko/xpcom/threads/nsThreadUtils.cpp:465:10
        #35 0x7fc56de41def in mozilla::ipc::MessagePump::Run(base::MessagePump::Delegate*) /gecko/ipc/glue/MessagePump.cpp:85:21
        #36 0x7fc56dcbbdd1 in RunInternal /gecko/ipc/chromium/src/base/message_loop.cc:380:10
        #37 0x7fc56dcbbdd1 in RunHandler /gecko/ipc/chromium/src/base/message_loop.cc:373:3
        #38 0x7fc56dcbbdd1 in MessageLoop::Run() /gecko/ipc/chromium/src/base/message_loop.cc:355:3
        #39 0x7fc574b4b257 in nsBaseAppShell::Run() /gecko/widget/nsBaseAppShell.cpp:137:27
        #40 0x7fc5799e8f2f in XRE_RunAppShell() /gecko/toolkit/xre/nsEmbedFunctions.cpp:870:20
        #41 0x7fc56dcbbdd1 in RunInternal /gecko/ipc/chromium/src/base/message_loop.cc:380:10
        #42 0x7fc56dcbbdd1 in RunHandler /gecko/ipc/chromium/src/base/message_loop.cc:373:3
        #43 0x7fc56dcbbdd1 in MessageLoop::Run() /gecko/ipc/chromium/src/base/message_loop.cc:355:3
        #44 0x7fc5799e8153 in XRE_InitChildProcess(int, char**, XREChildData const*) /gecko/toolkit/xre/nsEmbedFunctions.cpp:729:34
        #45 0x55d22751647d in content_process_main(mozilla::Bootstrap*, int, char**) /gecko/browser/app/../../ipc/contentproc/plugin-container.cpp:57:28
        #46 0x55d2275168b0 in main /gecko/browser/app/nsBrowserApp.cpp:327:18
        #47 0x7fc5914c40b2 in __libc_start_main /build/glibc-sMfBJT/glibc-2.31/csu/../csu/libc-start.c:308:16
        #48 0x55d227465569 in _start (/home/worker/builds/m-c-20220419093010-fuzzing-asan-opt/firefox+0x5e569)
    
    Address 0x176ca48bf008 is a wild pointer inside of access range of size 0x000000000008.
    SUMMARY: AddressSanitizer: use-after-poison /builds/worker/workspace/obj-build/dist/include/js/HeapAPI.h:533:10 in GetTenuredGCThingZone
    Shadow bytes around the buggy address:
      0x02ee1490fdb0: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fdc0: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fdd0: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fde0: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fdf0: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
    =>0x02ee1490fe00: f7[f7]f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fe10: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fe20: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fe30: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fe40: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
      0x02ee1490fe50: f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7 f7
    Shadow byte legend (one shadow byte represents 8 application bytes):
      Addressable:           00
      Partially addressable: 01 02 03 04 05 06 07 
      Heap left redzone:       fa
      Freed heap region:       fd
      Stack left redzone:      f1
      Stack mid redzone:       f2
      Stack right redzone:     f3
      Stack after return:      f5
      Stack use after scope:   f8
      Global redzone:          f9
      Global init order:       f6
      Poisoned by user:        f7
      Container overflow:      fc
      Array cookie:            ac
      Intra object redzone:    bb
      ASan internal:           fe
      Left alloca redzone:     ca
      Right alloca redzone:    cb
    ==332==ABORTING

Looking at that stack, it seems like we're running into a problem loading valueWithSize's mValue

The problem seems to be that despite writing the tracing code for WritableStreamDefaultController, they weren't added to the trace list, so the QueueWithSizes is never getting traced.

I've got a patch.

Assignee: nobody → mgaudet
Status: NEW → ASSIGNED
Severity: -- → S2
Priority: -- → P1

Marking 1759597 as the regressing bug, as that's when it was enabled by default.

Regressed by: 1759597

Comment on attachment 9272864 [details]
Bug 1765343 - Ensure WritableStreamDefaultController gets traced r?evilpie

Security Approval Request

  • How easily could an exploit be constructed based on the patch?: Not easily; would require careful construction of writable stream sequence of operations to get access to potentially cleared value.
  • Do comments in the patch, the check-in comment, or tests included in the patch paint a bulls-eye on the security problem?: Yes
  • Which older supported branches are affected by this flaw?: 100
  • If not all supported branches, which bug introduced the flaw?: Bug 1759597
  • Do you have backports for the affected branches?: No
  • If not, how different, hard to create, and risky will they be?: Patch should be upliftable.
  • How likely is this patch to cause regressions; how much testing does it need?: Should cause no regressions, only improving GC tracing.
Attachment #9272864 - Flags: sec-approval?

Set release status flags based on info from the regressing bug 1759597

Has Regression Range: --- → yes

Comment on attachment 9272864 [details]
Bug 1765343 - Ensure WritableStreamDefaultController gets traced r?evilpie

Approved to land and uplift

Attachment #9272864 - Flags: sec-approval? → sec-approval+

[Tracking Requested - why for this release]: sec-high regression

Group: dom-core-security → core-security-release
Status: ASSIGNED → RESOLVED
Closed: 3 years ago
Resolution: --- → FIXED
Target Milestone: --- → 101 Branch

Comment on attachment 9272864 [details]
Bug 1765343 - Ensure WritableStreamDefaultController gets traced r?evilpie

Beta/Release Uplift Approval Request

  • User impact if declined: Potential Use-after free, crashes.
  • Is this code covered by automated tests?: No
  • Has the fix been verified in Nightly?: Yes
  • Needs manual test from QE?: No
  • If yes, steps to reproduce:
  • List of other uplifts needed: None
  • Risk to taking this patch: Low
  • Why is the change risky/not risky? (and alternatives if risky): Very clear idiom failure
  • String changes made/needed:
Attachment #9272864 - Flags: approval-mozilla-beta?

Comment on attachment 9272864 [details]
Bug 1765343 - Ensure WritableStreamDefaultController gets traced r?evilpie

Approved for 100.0b9

Attachment #9272864 - Flags: approval-mozilla-beta? → approval-mozilla-beta+
QA Whiteboard: [post-critsmash-triage]
Flags: qe-verify-
Group: core-security-release
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: