tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

commit d8e3b23cd602a8fcd13221a42f31608b98e1256f
parent f3e968c5ec1d577d46b206b6e43a050e9ae6067a
Author: Matthew Gaudet <mgaudet@mozilla.com>
Date:   Wed,  1 Oct 2025 21:38:50 +0000

Bug 1983154 - Create MaybeGetPromiseAllocationSite r=arai

This is a more flexibile version

Differential Revision: https://phabricator.services.mozilla.com/D261177

Diffstat:
Mjs/public/Promise.h | 16++++++++++++++++
Mjs/src/vm/Runtime.cpp | 35+++++++++++++++++++++++------------
2 files changed, 39 insertions(+), 12 deletions(-)

diff --git a/js/public/Promise.h b/js/public/Promise.h @@ -398,10 +398,26 @@ extern JS_PUBLIC_API bool SetSettledPromiseIsHandled(JSContext* cx, /** * Returns a js::SavedFrame linked list of the stack that lead to the given * Promise's allocation. + * + * The promise parameter here should be an unwrapped promise. */ extern JS_PUBLIC_API JSObject* GetPromiseAllocationSite( JS::HandleObject promise); +/** + * A more flexible version of the above: Handles the cases where + * 1. maybePromise is wrapped + * 2. maybePromise is null + * 3. maybePromise isn't actually a promise. + * + * Returns js::SavedFrame if the passed argument is a + * wrapped promise (that's not a dead object wrapper) and it + * has an allocation site. + */ +extern JS_PUBLIC_API JSObject* +MaybeGetPromiseAllocationSiteFromPossiblyWrappedPromise( + JS::HandleObject maybePromise); + extern JS_PUBLIC_API JSObject* GetPromiseResolutionSite( JS::HandleObject promise); diff --git a/js/src/vm/Runtime.cpp b/js/src/vm/Runtime.cpp @@ -576,6 +576,26 @@ bool JSRuntime::getHostDefinedData(JSContext* cx, return cx->jobQueue->getHostDefinedData(cx, data); } +JS_PUBLIC_API JSObject* +JS::MaybeGetPromiseAllocationSiteFromPossiblyWrappedPromise( + HandleObject promise) { + if (!promise) { + return nullptr; + } + + JSObject* unwrappedPromise = promise; + // While the job object is guaranteed to be unwrapped, the promise + // might be wrapped. See the comments in EnqueuePromiseReactionJob in + // builtin/Promise.cpp for details. + if (IsWrapper(promise)) { + unwrappedPromise = UncheckedUnwrap(promise); + } + if (unwrappedPromise->is<PromiseObject>()) { + return unwrappedPromise->as<PromiseObject>().allocationSite(); + } + return nullptr; +} + bool JSRuntime::enqueuePromiseJob(JSContext* cx, HandleFunction job, HandleObject promise, HandleObject hostDefinedData) { @@ -583,23 +603,14 @@ bool JSRuntime::enqueuePromiseJob(JSContext* cx, HandleFunction job, "Must select a JobQueue implementation using JS::JobQueue " "or js::UseInternalJobQueues before using Promises"); - RootedObject allocationSite(cx); if (promise) { #ifdef DEBUG AssertSameCompartment(job, promise); #endif - - RootedObject unwrappedPromise(cx, promise); - // While the job object is guaranteed to be unwrapped, the promise - // might be wrapped. See the comments in EnqueuePromiseReactionJob in - // builtin/Promise.cpp for details. - if (IsWrapper(promise)) { - unwrappedPromise = UncheckedUnwrap(promise); - } - if (unwrappedPromise->is<PromiseObject>()) { - allocationSite = JS::GetPromiseAllocationSite(unwrappedPromise); - } } + + RootedObject allocationSite( + cx, JS::MaybeGetPromiseAllocationSiteFromPossiblyWrappedPromise(promise)); return cx->jobQueue->enqueuePromiseJob(cx, promise, job, allocationSite, hostDefinedData); }