summaryrefslogtreecommitdiffstats
path: root/js/src/builtin
diff options
context:
space:
mode:
Diffstat (limited to 'js/src/builtin')
-rw-r--r--js/src/builtin/AtomicsObject.cpp25
-rw-r--r--js/src/builtin/AtomicsObject.h26
-rw-r--r--js/src/builtin/Intl.cpp31
-rw-r--r--js/src/builtin/IntlTimeZoneData.h2
-rw-r--r--js/src/builtin/MapObject.cpp4
-rw-r--r--js/src/builtin/ModuleObject.cpp10
-rw-r--r--js/src/builtin/ModuleObject.h2
-rw-r--r--js/src/builtin/Object.cpp18
-rw-r--r--js/src/builtin/Object.h3
-rw-r--r--js/src/builtin/Object.js6
-rw-r--r--js/src/builtin/Promise.cpp129
-rw-r--r--js/src/builtin/Promise.h8
-rw-r--r--js/src/builtin/Reflect.cpp3
-rw-r--r--js/src/builtin/ReflectParse.cpp31
-rw-r--r--js/src/builtin/RegExp.cpp18
-rw-r--r--js/src/builtin/RegExp.h2
-rw-r--r--js/src/builtin/SIMD.cpp22
-rw-r--r--js/src/builtin/SymbolObject.cpp8
-rw-r--r--js/src/builtin/TestingFunctions.cpp39
-rw-r--r--js/src/builtin/TypedObject.cpp19
-rw-r--r--js/src/builtin/Utilities.js63
-rw-r--r--js/src/builtin/WeakMapObject.cpp6
-rw-r--r--js/src/builtin/WeakSetObject.cpp7
-rw-r--r--js/src/builtin/WeakSetObject.h2
24 files changed, 287 insertions, 197 deletions
diff --git a/js/src/builtin/AtomicsObject.cpp b/js/src/builtin/AtomicsObject.cpp
index 2551f3b7d..ceee83349 100644
--- a/js/src/builtin/AtomicsObject.cpp
+++ b/js/src/builtin/AtomicsObject.cpp
@@ -834,7 +834,7 @@ js::atomics_wait(JSContext* cx, unsigned argc, Value* vp)
}
bool
-js::atomics_wake(JSContext* cx, unsigned argc, Value* vp)
+js::atomics_notify(JSContext* cx, unsigned argc, Value* vp)
{
CallArgs args = CallArgsFromVp(argc, vp);
HandleValue objv = args.get(0);
@@ -874,7 +874,7 @@ js::atomics_wake(JSContext* cx, unsigned argc, Value* vp)
iter = iter->lower_pri;
if (c->offset != offset || !c->rt->fx.isWaiting())
continue;
- c->rt->fx.wake(FutexRuntime::WakeExplicit);
+ c->rt->fx.notify(FutexRuntime::NotifyExplicit);
++woken;
--count;
} while (count > 0 && iter != waiters);
@@ -950,7 +950,7 @@ js::FutexRuntime::isWaiting()
// When a worker is awoken for an interrupt it goes into state
// WaitingNotifiedForInterrupt for a short time before it actually
// wakes up and goes into WaitingInterrupted. In those states the
- // worker is still waiting, and if an explicit wake arrives the
+ // worker is still waiting, and if an explicit notify arrives the
// worker transitions to Woken. See further comments in
// FutexRuntime::wait().
return state_ == Waiting || state_ == WaitingInterrupted || state_ == WaitingNotifiedForInterrupt;
@@ -1029,14 +1029,14 @@ js::FutexRuntime::wait(JSContext* cx, js::UniqueLock<js::Mutex>& locked,
// should be woken when the interrupt handler returns.
// To that end, we flag the thread as interrupted around
// the interrupt and check state_ when the interrupt
- // handler returns. A wake() call that reaches the
+ // handler returns. A notify() call that reaches the
// runtime during the interrupt sets state_ to Woken.
//
// - It is in principle possible for wait() to be
// reentered on the same thread/runtime and waiting on the
// same location and to yet again be interrupted and enter
// the interrupt handler. In this case, it is important
- // that when another agent wakes waiters, all waiters using
+ // that when another agent notifies waiters, all waiters using
// the same runtime on the same location are woken in LIFO
// order; FIFO may be the required order, but FIFO would
// fail to wake up the innermost call. Interrupts are
@@ -1073,25 +1073,25 @@ finished:
}
void
-js::FutexRuntime::wake(WakeReason reason)
+js::FutexRuntime::notify(NotifyReason reason)
{
MOZ_ASSERT(isWaiting());
- if ((state_ == WaitingInterrupted || state_ == WaitingNotifiedForInterrupt) && reason == WakeExplicit) {
+ if ((state_ == WaitingInterrupted || state_ == WaitingNotifiedForInterrupt) && reason == NotifyExplicit) {
state_ = Woken;
return;
}
switch (reason) {
- case WakeExplicit:
+ case NotifyExplicit:
state_ = Woken;
break;
- case WakeForJSInterrupt:
+ case NotifyForJSInterrupt:
if (state_ == WaitingNotifiedForInterrupt)
return;
state_ = WaitingNotifiedForInterrupt;
break;
default:
- MOZ_CRASH("bad WakeReason in FutexRuntime::wake()");
+ MOZ_CRASH("bad NotifyReason in FutexRuntime::notify()");
}
cond_->notify_all();
}
@@ -1108,7 +1108,8 @@ const JSFunctionSpec AtomicsMethods[] = {
JS_INLINABLE_FN("xor", atomics_xor, 3,0, AtomicsXor),
JS_INLINABLE_FN("isLockFree", atomics_isLockFree, 1,0, AtomicsIsLockFree),
JS_FN("wait", atomics_wait, 4,0),
- JS_FN("wake", atomics_wake, 3,0),
+ JS_FN("notify", atomics_notify, 3,0),
+ JS_FN("wake", atomics_notify, 3,0), //Legacy name
JS_FS_END
};
@@ -1116,7 +1117,7 @@ JSObject*
AtomicsObject::initClass(JSContext* cx, Handle<GlobalObject*> global)
{
// Create Atomics Object.
- RootedObject objProto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject objProto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!objProto)
return nullptr;
RootedObject Atomics(cx, NewObjectWithGivenProto(cx, &AtomicsObject::class_, objProto,
diff --git a/js/src/builtin/AtomicsObject.h b/js/src/builtin/AtomicsObject.h
index adb6fb986..6511dc8bf 100644
--- a/js/src/builtin/AtomicsObject.h
+++ b/js/src/builtin/AtomicsObject.h
@@ -36,7 +36,7 @@ MOZ_MUST_USE bool atomics_or(JSContext* cx, unsigned argc, Value* vp);
MOZ_MUST_USE bool atomics_xor(JSContext* cx, unsigned argc, Value* vp);
MOZ_MUST_USE bool atomics_isLockFree(JSContext* cx, unsigned argc, Value* vp);
MOZ_MUST_USE bool atomics_wait(JSContext* cx, unsigned argc, Value* vp);
-MOZ_MUST_USE bool atomics_wake(JSContext* cx, unsigned argc, Value* vp);
+MOZ_MUST_USE bool atomics_notify(JSContext* cx, unsigned argc, Value* vp);
/* asm.js callouts */
namespace wasm { class Instance; }
@@ -63,10 +63,10 @@ public:
MOZ_MUST_USE bool initInstance();
void destroyInstance();
- // Parameters to wake().
- enum WakeReason {
- WakeExplicit, // Being asked to wake up by another thread
- WakeForJSInterrupt // Interrupt requested
+ // Parameters to notify().
+ enum NotifyReason {
+ NotifyExplicit, // Being asked to wake up by another thread
+ NotifyForJSInterrupt // Interrupt requested
};
// Result code from wait().
@@ -83,29 +83,27 @@ public:
// times allowed; specify mozilla::Nothing() for an indefinite
// wait.
//
- // wait() will not wake up spuriously. It will return true and
- // set *result to a return code appropriate for
- // Atomics.wait() on success, and return false on error.
+ // wait() will not wake up spuriously.
MOZ_MUST_USE bool wait(JSContext* cx, js::UniqueLock<js::Mutex>& locked,
mozilla::Maybe<mozilla::TimeDuration>& timeout, WaitResult* result);
- // Wake the thread represented by this Runtime.
+ // Notify the thread represented by this Runtime.
//
// The futex lock must be held around this call. (The sleeping
- // thread will not wake up until the caller of Atomics.wake()
+ // thread will not wake up until the caller of Atomics.notify()
// releases the lock.)
//
// If the thread is not waiting then this method does nothing.
//
// If the thread is waiting in a call to wait() and the
- // reason is WakeExplicit then the wait() call will return
+ // reason is NotifyExplicit then the wait() call will return
// with Woken.
//
// If the thread is waiting in a call to wait() and the
- // reason is WakeForJSInterrupt then the wait() will return
+ // reason is NotifyForJSInterrupt then the wait() will return
// with WaitingNotifiedForInterrupt; in the latter case the caller
// of wait() must handle the interrupt.
- void wake(WakeReason reason);
+ void notify(NotifyReason reason);
bool isWaiting();
@@ -128,7 +126,7 @@ public:
// interrupt handler
WaitingInterrupted, // We are waiting, but have been interrupted
// and are running the interrupt handler
- Woken // Woken by a script call to Atomics.wake
+ Woken // Woken by a script call to Atomics.notify
};
// Condition variable that this runtime will wait on.
diff --git a/js/src/builtin/Intl.cpp b/js/src/builtin/Intl.cpp
index 71f7b58d4..0cd0c62dd 100644
--- a/js/src/builtin/Intl.cpp
+++ b/js/src/builtin/Intl.cpp
@@ -270,7 +270,7 @@ Collator(JSContext* cx, const CallArgs& args, bool construct)
// See https://github.com/tc39/ecma402/issues/57
if (!construct) {
// ES Intl 1st ed., 10.1.2.1 step 3
- JSObject* intl = cx->global()->getOrCreateIntlObject(cx);
+ JSObject* intl = GlobalObject::getOrCreateIntlObject(cx, cx->global());
if (!intl)
return false;
RootedValue self(cx, args.thisv());
@@ -298,7 +298,7 @@ Collator(JSContext* cx, const CallArgs& args, bool construct)
return false;
if (!proto) {
- proto = cx->global()->getOrCreateCollatorPrototype(cx);
+ proto = GlobalObject::getOrCreateCollatorPrototype(cx, cx->global());
if (!proto)
return false;
}
@@ -358,11 +358,12 @@ collator_finalize(FreeOp* fop, JSObject* obj)
static JSObject*
CreateCollatorPrototype(JSContext* cx, HandleObject Intl, Handle<GlobalObject*> global)
{
- RootedFunction ctor(cx, global->createConstructor(cx, &Collator, cx->names().Collator, 0));
+ RootedFunction ctor(cx, GlobalObject::createConstructor(cx, &Collator, cx->names().Collator,
+ 0));
if (!ctor)
return nullptr;
- RootedNativeObject proto(cx, global->createBlankPrototype(cx, &CollatorClass));
+ RootedNativeObject proto(cx, GlobalObject::createBlankPrototype(cx, global, &CollatorClass));
if (!proto)
return nullptr;
proto->setReservedSlot(UCOLLATOR_SLOT, PrivateValue(nullptr));
@@ -772,7 +773,7 @@ NumberFormat(JSContext* cx, const CallArgs& args, bool construct)
// See https://github.com/tc39/ecma402/issues/57
if (!construct) {
// ES Intl 1st ed., 11.1.2.1 step 3
- JSObject* intl = cx->global()->getOrCreateIntlObject(cx);
+ JSObject* intl = GlobalObject::getOrCreateIntlObject(cx, cx->global());
if (!intl)
return false;
RootedValue self(cx, args.thisv());
@@ -800,7 +801,7 @@ NumberFormat(JSContext* cx, const CallArgs& args, bool construct)
return false;
if (!proto) {
- proto = cx->global()->getOrCreateNumberFormatPrototype(cx);
+ proto = GlobalObject::getOrCreateNumberFormatPrototype(cx, cx->global());
if (!proto)
return false;
}
@@ -862,11 +863,12 @@ static JSObject*
CreateNumberFormatPrototype(JSContext* cx, HandleObject Intl, Handle<GlobalObject*> global)
{
RootedFunction ctor(cx);
- ctor = global->createConstructor(cx, &NumberFormat, cx->names().NumberFormat, 0);
+ ctor = GlobalObject::createConstructor(cx, &NumberFormat, cx->names().NumberFormat, 0);
if (!ctor)
return nullptr;
- RootedNativeObject proto(cx, global->createBlankPrototype(cx, &NumberFormatClass));
+ RootedNativeObject proto(cx, GlobalObject::createBlankPrototype(cx, global,
+ &NumberFormatClass));
if (!proto)
return nullptr;
proto->setReservedSlot(UNUMBER_FORMAT_SLOT, PrivateValue(nullptr));
@@ -1250,7 +1252,7 @@ DateTimeFormat(JSContext* cx, const CallArgs& args, bool construct)
// See https://github.com/tc39/ecma402/issues/57
if (!construct) {
// ES Intl 1st ed., 12.1.2.1 step 3
- JSObject* intl = cx->global()->getOrCreateIntlObject(cx);
+ JSObject* intl = GlobalObject::getOrCreateIntlObject(cx, cx->global());
if (!intl)
return false;
RootedValue self(cx, args.thisv());
@@ -1278,7 +1280,7 @@ DateTimeFormat(JSContext* cx, const CallArgs& args, bool construct)
return false;
if (!proto) {
- proto = cx->global()->getOrCreateDateTimeFormatPrototype(cx);
+ proto = GlobalObject::getOrCreateDateTimeFormatPrototype(cx, cx->global());
if (!proto)
return false;
}
@@ -1340,11 +1342,12 @@ static JSObject*
CreateDateTimeFormatPrototype(JSContext* cx, HandleObject Intl, Handle<GlobalObject*> global)
{
RootedFunction ctor(cx);
- ctor = global->createConstructor(cx, &DateTimeFormat, cx->names().DateTimeFormat, 0);
+ ctor = GlobalObject::createConstructor(cx, &DateTimeFormat, cx->names().DateTimeFormat, 0);
if (!ctor)
return nullptr;
- RootedNativeObject proto(cx, global->createBlankPrototype(cx, &DateTimeFormatClass));
+ RootedNativeObject proto(cx, GlobalObject::createBlankPrototype(cx, global,
+ &DateTimeFormatClass));
if (!proto)
return nullptr;
proto->setReservedSlot(UDATE_FORMAT_SLOT, PrivateValue(nullptr));
@@ -2731,10 +2734,10 @@ static const JSFunctionSpec intl_static_methods[] = {
* Initializes the Intl Object and its standard built-in properties.
* Spec: ECMAScript Internationalization API Specification, 8.0, 8.1
*/
-bool
+/* static */ bool
GlobalObject::initIntlObject(JSContext* cx, Handle<GlobalObject*> global)
{
- RootedObject proto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject proto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!proto)
return false;
diff --git a/js/src/builtin/IntlTimeZoneData.h b/js/src/builtin/IntlTimeZoneData.h
index fa808c0b9..8f963ffbc 100644
--- a/js/src/builtin/IntlTimeZoneData.h
+++ b/js/src/builtin/IntlTimeZoneData.h
@@ -1,5 +1,5 @@
// Generated by make_intl_data.py. DO NOT EDIT.
-// tzdata version = 2018e
+// tzdata version = 2019a
#ifndef builtin_IntlTimeZoneData_h
#define builtin_IntlTimeZoneData_h
diff --git a/js/src/builtin/MapObject.cpp b/js/src/builtin/MapObject.cpp
index c496cfb77..34e2e566d 100644
--- a/js/src/builtin/MapObject.cpp
+++ b/js/src/builtin/MapObject.cpp
@@ -164,7 +164,7 @@ MapIteratorObject::kind() const
return MapObject::IteratorKind(i);
}
-bool
+/* static */ bool
GlobalObject::initMapIteratorProto(JSContext* cx, Handle<GlobalObject*> global)
{
Rooted<JSObject*> base(cx, GlobalObject::getOrCreateIteratorPrototype(cx, global));
@@ -924,7 +924,7 @@ SetIteratorObject::kind() const
return SetObject::IteratorKind(i);
}
-bool
+/* static */ bool
GlobalObject::initSetIteratorProto(JSContext* cx, Handle<GlobalObject*> global)
{
Rooted<JSObject*> base(cx, GlobalObject::getOrCreateIteratorPrototype(cx, global));
diff --git a/js/src/builtin/ModuleObject.cpp b/js/src/builtin/ModuleObject.cpp
index 710c7a76c..798ef46e1 100644
--- a/js/src/builtin/ModuleObject.cpp
+++ b/js/src/builtin/ModuleObject.cpp
@@ -103,7 +103,7 @@ GlobalObject::initImportEntryProto(JSContext* cx, Handle<GlobalObject*> global)
JS_PS_END
};
- RootedObject proto(cx, global->createBlankPrototype<PlainObject>(cx));
+ RootedObject proto(cx, GlobalObject::createBlankPrototype<PlainObject>(cx, global));
if (!proto)
return false;
@@ -169,7 +169,7 @@ GlobalObject::initExportEntryProto(JSContext* cx, Handle<GlobalObject*> global)
JS_PS_END
};
- RootedObject proto(cx, global->createBlankPrototype<PlainObject>(cx));
+ RootedObject proto(cx, GlobalObject::createBlankPrototype<PlainObject>(cx, global));
if (!proto)
return false;
@@ -788,7 +788,7 @@ AssertModuleScopesMatch(ModuleObject* module)
}
void
-ModuleObject::fixEnvironmentsAfterCompartmentMerge(JSContext* cx)
+ModuleObject::fixEnvironmentsAfterCompartmentMerge()
{
AssertModuleScopesMatch(this);
initialEnvironment().fixEnclosingEnvironmentAfterCompartmentMerge(script()->global());
@@ -947,7 +947,7 @@ ModuleObject::evaluate(JSContext* cx, HandleModuleObject self, MutableHandleValu
ModuleObject::createNamespace(JSContext* cx, HandleModuleObject self, HandleObject exports)
{
MOZ_ASSERT(!self->namespace_());
- MOZ_ASSERT(exports->is<ArrayObject>() || exports->is<UnboxedArrayObject>());
+ MOZ_ASSERT(exports->is<ArrayObject>());
RootedModuleNamespaceObject ns(cx, ModuleNamespaceObject::create(cx, self));
if (!ns)
@@ -1020,7 +1020,7 @@ GlobalObject::initModuleProto(JSContext* cx, Handle<GlobalObject*> global)
JS_FS_END
};
- RootedObject proto(cx, global->createBlankPrototype<PlainObject>(cx));
+ RootedObject proto(cx, GlobalObject::createBlankPrototype<PlainObject>(cx, global));
if (!proto)
return false;
diff --git a/js/src/builtin/ModuleObject.h b/js/src/builtin/ModuleObject.h
index d0ed8ed08..e83520ebe 100644
--- a/js/src/builtin/ModuleObject.h
+++ b/js/src/builtin/ModuleObject.h
@@ -244,7 +244,7 @@ class ModuleObject : public NativeObject
#ifdef DEBUG
static bool IsFrozen(JSContext* cx, HandleModuleObject self);
#endif
- void fixEnvironmentsAfterCompartmentMerge(JSContext* cx);
+ void fixEnvironmentsAfterCompartmentMerge();
JSScript* script() const;
Scope* enclosingScope() const;
diff --git a/js/src/builtin/Object.cpp b/js/src/builtin/Object.cpp
index 389bb57db..56c77f304 100644
--- a/js/src/builtin/Object.cpp
+++ b/js/src/builtin/Object.cpp
@@ -525,18 +525,6 @@ js::obj_toString(JSContext* cx, unsigned argc, Value* vp)
return true;
}
-
-bool
-js::obj_valueOf(JSContext* cx, unsigned argc, Value* vp)
-{
- CallArgs args = CallArgsFromVp(argc, vp);
- RootedObject obj(cx, ToObject(cx, args.thisv()));
- if (!obj)
- return false;
- args.rval().setObject(*obj);
- return true;
-}
-
static bool
obj_setPrototypeOf(JSContext* cx, unsigned argc, Value* vp)
{
@@ -1301,7 +1289,7 @@ static const JSFunctionSpec object_methods[] = {
#endif
JS_FN(js_toString_str, obj_toString, 0,0),
JS_SELF_HOSTED_FN(js_toLocaleString_str, "Object_toLocaleString", 0, 0),
- JS_FN(js_valueOf_str, obj_valueOf, 0,0),
+ JS_SELF_HOSTED_FN(js_valueOf_str, "Object_valueOf", 0,0),
#if JS_HAS_OBJ_WATCHPOINT
JS_FN(js_watch_str, obj_watch, 2,0),
JS_FN(js_unwatch_str, obj_unwatch, 1,0),
@@ -1420,8 +1408,8 @@ FinishObjectClassInit(JSContext* cx, JS::HandleObject ctor, JS::HandleObject pro
* only set the [[Prototype]] if it hasn't already been set.
*/
Rooted<TaggedProto> tagged(cx, TaggedProto(proto));
- if (global->shouldSplicePrototype(cx)) {
- if (!global->splicePrototype(cx, global->getClass(), tagged))
+ if (global->shouldSplicePrototype()) {
+ if (!JSObject::splicePrototype(cx, global, global->getClass(), tagged))
return false;
}
return true;
diff --git a/js/src/builtin/Object.h b/js/src/builtin/Object.h
index 09512be36..8231888b1 100644
--- a/js/src/builtin/Object.h
+++ b/js/src/builtin/Object.h
@@ -25,9 +25,6 @@ obj_construct(JSContext* cx, unsigned argc, JS::Value* vp);
MOZ_MUST_USE bool
obj_propertyIsEnumerable(JSContext* cx, unsigned argc, Value* vp);
-MOZ_MUST_USE bool
-obj_valueOf(JSContext* cx, unsigned argc, JS::Value* vp);
-
PlainObject*
ObjectCreateImpl(JSContext* cx, HandleObject proto, NewObjectKind newKind = GenericObject,
HandleObjectGroup group = nullptr);
diff --git a/js/src/builtin/Object.js b/js/src/builtin/Object.js
index a7440aec7..9ed1be0e1 100644
--- a/js/src/builtin/Object.js
+++ b/js/src/builtin/Object.js
@@ -87,6 +87,12 @@ function Object_toLocaleString() {
return callContentFunction(O.toString, O);
}
+// ES 2017 draft bb96899bb0d9ef9be08164a26efae2ee5f25e875 19.1.3.7
+function Object_valueOf() {
+ // Step 1.
+ return ToObject(this);
+}
+
// ES7 draft (2016 March 8) B.2.2.3
function ObjectDefineSetter(name, setter) {
// Step 1.
diff --git a/js/src/builtin/Promise.cpp b/js/src/builtin/Promise.cpp
index c781a336d..ec7845e89 100644
--- a/js/src/builtin/Promise.cpp
+++ b/js/src/builtin/Promise.cpp
@@ -603,7 +603,7 @@ ResolvePromise(JSContext* cx, Handle<PromiseObject*> promise, HandleValue valueO
// Now that everything else is done, do the things the debugger needs.
// Step 7 of RejectPromise implemented in onSettled.
- promise->onSettled(cx);
+ PromiseObject::onSettled(cx, promise);
// Step 7 of FulfillPromise.
// Step 8 of RejectPromise.
@@ -1947,26 +1947,23 @@ PerformPromiseRace(JSContext *cx, JS::ForOfIterator& iterator, HandleObject C,
}
// ES2016, Sub-steps of 25.4.4.4 and 25.4.4.5.
-static MOZ_MUST_USE bool
-CommonStaticResolveRejectImpl(JSContext* cx, unsigned argc, Value* vp, ResolutionMode mode)
+static MOZ_MUST_USE JSObject*
+CommonStaticResolveRejectImpl(JSContext* cx, HandleValue thisVal, HandleValue argVal,
+ ResolutionMode mode)
{
- CallArgs args = CallArgsFromVp(argc, vp);
- RootedValue x(cx, args.get(0));
-
// Steps 1-2.
- if (!args.thisv().isObject()) {
+ if (!thisVal.isObject()) {
const char* msg = mode == ResolveMode
? "Receiver of Promise.resolve call"
: "Receiver of Promise.reject call";
JS_ReportErrorNumberASCII(cx, GetErrorMessage, nullptr, JSMSG_NOT_NONNULL_OBJECT, msg);
- return false;
+ return nullptr;
}
- RootedValue cVal(cx, args.thisv());
- RootedObject C(cx, &cVal.toObject());
+ RootedObject C(cx, &thisVal.toObject());
// Step 3 of Resolve.
- if (mode == ResolveMode && x.isObject()) {
- RootedObject xObj(cx, &x.toObject());
+ if (mode == ResolveMode && argVal.isObject()) {
+ RootedObject xObj(cx, &argVal.toObject());
bool isPromise = false;
if (xObj->is<PromiseObject>()) {
isPromise = true;
@@ -1985,11 +1982,9 @@ CommonStaticResolveRejectImpl(JSContext* cx, unsigned argc, Value* vp, Resolutio
if (isPromise) {
RootedValue ctorVal(cx);
if (!GetProperty(cx, xObj, xObj, cx->names().constructor, &ctorVal))
- return false;
- if (ctorVal == cVal) {
- args.rval().set(x);
- return true;
- }
+ return nullptr;
+ if (ctorVal == thisVal)
+ return xObj;
}
}
@@ -1998,15 +1993,17 @@ CommonStaticResolveRejectImpl(JSContext* cx, unsigned argc, Value* vp, Resolutio
RootedObject resolveFun(cx);
RootedObject rejectFun(cx);
if (!NewPromiseCapability(cx, C, &promise, &resolveFun, &rejectFun, true))
- return false;
+ return nullptr;
// Step 5 of Resolve, 4 of Reject.
- if (!RunResolutionFunction(cx, mode == ResolveMode ? resolveFun : rejectFun, x, mode, promise))
- return false;
+ if (!RunResolutionFunction(cx, mode == ResolveMode ? resolveFun : rejectFun, argVal, mode,
+ promise))
+ {
+ return nullptr;
+ }
// Step 6 of Resolve, 4 of Reject.
- args.rval().setObject(*promise);
- return true;
+ return promise;
}
/**
@@ -2015,7 +2012,14 @@ CommonStaticResolveRejectImpl(JSContext* cx, unsigned argc, Value* vp, Resolutio
bool
js::Promise_reject(JSContext* cx, unsigned argc, Value* vp)
{
- return CommonStaticResolveRejectImpl(cx, argc, vp, RejectMode);
+ CallArgs args = CallArgsFromVp(argc, vp);
+ RootedValue thisVal(cx, args.thisv());
+ RootedValue argVal(cx, args.get(0));
+ JSObject* result = CommonStaticResolveRejectImpl(cx, thisVal, argVal, RejectMode);
+ if (!result)
+ return false;
+ args.rval().setObject(*result);
+ return true;
}
/**
@@ -2024,19 +2028,11 @@ js::Promise_reject(JSContext* cx, unsigned argc, Value* vp)
/* static */ JSObject*
PromiseObject::unforgeableReject(JSContext* cx, HandleValue value)
{
- // Steps 1-2 (omitted).
-
- // Roughly step 3.
- Rooted<PromiseObject*> promise(cx, CreatePromiseObjectInternal(cx));
- if (!promise)
+ RootedObject promiseCtor(cx, JS::GetPromiseConstructor(cx));
+ if (!promiseCtor)
return nullptr;
-
- // Roughly step 4.
- if (!ResolvePromise(cx, promise, value, JS::PromiseState::Rejected))
- return nullptr;
-
- // Step 5.
- return promise;
+ RootedValue cVal(cx, ObjectValue(*promiseCtor));
+ return CommonStaticResolveRejectImpl(cx, cVal, value, RejectMode);
}
/**
@@ -2045,7 +2041,14 @@ PromiseObject::unforgeableReject(JSContext* cx, HandleValue value)
bool
js::Promise_static_resolve(JSContext* cx, unsigned argc, Value* vp)
{
- return CommonStaticResolveRejectImpl(cx, argc, vp, ResolveMode);
+ CallArgs args = CallArgsFromVp(argc, vp);
+ RootedValue thisVal(cx, args.thisv());
+ RootedValue argVal(cx, args.get(0));
+ JSObject* result = CommonStaticResolveRejectImpl(cx, thisVal, argVal, ResolveMode);
+ if (!result)
+ return false;
+ args.rval().setObject(*result);
+ return true;
}
/**
@@ -2054,30 +2057,11 @@ js::Promise_static_resolve(JSContext* cx, unsigned argc, Value* vp)
/* static */ JSObject*
PromiseObject::unforgeableResolve(JSContext* cx, HandleValue value)
{
- // Steps 1-2 (omitted).
-
- // Step 3.
- if (value.isObject()) {
- JSObject* obj = &value.toObject();
- if (IsWrapper(obj))
- obj = CheckedUnwrap(obj);
- // Instead of getting the `constructor` property, do an unforgeable
- // check.
- if (obj && obj->is<PromiseObject>())
- return obj;
- }
-
- // Step 4.
- Rooted<PromiseObject*> promise(cx, CreatePromiseObjectInternal(cx));
- if (!promise)
+ RootedObject promiseCtor(cx, JS::GetPromiseConstructor(cx));
+ if (!promiseCtor)
return nullptr;
-
- // Steps 5.
- if (!ResolvePromiseInternal(cx, promise, value))
- return nullptr;
-
- // Step 6.
- return promise;
+ RootedValue cVal(cx, ObjectValue(*promiseCtor));
+ return CommonStaticResolveRejectImpl(cx, cVal, value, ResolveMode);
}
// ES2016, 25.4.4.6, implemented in Promise.js.
@@ -2647,14 +2631,14 @@ PromiseObject::dependentPromises(JSContext* cx, MutableHandle<GCVector<Value>> v
return true;
}
-bool
-PromiseObject::resolve(JSContext* cx, HandleValue resolutionValue)
+/* static */ bool
+PromiseObject::resolve(JSContext* cx, Handle<PromiseObject*> promise, HandleValue resolutionValue)
{
- MOZ_ASSERT(!PromiseHasAnyFlag(*this, PROMISE_FLAG_ASYNC));
- if (state() != JS::PromiseState::Pending)
+ MOZ_ASSERT(!PromiseHasAnyFlag(*promise, PROMISE_FLAG_ASYNC));
+ if (promise->state() != JS::PromiseState::Pending)
return true;
- RootedObject resolveFun(cx, GetResolveFunctionFromPromise(this));
+ RootedObject resolveFun(cx, GetResolveFunctionFromPromise(promise));
RootedValue funVal(cx, ObjectValue(*resolveFun));
// For xray'd Promises, the resolve fun may have been created in another
@@ -2670,14 +2654,14 @@ PromiseObject::resolve(JSContext* cx, HandleValue resolutionValue)
return Call(cx, funVal, UndefinedHandleValue, args, &dummy);
}
-bool
-PromiseObject::reject(JSContext* cx, HandleValue rejectionValue)
+/* static */ bool
+PromiseObject::reject(JSContext* cx, Handle<PromiseObject*> promise, HandleValue rejectionValue)
{
- MOZ_ASSERT(!PromiseHasAnyFlag(*this, PROMISE_FLAG_ASYNC));
- if (state() != JS::PromiseState::Pending)
+ MOZ_ASSERT(!PromiseHasAnyFlag(*promise, PROMISE_FLAG_ASYNC));
+ if (promise->state() != JS::PromiseState::Pending)
return true;
- RootedValue funVal(cx, this->getFixedSlot(PromiseSlot_RejectFunction));
+ RootedValue funVal(cx, promise->getFixedSlot(PromiseSlot_RejectFunction));
MOZ_ASSERT(IsCallable(funVal));
FixedInvokeArgs<1> args(cx);
@@ -2687,10 +2671,9 @@ PromiseObject::reject(JSContext* cx, HandleValue rejectionValue)
return Call(cx, funVal, UndefinedHandleValue, args, &dummy);
}
-void
-PromiseObject::onSettled(JSContext* cx)
+/* static */ void
+PromiseObject::onSettled(JSContext* cx, Handle<PromiseObject*> promise)
{
- Rooted<PromiseObject*> promise(cx, this);
RootedObject stack(cx);
if (cx->options().asyncStack() || cx->compartment()->isDebuggee()) {
if (!JS::CaptureCurrentStack(cx, &stack, JS::StackCapture(JS::AllFrames()))) {
@@ -2750,7 +2733,7 @@ PromiseTask::executeAndFinish(JSContext* cx)
static JSObject*
CreatePromisePrototype(JSContext* cx, JSProtoKey key)
{
- return cx->global()->createBlankPrototype(cx, &PromiseObject::protoClass_);
+ return GlobalObject::createBlankPrototype(cx, cx->global(), &PromiseObject::protoClass_);
}
static const JSFunctionSpec promise_methods[] = {
diff --git a/js/src/builtin/Promise.h b/js/src/builtin/Promise.h
index bb4778631..c76dc358c 100644
--- a/js/src/builtin/Promise.h
+++ b/js/src/builtin/Promise.h
@@ -66,10 +66,12 @@ class PromiseObject : public NativeObject
return getFixedSlot(PromiseSlot_ReactionsOrResult);
}
- MOZ_MUST_USE bool resolve(JSContext* cx, HandleValue resolutionValue);
- MOZ_MUST_USE bool reject(JSContext* cx, HandleValue rejectionValue);
+ static MOZ_MUST_USE bool resolve(JSContext* cx, Handle<PromiseObject*> promise,
+ HandleValue resolutionValue);
+ static MOZ_MUST_USE bool reject(JSContext* cx, Handle<PromiseObject*> promise,
+ HandleValue rejectionValue);
- void onSettled(JSContext* cx);
+ static void onSettled(JSContext* cx, Handle<PromiseObject*> promise);
double allocationTime() { return getFixedSlot(PromiseSlot_AllocationTime).toNumber(); }
double resolutionTime() { return getFixedSlot(PromiseSlot_ResolutionTime).toNumber(); }
diff --git a/js/src/builtin/Reflect.cpp b/js/src/builtin/Reflect.cpp
index 2f509a226..4e7fae78c 100644
--- a/js/src/builtin/Reflect.cpp
+++ b/js/src/builtin/Reflect.cpp
@@ -268,7 +268,8 @@ static const JSFunctionSpec methods[] = {
JSObject*
js::InitReflect(JSContext* cx, HandleObject obj)
{
- RootedObject proto(cx, obj->as<GlobalObject>().getOrCreateObjectPrototype(cx));
+ Handle<GlobalObject*> global = obj.as<GlobalObject>();
+ RootedObject proto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!proto)
return nullptr;
diff --git a/js/src/builtin/ReflectParse.cpp b/js/src/builtin/ReflectParse.cpp
index beff58e13..8e8bb2417 100644
--- a/js/src/builtin/ReflectParse.cpp
+++ b/js/src/builtin/ReflectParse.cpp
@@ -3044,7 +3044,12 @@ ASTSerializer::expression(ParseNode* pn, MutableHandleValue dst)
MOZ_ASSERT(pn->pn_pos.encloses(next->pn_pos));
RootedValue expr(cx);
- expr.setString(next->pn_atom);
+ if (next->isKind(PNK_RAW_UNDEFINED)) {
+ expr.setUndefined();
+ } else {
+ MOZ_ASSERT(next->isKind(PNK_TEMPLATE_STRING));
+ expr.setString(next->pn_atom);
+ }
cooked.infallibleAppend(expr);
}
@@ -3136,6 +3141,7 @@ ASTSerializer::expression(ParseNode* pn, MutableHandleValue dst)
case PNK_TRUE:
case PNK_FALSE:
case PNK_NULL:
+ case PNK_RAW_UNDEFINED:
return literal(pn, dst);
case PNK_YIELD_STAR:
@@ -3216,6 +3222,8 @@ ASTSerializer::property(ParseNode* pn, MutableHandleValue dst)
return expression(pn->pn_kid, &val) &&
builder.prototypeMutation(val, &pn->pn_pos, dst);
}
+ if (pn->isKind(PNK_SPREAD))
+ return expression(pn, dst);
PropKind kind;
switch (pn->getOp()) {
@@ -3276,6 +3284,10 @@ ASTSerializer::literal(ParseNode* pn, MutableHandleValue dst)
val.setNull();
break;
+ case PNK_RAW_UNDEFINED:
+ val.setUndefined();
+ break;
+
case PNK_TRUE:
val.setBoolean(true);
break;
@@ -3332,6 +3344,16 @@ ASTSerializer::objectPattern(ParseNode* pn, MutableHandleValue dst)
return false;
for (ParseNode* propdef = pn->pn_head; propdef; propdef = propdef->pn_next) {
+ if (propdef->isKind(PNK_SPREAD)) {
+ RootedValue target(cx);
+ RootedValue spread(cx);
+ if (!pattern(propdef->pn_kid, &target))
+ return false;
+ if(!builder.spreadExpression(target, &propdef->pn_pos, &spread))
+ return false;
+ elts.infallibleAppend(spread);
+ continue;
+ }
LOCAL_ASSERT(propdef->isKind(PNK_MUTATEPROTO) != propdef->isOp(JSOP_INITPROP));
RootedValue key(cx);
@@ -3407,12 +3429,7 @@ ASTSerializer::function(ParseNode* pn, ASTType type, MutableHandleValue dst)
: GeneratorStyle::None;
bool isAsync = pn->pn_funbox->isAsync();
- bool isExpression =
-#if JS_HAS_EXPR_CLOSURES
- func->isExprBody();
-#else
- false;
-#endif
+ bool isExpression = pn->pn_funbox->isExprBody();
RootedValue id(cx);
RootedAtom funcAtom(cx, func->explicitName());
diff --git a/js/src/builtin/RegExp.cpp b/js/src/builtin/RegExp.cpp
index b20f41c53..7cf20d23c 100644
--- a/js/src/builtin/RegExp.cpp
+++ b/js/src/builtin/RegExp.cpp
@@ -140,12 +140,12 @@ ExecuteRegExpImpl(JSContext* cx, RegExpStatics* res, RegExpShared& re, HandleLin
/* Legacy ExecuteRegExp behavior is baked into the JSAPI. */
bool
-js::ExecuteRegExpLegacy(JSContext* cx, RegExpStatics* res, RegExpObject& reobj,
+js::ExecuteRegExpLegacy(JSContext* cx, RegExpStatics* res, Handle<RegExpObject*> reobj,
HandleLinearString input, size_t* lastIndex, bool test,
MutableHandleValue rval)
{
RegExpGuard shared(cx);
- if (!reobj.getShared(cx, &shared))
+ if (!RegExpObject::getShared(cx, reobj, &shared))
return false;
ScopedMatchPairs matches(&cx->tempLifoAlloc());
@@ -801,7 +801,7 @@ const JSFunctionSpec js::regexp_methods[] = {
name(JSContext* cx, unsigned argc, Value* vp) \
{ \
CallArgs args = CallArgsFromVp(argc, vp); \
- RegExpStatics* res = cx->global()->getRegExpStatics(cx); \
+ RegExpStatics* res = GlobalObject::getRegExpStatics(cx, cx->global()); \
if (!res) \
return false; \
code; \
@@ -827,7 +827,7 @@ DEFINE_STATIC_GETTER(static_paren9_getter, STATIC_PAREN_GETTER_CODE(9))
static bool \
name(JSContext* cx, unsigned argc, Value* vp) \
{ \
- RegExpStatics* res = cx->global()->getRegExpStatics(cx); \
+ RegExpStatics* res = GlobalObject::getRegExpStatics(cx, cx->global()); \
if (!res) \
return false; \
code; \
@@ -838,7 +838,7 @@ static bool
static_input_setter(JSContext* cx, unsigned argc, Value* vp)
{
CallArgs args = CallArgsFromVp(argc, vp);
- RegExpStatics* res = cx->global()->getRegExpStatics(cx);
+ RegExpStatics* res = GlobalObject::getRegExpStatics(cx, cx->global());
if (!res)
return false;
@@ -918,12 +918,12 @@ ExecuteRegExp(JSContext* cx, HandleObject regexp, HandleString string,
Rooted<RegExpObject*> reobj(cx, &regexp->as<RegExpObject>());
RegExpGuard re(cx);
- if (!reobj->getShared(cx, &re))
+ if (!RegExpObject::getShared(cx, reobj, &re))
return RegExpRunStatus_Error;
RegExpStatics* res;
if (staticsUpdate == UpdateRegExpStatics) {
- res = cx->global()->getRegExpStatics(cx);
+ res = GlobalObject::getRegExpStatics(cx, cx->global());
if (!res)
return RegExpRunStatus_Error;
} else {
@@ -1725,7 +1725,7 @@ js::intrinsic_GetElemBaseForLambda(JSContext* cx, unsigned argc, Value* vp)
if (!fun->isInterpreted() || fun->isClassConstructor())
return true;
- JSScript* script = fun->getOrCreateScript(cx);
+ JSScript* script = JSFunction::getOrCreateScript(cx, fun);
if (!script)
return false;
@@ -1800,7 +1800,7 @@ js::intrinsic_GetStringDataProperty(JSContext* cx, unsigned argc, Value* vp)
return false;
RootedValue v(cx);
- if (HasDataProperty(cx, nobj, AtomToId(atom), v.address()) && v.isString())
+ if (GetPropertyPure(cx, nobj, AtomToId(atom), v.address()) && v.isString())
args.rval().set(v);
else
args.rval().setUndefined();
diff --git a/js/src/builtin/RegExp.h b/js/src/builtin/RegExp.h
index 715656f40..4e0ff6948 100644
--- a/js/src/builtin/RegExp.h
+++ b/js/src/builtin/RegExp.h
@@ -31,7 +31,7 @@ enum RegExpStaticsUpdate { UpdateRegExpStatics, DontUpdateRegExpStatics };
* |chars| and |length|.
*/
MOZ_MUST_USE bool
-ExecuteRegExpLegacy(JSContext* cx, RegExpStatics* res, RegExpObject& reobj,
+ExecuteRegExpLegacy(JSContext* cx, RegExpStatics* res, Handle<RegExpObject*> reobj,
HandleLinearString input, size_t* lastIndex, bool test,
MutableHandleValue rval);
diff --git a/js/src/builtin/SIMD.cpp b/js/src/builtin/SIMD.cpp
index 2383922db..5fe691152 100644
--- a/js/src/builtin/SIMD.cpp
+++ b/js/src/builtin/SIMD.cpp
@@ -475,7 +475,7 @@ const Class SimdObject::class_ = {
&SimdObjectClassOps
};
-bool
+/* static */ bool
GlobalObject::initSimdObject(JSContext* cx, Handle<GlobalObject*> global)
{
// SIMD relies on the TypedObject module being initialized.
@@ -483,11 +483,11 @@ GlobalObject::initSimdObject(JSContext* cx, Handle<GlobalObject*> global)
// to be able to call GetTypedObjectModule(). It is NOT necessary
// to install the TypedObjectModule global, but at the moment
// those two things are not separable.
- if (!global->getOrCreateTypedObjectModule(cx))
+ if (!GlobalObject::getOrCreateTypedObjectModule(cx, global))
return false;
RootedObject globalSimdObject(cx);
- RootedObject objProto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject objProto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!objProto)
return false;
@@ -510,7 +510,7 @@ static bool
CreateSimdType(JSContext* cx, Handle<GlobalObject*> global, HandlePropertyName stringRepr,
SimdType simdType, const JSFunctionSpec* methods)
{
- RootedObject funcProto(cx, global->getOrCreateFunctionPrototype(cx));
+ RootedObject funcProto(cx, GlobalObject::getOrCreateFunctionPrototype(cx, global));
if (!funcProto)
return false;
@@ -531,7 +531,7 @@ CreateSimdType(JSContext* cx, Handle<GlobalObject*> global, HandlePropertyName s
return false;
// Create prototype property, which inherits from Object.prototype.
- RootedObject objProto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject objProto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!objProto)
return false;
Rooted<TypedProto*> proto(cx);
@@ -551,7 +551,7 @@ CreateSimdType(JSContext* cx, Handle<GlobalObject*> global, HandlePropertyName s
}
// Bind type descriptor to the global SIMD object
- RootedObject globalSimdObject(cx, global->getOrCreateSimdGlobalObject(cx));
+ RootedObject globalSimdObject(cx, GlobalObject::getOrCreateSimdGlobalObject(cx, global));
MOZ_ASSERT(globalSimdObject);
RootedValue typeValue(cx, ObjectValue(*typeDescr));
@@ -568,7 +568,7 @@ CreateSimdType(JSContext* cx, Handle<GlobalObject*> global, HandlePropertyName s
return !!typeDescr;
}
-bool
+/* static */ bool
GlobalObject::initSimdType(JSContext* cx, Handle<GlobalObject*> global, SimdType simdType)
{
#define CREATE_(Type) \
@@ -584,13 +584,13 @@ GlobalObject::initSimdType(JSContext* cx, Handle<GlobalObject*> global, SimdType
#undef CREATE_
}
-SimdTypeDescr*
+/* static */ SimdTypeDescr*
GlobalObject::getOrCreateSimdTypeDescr(JSContext* cx, Handle<GlobalObject*> global,
SimdType simdType)
{
MOZ_ASSERT(unsigned(simdType) < unsigned(SimdType::Count), "Invalid SIMD type");
- RootedObject globalSimdObject(cx, global->getOrCreateSimdGlobalObject(cx));
+ RootedObject globalSimdObject(cx, GlobalObject::getOrCreateSimdGlobalObject(cx, global));
if (!globalSimdObject)
return nullptr;
@@ -628,8 +628,8 @@ SimdObject::resolve(JSContext* cx, JS::HandleObject obj, JS::HandleId id, bool*
JSObject*
js::InitSimdClass(JSContext* cx, HandleObject obj)
{
- Rooted<GlobalObject*> global(cx, &obj->as<GlobalObject>());
- return global->getOrCreateSimdGlobalObject(cx);
+ Handle<GlobalObject*> global = obj.as<GlobalObject>();
+ return GlobalObject::getOrCreateSimdGlobalObject(cx, global);
}
template<typename V>
diff --git a/js/src/builtin/SymbolObject.cpp b/js/src/builtin/SymbolObject.cpp
index ae38d5371..8fa860ef3 100644
--- a/js/src/builtin/SymbolObject.cpp
+++ b/js/src/builtin/SymbolObject.cpp
@@ -53,17 +53,17 @@ const JSFunctionSpec SymbolObject::staticMethods[] = {
JSObject*
SymbolObject::initClass(JSContext* cx, HandleObject obj)
{
- Rooted<GlobalObject*> global(cx, &obj->as<GlobalObject>());
+ Handle<GlobalObject*> global = obj.as<GlobalObject>();
// This uses &JSObject::class_ because: "The Symbol prototype object is an
// ordinary object. It is not a Symbol instance and does not have a
// [[SymbolData]] internal slot." (ES6 rev 24, 19.4.3)
- RootedObject proto(cx, global->createBlankPrototype<PlainObject>(cx));
+ RootedObject proto(cx, GlobalObject::createBlankPrototype<PlainObject>(cx, global));
if (!proto)
return nullptr;
- RootedFunction ctor(cx, global->createConstructor(cx, construct,
- ClassName(JSProto_Symbol, cx), 0));
+ RootedFunction ctor(cx, GlobalObject::createConstructor(cx, construct,
+ ClassName(JSProto_Symbol, cx), 0));
if (!ctor)
return nullptr;
diff --git a/js/src/builtin/TestingFunctions.cpp b/js/src/builtin/TestingFunctions.cpp
index c896ce5d1..992fe2c97 100644
--- a/js/src/builtin/TestingFunctions.cpp
+++ b/js/src/builtin/TestingFunctions.cpp
@@ -3218,13 +3218,13 @@ ByteSizeOfScript(JSContext*cx, unsigned argc, Value* vp)
return false;
}
- JSFunction* fun = &args[0].toObject().as<JSFunction>();
+ RootedFunction fun(cx, &args[0].toObject().as<JSFunction>());
if (fun->isNative()) {
JS_ReportErrorASCII(cx, "Argument must be a scripted function");
return false;
}
- RootedScript script(cx, fun->getOrCreateScript(cx));
+ RootedScript script(cx, JSFunction::getOrCreateScript(cx, fun));
if (!script)
return false;
@@ -3319,7 +3319,8 @@ GetConstructorName(JSContext* cx, unsigned argc, Value* vp)
}
RootedAtom name(cx);
- if (!args[0].toObject().constructorDisplayAtom(cx, &name))
+ RootedObject obj(cx, &args[0].toObject());
+ if (!JSObject::constructorDisplayAtom(cx, obj, &name))
return false;
if (name) {
@@ -4023,7 +4024,7 @@ DisRegExp(JSContext* cx, unsigned argc, Value* vp)
return false;
}
- if (!reobj->dumpBytecode(cx, match_only, input))
+ if (!RegExpObject::dumpBytecode(cx, reobj, match_only, input))
return false;
args.rval().setUndefined();
@@ -4042,6 +4043,32 @@ IsConstructor(JSContext* cx, unsigned argc, Value* vp)
return true;
}
+static bool
+GetErrorNotes(JSContext* cx, unsigned argc, Value* vp)
+{
+ CallArgs args = CallArgsFromVp(argc, vp);
+ if (!args.requireAtLeast(cx, "getErrorNotes", 1))
+ return false;
+
+ if (!args[0].isObject() || !args[0].toObject().is<ErrorObject>()) {
+ args.rval().setNull();
+ return true;
+ }
+
+ JSErrorReport* report = args[0].toObject().as<ErrorObject>().getErrorReport();
+ if (!report) {
+ args.rval().setNull();
+ return true;
+ }
+
+ RootedObject notesArray(cx, CreateErrorNotesArray(cx, report));
+ if (!notesArray)
+ return false;
+
+ args.rval().setObject(*notesArray);
+ return true;
+}
+
static const JSFunctionSpecWithHelp TestingFunctions[] = {
JS_FN_HELP("gc", ::GC, 0, 0,
"gc([obj] | 'zone' [, 'shrinking'])",
@@ -4576,6 +4603,10 @@ static const JSFunctionSpecWithHelp FuzzingUnsafeTestingFunctions[] = {
" Dumps RegExp bytecode."),
#endif
+ JS_FN_HELP("getErrorNotes", GetErrorNotes, 1, 0,
+"getErrorNotes(error)",
+" Returns an array of error notes."),
+
JS_FS_HELP_END
};
diff --git a/js/src/builtin/TypedObject.cpp b/js/src/builtin/TypedObject.cpp
index 0dfc1123a..ff3680774 100644
--- a/js/src/builtin/TypedObject.cpp
+++ b/js/src/builtin/TypedObject.cpp
@@ -1124,11 +1124,11 @@ DefineSimpleTypeDescr(JSContext* cx,
typename T::Type type,
HandlePropertyName className)
{
- RootedObject objProto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject objProto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!objProto)
return false;
- RootedObject funcProto(cx, global->getOrCreateFunctionPrototype(cx));
+ RootedObject funcProto(cx, GlobalObject::getOrCreateFunctionPrototype(cx, global));
if (!funcProto)
return false;
@@ -1185,7 +1185,7 @@ DefineMetaTypeDescr(JSContext* cx,
if (!className)
return nullptr;
- RootedObject funcProto(cx, global->getOrCreateFunctionPrototype(cx));
+ RootedObject funcProto(cx, GlobalObject::getOrCreateFunctionPrototype(cx, global));
if (!funcProto)
return nullptr;
@@ -1197,7 +1197,7 @@ DefineMetaTypeDescr(JSContext* cx,
// Create ctor.prototype.prototype, which inherits from Object.__proto__
- RootedObject objProto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject objProto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!objProto)
return nullptr;
RootedObject protoProto(cx);
@@ -1216,7 +1216,7 @@ DefineMetaTypeDescr(JSContext* cx,
const int constructorLength = 2;
RootedFunction ctor(cx);
- ctor = global->createConstructor(cx, T::construct, className, constructorLength);
+ ctor = GlobalObject::createConstructor(cx, T::construct, className, constructorLength);
if (!ctor ||
!LinkConstructorAndPrototype(cx, ctor, proto) ||
!DefinePropertiesAndFunctions(cx, proto,
@@ -1240,10 +1240,10 @@ DefineMetaTypeDescr(JSContext* cx,
* initializer for the `TypedObject` class populate the
* `TypedObject` global (which is referred to as "module" herein).
*/
-bool
+/* static */ bool
GlobalObject::initTypedObjectModule(JSContext* cx, Handle<GlobalObject*> global)
{
- RootedObject objProto(cx, global->getOrCreateObjectPrototype(cx));
+ RootedObject objProto(cx, GlobalObject::getOrCreateObjectPrototype(cx, global));
if (!objProto)
return false;
@@ -1317,9 +1317,8 @@ GlobalObject::initTypedObjectModule(JSContext* cx, Handle<GlobalObject*> global)
JSObject*
js::InitTypedObjectModuleObject(JSContext* cx, HandleObject obj)
{
- MOZ_ASSERT(obj->is<GlobalObject>());
- Rooted<GlobalObject*> global(cx, &obj->as<GlobalObject>());
- return global->getOrCreateTypedObjectModule(cx);
+ Handle<GlobalObject*> global = obj.as<GlobalObject>();
+ return GlobalObject::getOrCreateTypedObjectModule(cx, global);
}
/******************************************************************************
diff --git a/js/src/builtin/Utilities.js b/js/src/builtin/Utilities.js
index c73bc5e7f..d5f233d05 100644
--- a/js/src/builtin/Utilities.js
+++ b/js/src/builtin/Utilities.js
@@ -229,6 +229,69 @@ function GetInternalError(msg) {
// To be used when a function is required but calling it shouldn't do anything.
function NullFunction() {}
+// Object Rest/Spread Properties proposal
+// Abstract operation: CopyDataProperties (target, source, excluded)
+function CopyDataProperties(target, source, excluded) {
+ // Step 1.
+ assert(IsObject(target), "target is an object");
+
+ // Step 2.
+ assert(IsObject(excluded), "excluded is an object");
+
+ // Steps 3, 6.
+ if (source === undefined || source === null)
+ return;
+
+ // Step 4.a.
+ source = ToObject(source);
+
+ // Step 4.b.
+ var keys = OwnPropertyKeys(source, JSITER_OWNONLY | JSITER_HIDDEN | JSITER_SYMBOLS);
+
+ // Step 5.
+ for (var index = 0; index < keys.length; index++) {
+ var key = keys[index];
+
+ // We abbreviate this by calling propertyIsEnumerable which is faster
+ // and returns false for not defined properties.
+ if (!callFunction(std_Object_hasOwnProperty, excluded, key) && callFunction(std_Object_propertyIsEnumerable, source, key))
+ _DefineDataProperty(target, key, source[key]);
+ }
+
+ // Step 6 (Return).
+}
+
+// Object Rest/Spread Properties proposal
+// Abstract operation: CopyDataProperties (target, source, excluded)
+function CopyDataPropertiesUnfiltered(target, source) {
+ // Step 1.
+ assert(IsObject(target), "target is an object");
+
+ // Step 2 (Not applicable).
+
+ // Steps 3, 6.
+ if (source === undefined || source === null)
+ return;
+
+ // Step 4.a.
+ source = ToObject(source);
+
+ // Step 4.b.
+ var keys = OwnPropertyKeys(source, JSITER_OWNONLY | JSITER_HIDDEN | JSITER_SYMBOLS);
+
+ // Step 5.
+ for (var index = 0; index < keys.length; index++) {
+ var key = keys[index];
+
+ // We abbreviate this by calling propertyIsEnumerable which is faster
+ // and returns false for not defined properties.
+ if (callFunction(std_Object_propertyIsEnumerable, source, key))
+ _DefineDataProperty(target, key, source[key]);
+ }
+
+ // Step 6 (Return).
+}
+
/*************************************** Testing functions ***************************************/
function outer() {
return function inner() {
diff --git a/js/src/builtin/WeakMapObject.cpp b/js/src/builtin/WeakMapObject.cpp
index 555b9e03a..dcfa19776 100644
--- a/js/src/builtin/WeakMapObject.cpp
+++ b/js/src/builtin/WeakMapObject.cpp
@@ -350,14 +350,14 @@ InitWeakMapClass(JSContext* cx, HandleObject obj, bool defineMembers)
{
MOZ_ASSERT(obj->isNative());
- Rooted<GlobalObject*> global(cx, &obj->as<GlobalObject>());
+ Handle<GlobalObject*> global = obj.as<GlobalObject>();
RootedPlainObject proto(cx, NewBuiltinClassInstance<PlainObject>(cx));
if (!proto)
return nullptr;
- RootedFunction ctor(cx, global->createConstructor(cx, WeakMap_construct,
- cx->names().WeakMap, 0));
+ RootedFunction ctor(cx, GlobalObject::createConstructor(cx, WeakMap_construct,
+ cx->names().WeakMap, 0));
if (!ctor)
return nullptr;
diff --git a/js/src/builtin/WeakSetObject.cpp b/js/src/builtin/WeakSetObject.cpp
index 7ea3f2fef..fbe5e418c 100644
--- a/js/src/builtin/WeakSetObject.cpp
+++ b/js/src/builtin/WeakSetObject.cpp
@@ -41,14 +41,15 @@ const JSFunctionSpec WeakSetObject::methods[] = {
};
JSObject*
-WeakSetObject::initClass(JSContext* cx, JSObject* obj)
+WeakSetObject::initClass(JSContext* cx, HandleObject obj)
{
- Rooted<GlobalObject*> global(cx, &obj->as<GlobalObject>());
+ Handle<GlobalObject*> global = obj.as<GlobalObject>();
RootedPlainObject proto(cx, NewBuiltinClassInstance<PlainObject>(cx));
if (!proto)
return nullptr;
- Rooted<JSFunction*> ctor(cx, global->createConstructor(cx, construct, ClassName(JSProto_WeakSet, cx), 0));
+ Rooted<JSFunction*> ctor(cx, GlobalObject::createConstructor(cx, construct,
+ ClassName(JSProto_WeakSet, cx), 0));
if (!ctor ||
!LinkConstructorAndPrototype(cx, ctor, proto) ||
!DefinePropertiesAndFunctions(cx, proto, properties, methods) ||
diff --git a/js/src/builtin/WeakSetObject.h b/js/src/builtin/WeakSetObject.h
index 0a6ff33f3..50e54c182 100644
--- a/js/src/builtin/WeakSetObject.h
+++ b/js/src/builtin/WeakSetObject.h
@@ -16,7 +16,7 @@ class WeakSetObject : public NativeObject
public:
static const unsigned RESERVED_SLOTS = 1;
- static JSObject* initClass(JSContext* cx, JSObject* obj);
+ static JSObject* initClass(JSContext* cx, HandleObject obj);
static const Class class_;
private: