Backed out changeset b6f1126059ef (bug 1198377) for asserting in for-in-iterator-1.js. r=backout

This commit is contained in:
Sebastian Hengst 2016-10-07 17:53:15 +02:00
Родитель 375da61c8b
Коммит 6fe4a47253
13 изменённых файлов: 218 добавлений и 317 удалений

Просмотреть файл

@ -2,53 +2,8 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
// ES2017 draft rev 0e10c9f29fca1385980c08a7d5e7bb3eb775e2e4
// 23.1.1.1 Map, steps 6-8
function MapConstructorInit(iterable) {
var map = this;
// Step 6.a.
var adder = map.set;
// Step 6.b.
if (!IsCallable(adder))
ThrowTypeError(JSMSG_NOT_FUNCTION, typeof adder);
// Step 6.c.
var iterFn = iterable[std_iterator];
if (!IsCallable(iterFn))
ThrowTypeError(JSMSG_NOT_ITERABLE, DecompileArg(0, iterable));
var iter = callContentFunction(iterFn, iterable);
if (!IsObject(iter))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof iter);
// Step 7 (not applicable).
// Step 8.
while (true) {
// Step 8.a.
var next = callContentFunction(iter.next, iter);
if (!IsObject(next))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof next);
// Step 8.b.
if (next.done)
return;
// Step 8.c.
var nextItem = next.value;
// Step 8.d.
if (!IsObject(nextItem))
ThrowTypeError(JSMSG_INVALID_MAP_ITERABLE, "Map");
// Steps 8.e-j.
callContentFunction(adder, map, nextItem[0], nextItem[1]);
}
}
/* ES6 20121122 draft 15.14.4.4. */
function MapForEach(callbackfn, thisArg = undefined) {
/* Step 1-2. */
var M = this;

Просмотреть файл

@ -15,7 +15,6 @@
#include "js/Utility.h"
#include "vm/GlobalObject.h"
#include "vm/Interpreter.h"
#include "vm/SelfHosting.h"
#include "jsobjinlines.h"
@ -501,12 +500,72 @@ MapObject::construct(JSContext* cx, unsigned argc, Value* vp)
return false;
if (!args.get(0).isNullOrUndefined()) {
FixedInvokeArgs<1> args2(cx);
args2[0].set(args[0]);
RootedValue thisv(cx, ObjectValue(*obj));
if (!CallSelfHostedFunction(cx, cx->names().MapConstructorInit, thisv, args2, args2.rval()))
RootedValue adderVal(cx);
if (!GetProperty(cx, obj, obj, cx->names().set, &adderVal))
return false;
if (!IsCallable(adderVal))
return ReportIsNotFunction(cx, adderVal);
bool isOriginalAdder = IsNativeFunction(adderVal, MapObject::set);
RootedValue mapVal(cx, ObjectValue(*obj));
FastCallGuard fig(cx, adderVal);
InvokeArgs& args2 = fig.args();
ForOfIterator iter(cx);
if (!iter.init(args[0]))
return false;
RootedValue pairVal(cx);
RootedObject pairObj(cx);
RootedValue dummy(cx);
Rooted<HashableValue> hkey(cx);
ValueMap* map = obj->getData();
while (true) {
bool done;
if (!iter.next(&pairVal, &done))
return false;
if (done)
break;
if (!pairVal.isObject()) {
JS_ReportErrorNumberASCII(cx, GetErrorMessage, nullptr, JSMSG_INVALID_MAP_ITERABLE,
"Map");
return false;
}
pairObj = &pairVal.toObject();
if (!pairObj)
return false;
RootedValue key(cx);
if (!GetElement(cx, pairObj, pairObj, 0, &key))
return false;
RootedValue val(cx);
if (!GetElement(cx, pairObj, pairObj, 1, &val))
return false;
if (isOriginalAdder) {
if (!hkey.setValue(cx, key))
return false;
HeapPtr<Value> rval(val);
if (!map->put(hkey, rval)) {
ReportOutOfMemory(cx);
return false;
}
WriteBarrierPost(cx->runtime(), map, key);
} else {
if (!args2.init(2))
return false;
args2[0].set(key);
args2[1].set(val);
if (!fig.call(cx, adderVal, mapVal, &dummy))
return false;
}
}
}
args.rval().setObject(*obj);
@ -1083,12 +1142,6 @@ SetObject::finalize(FreeOp* fop, JSObject* obj)
fop->delete_(set);
}
bool
SetObject::isBuiltinAdd(HandleValue add, JSContext* cx)
{
return IsNativeFunction(add, SetObject::add);
}
bool
SetObject::construct(JSContext* cx, unsigned argc, Value* vp)
{
@ -1107,20 +1160,33 @@ SetObject::construct(JSContext* cx, unsigned argc, Value* vp)
return false;
if (!args.get(0).isNullOrUndefined()) {
RootedValue iterable(cx, args[0]);
bool optimized = false;
if (!IsOptimizableInitForSet<GlobalObject::getOrCreateSetPrototype, isBuiltinAdd>(cx, obj, iterable, &optimized))
RootedValue adderVal(cx);
if (!GetProperty(cx, obj, obj, cx->names().add, &adderVal))
return false;
if (optimized) {
RootedValue keyVal(cx);
Rooted<HashableValue> key(cx);
ValueSet* set = obj->getData();
ArrayObject* array = &iterable.toObject().as<ArrayObject>();
for (uint32_t index = 0; index < array->getDenseInitializedLength(); ++index) {
keyVal.set(array->getDenseElement(index));
MOZ_ASSERT(!keyVal.isMagic(JS_ELEMENTS_HOLE));
if (!IsCallable(adderVal))
return ReportIsNotFunction(cx, adderVal);
bool isOriginalAdder = IsNativeFunction(adderVal, SetObject::add);
RootedValue setVal(cx, ObjectValue(*obj));
FastCallGuard fig(cx, adderVal);
InvokeArgs& args2 = fig.args();
RootedValue keyVal(cx);
ForOfIterator iter(cx);
if (!iter.init(args[0]))
return false;
Rooted<HashableValue> key(cx);
RootedValue dummy(cx);
ValueSet* set = obj->getData();
while (true) {
bool done;
if (!iter.next(&keyVal, &done))
return false;
if (done)
break;
if (isOriginalAdder) {
if (!key.setValue(cx, keyVal))
return false;
if (!set->put(key)) {
@ -1128,14 +1194,15 @@ SetObject::construct(JSContext* cx, unsigned argc, Value* vp)
return false;
}
WriteBarrierPost(cx->runtime(), set, keyVal);
}
} else {
FixedInvokeArgs<1> args2(cx);
args2[0].set(args[0]);
RootedValue thisv(cx, ObjectValue(*obj));
if (!CallSelfHostedFunction(cx, cx->names().SetConstructorInit, thisv, args2, args2.rval()))
if (!args2.init(1))
return false;
args2[0].set(keyVal);
if (!fig.call(cx, adderVal, setVal, &dummy))
return false;
}
}
}

Просмотреть файл

@ -10,8 +10,6 @@
#include "jsobj.h"
#include "builtin/SelfHostingDefines.h"
#include "vm/GlobalObject.h"
#include "vm/PIC.h"
#include "vm/Runtime.h"
namespace js {
@ -215,8 +213,6 @@ class SetObject : public NativeObject {
static bool is(HandleValue v);
static bool is(HandleObject o);
static bool isBuiltinAdd(HandleValue add, JSContext* cx);
static MOZ_MUST_USE bool iterator_impl(JSContext* cx, const CallArgs& args, IteratorKind kind);
static MOZ_MUST_USE bool size_impl(JSContext* cx, const CallArgs& args);
@ -255,48 +251,6 @@ class SetIteratorObject : public NativeObject
extern bool
InitSelfHostingCollectionIteratorFunctions(JSContext* cx, js::HandleObject obj);
bool IsPackedArray(JSObject* obj);
using SetInitGetPrototypeOp = NativeObject* (*)(JSContext*, Handle<GlobalObject*>);
using SetInitIsBuiltinOp = bool (*)(HandleValue, JSContext*);
template <SetInitGetPrototypeOp getPrototypeOp, SetInitIsBuiltinOp isBuiltinOp>
static MOZ_MUST_USE bool
IsOptimizableInitForSet(JSContext* cx, HandleObject setObject, HandleValue iterable, bool* optimized)
{
if (!iterable.isObject())
return true;
RootedObject array(cx, &iterable.toObject());
if (!IsPackedArray(array))
return true;
// Get the canonical prototype object.
RootedNativeObject setProto(cx, getPrototypeOp(cx, cx->global()));
if (!setProto)
return false;
// Ensures setObject's prototype is the canonical prototype.
if (setObject->staticPrototype() != setProto)
return true;
// Look up the 'add' value on the prototype object.
Shape* addShape = setProto->lookup(cx, cx->names().add);
if (!addShape || !addShape->hasSlot())
return true;
// Get the referred value, ensure it holds the canonical add function.
RootedValue add(cx, setProto->getSlot(addShape->slot()));
if (!isBuiltinOp(add, cx))
return true;
ForOfPIC::Chain* stubChain = ForOfPIC::getOrCreate(cx);
if (!stubChain)
return false;
return stubChain->tryOptimizeArray(cx, array.as<ArrayObject>(), optimized);
}
extern JSObject*
InitMapClass(JSContext* cx, HandleObject obj);

Просмотреть файл

@ -2,49 +2,8 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
// ES2017 draft rev 0e10c9f29fca1385980c08a7d5e7bb3eb775e2e4
// 23.2.1.1 Set, steps 6-8
function SetConstructorInit(iterable) {
var set = this;
// Step 6.a.
var adder = set.add;
// Step 6.b.
if (!IsCallable(adder))
ThrowTypeError(JSMSG_NOT_FUNCTION, typeof adder);
// Step 6.c.
var iterFn = iterable[std_iterator];
if (!IsCallable(iterFn))
ThrowTypeError(JSMSG_NOT_ITERABLE, DecompileArg(0, iterable));
var iter = callContentFunction(iterFn, iterable);
if (!IsObject(iter))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof iter);
// Step 7 (not applicable).
// Step 8.
while (true) {
// Step 8.a.
var next = callContentFunction(iter.next, iter);
if (!IsObject(next))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof next);
// Step 8.b.
if (next.done)
return;
// Step 8.c.
var nextValue = next.value;
// Steps 8.d-e.
callContentFunction(adder, set, nextValue);
}
}
/* ES6 20121122 draft 15.16.4.6. */
function SetForEach(callbackfn, thisArg = undefined) {
/* Step 1-2. */
var S = this;

Просмотреть файл

@ -1,49 +0,0 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
// ES2017 draft rev 0e10c9f29fca1385980c08a7d5e7bb3eb775e2e4
// 23.3.1.1 WeakMap, steps 6-8
function WeakMapConstructorInit(iterable) {
var map = this;
// Step 6.a.
var adder = map.set;
// Step 6.b.
if (!IsCallable(adder))
ThrowTypeError(JSMSG_NOT_FUNCTION, typeof adder);
// Step 6.c.
var iterFn = iterable[std_iterator];
if (!IsCallable(iterFn))
ThrowTypeError(JSMSG_NOT_ITERABLE, DecompileArg(0, iterable));
var iter = callContentFunction(iterFn, iterable);
if (!IsObject(iter))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof iter);
// Step 7 (not applicable).
// Step 8.
while (true) {
// Step 8.a.
var next = callContentFunction(iter.next, iter);
if (!IsObject(next))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof next);
// Step 8.b.
if (next.done)
return;
// Step 8.c.
var nextItem = next.value;
// Step 8.d.
if (!IsObject(nextItem))
ThrowTypeError(JSMSG_INVALID_MAP_ITERABLE, "WeakMap");
// Steps 8.e-j.
callContentFunction(adder, map, nextItem[0], nextItem[1]);
}
}

Просмотреть файл

@ -9,8 +9,6 @@
#include "jsapi.h"
#include "jscntxt.h"
#include "vm/SelfHosting.h"
#include "vm/Interpreter-inl.h"
using namespace js;
@ -302,12 +300,85 @@ WeakMap_construct(JSContext* cx, unsigned argc, Value* vp)
// Steps 5-6, 11.
if (!args.get(0).isNullOrUndefined()) {
FixedInvokeArgs<1> args2(cx);
args2[0].set(args[0]);
RootedValue thisv(cx, ObjectValue(*obj));
if (!CallSelfHostedFunction(cx, cx->names().WeakMapConstructorInit, thisv, args2, args2.rval()))
// Steps 7a-b.
RootedValue adderVal(cx);
if (!GetProperty(cx, obj, obj, cx->names().set, &adderVal))
return false;
// Step 7c.
if (!IsCallable(adderVal))
return ReportIsNotFunction(cx, adderVal);
bool isOriginalAdder = IsNativeFunction(adderVal, WeakMap_set);
RootedValue mapVal(cx, ObjectValue(*obj));
FastCallGuard fig(cx, adderVal);
InvokeArgs& args2 = fig.args();
// Steps 7d-e.
JS::ForOfIterator iter(cx);
if (!iter.init(args[0]))
return false;
RootedValue pairVal(cx);
RootedObject pairObject(cx);
RootedValue keyVal(cx);
RootedObject keyObject(cx);
RootedValue val(cx);
RootedValue dummy(cx);
while (true) {
// Steps 12a-e.
bool done;
if (!iter.next(&pairVal, &done))
return false;
if (done)
break;
// Step 12f.
if (!pairVal.isObject()) {
JS_ReportErrorNumberASCII(cx, GetErrorMessage, nullptr, JSMSG_INVALID_MAP_ITERABLE,
"WeakMap");
return false;
}
pairObject = &pairVal.toObject();
if (!pairObject)
return false;
// Steps 12g-h.
if (!GetElement(cx, pairObject, pairObject, 0, &keyVal))
return false;
// Steps 12i-j.
if (!GetElement(cx, pairObject, pairObject, 1, &val))
return false;
// Steps 12k-l.
if (isOriginalAdder) {
if (keyVal.isPrimitive()) {
UniqueChars bytes =
DecompileValueGenerator(cx, JSDVG_SEARCH_STACK, keyVal, nullptr);
if (!bytes)
return false;
JS_ReportErrorNumberLatin1(cx, GetErrorMessage, nullptr,
JSMSG_NOT_NONNULL_OBJECT,
bytes.get());
return false;
}
keyObject = &keyVal.toObject();
if (!SetWeakMapEntry(cx, obj, keyObject, val))
return false;
} else {
if (!args2.init(2))
return false;
args2[0].set(keyVal);
args2[1].set(val);
if (!fig.call(cx, adderVal, mapVal, &dummy))
return false;
}
}
}
args.rval().setObject(*obj);

Просмотреть файл

@ -2,48 +2,6 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
// ES2017 draft rev 0e10c9f29fca1385980c08a7d5e7bb3eb775e2e4
// 23.4.1.1 WeakSet, steps 6-8
function WeakSetConstructorInit(iterable) {
var set = this;
// Step 6.a.
var adder = set.add;
// Step 6.b.
if (!IsCallable(adder))
ThrowTypeError(JSMSG_NOT_FUNCTION, typeof adder);
// Step 6.c.
var iterFn = iterable[std_iterator];
if (!IsCallable(iterFn))
ThrowTypeError(JSMSG_NOT_ITERABLE, DecompileArg(0, iterable));
var iter = callContentFunction(iterFn, iterable);
if (!IsObject(iter))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof iter);
// Step 7 (not applicable).
// Step 8.
while (true) {
// Step 8.a.
var next = callContentFunction(iter.next, iter);
if (!IsObject(next))
ThrowTypeError(JSMSG_NOT_NONNULL_OBJECT, typeof next);
// Step 8.b.
if (next.done)
return;
// Step 8.c.
var nextValue = next.value;
// Steps 8.d-e.
callContentFunction(adder, set, nextValue);
}
}
// 23.4.3.1
function WeakSet_add(value) {
// Steps 1-3.

Просмотреть файл

@ -10,7 +10,6 @@
#include "jscntxt.h"
#include "jsiter.h"
#include "builtin/MapObject.h"
#include "builtin/SelfHostingDefines.h"
#include "builtin/WeakMapObject.h"
#include "vm/GlobalObject.h"
@ -75,13 +74,6 @@ WeakSetObject::create(JSContext* cx, HandleObject proto /* = nullptr */)
return obj;
}
bool
WeakSetObject::isBuiltinAdd(HandleValue add, JSContext* cx)
{
JSFunction* addFn;
return IsFunctionObject(add, &addFn) && IsSelfHostedFunctionWithName(addFn, cx->names().WeakSet_add);
}
bool
WeakSetObject::construct(JSContext* cx, unsigned argc, Value* vp)
{
@ -101,42 +93,61 @@ WeakSetObject::construct(JSContext* cx, unsigned argc, Value* vp)
return false;
if (!args.get(0).isNullOrUndefined()) {
RootedValue iterable(cx, args[0]);
bool optimized = false;
if (!IsOptimizableInitForSet<GlobalObject::getOrCreateWeakSetPrototype, isBuiltinAdd>(cx, obj, iterable, &optimized))
RootedObject map(cx, &obj->getReservedSlot(WEAKSET_MAP_SLOT).toObject());
RootedValue adderVal(cx);
if (!GetProperty(cx, obj, obj, cx->names().add, &adderVal))
return false;
if (!IsCallable(adderVal))
return ReportIsNotFunction(cx, adderVal);
JSFunction* adder;
bool isOriginalAdder = IsFunctionObject(adderVal, &adder) &&
IsSelfHostedFunctionWithName(adder, cx->names().WeakSet_add);
RootedValue setVal(cx, ObjectValue(*obj));
FastCallGuard fig(cx, adderVal);
InvokeArgs& args2 = fig.args();
JS::ForOfIterator iter(cx);
if (!iter.init(args[0]))
return false;
if (optimized) {
RootedValue keyVal(cx);
RootedObject keyObject(cx);
RootedValue dummy(cx);
RootedValue placeholder(cx, BooleanValue(true));
RootedObject map(cx, &obj->getReservedSlot(WEAKSET_MAP_SLOT).toObject());
RootedArrayObject array(cx, &iterable.toObject().as<ArrayObject>());
for (uint32_t index = 0; index < array->getDenseInitializedLength(); ++index) {
keyVal.set(array->getDenseElement(index));
MOZ_ASSERT(!keyVal.isMagic(JS_ELEMENTS_HOLE));
while (true) {
bool done;
if (!iter.next(&keyVal, &done))
return false;
if (done)
break;
if (isOriginalAdder) {
if (keyVal.isPrimitive()) {
UniqueChars bytes =
DecompileValueGenerator(cx, JSDVG_SEARCH_STACK, keyVal, nullptr);
if (!bytes)
return false;
JS_ReportErrorNumberLatin1(cx, GetErrorMessage, nullptr,
JSMSG_NOT_NONNULL_OBJECT, bytes.get());
JSMSG_NOT_NONNULL_OBJECT,
bytes.get());
return false;
}
keyObject = &keyVal.toObject();
if (!SetWeakMapEntry(cx, map, keyObject, placeholder))
return false;
}
} else {
FixedInvokeArgs<1> args2(cx);
args2[0].set(args[0]);
RootedValue thisv(cx, ObjectValue(*obj));
if (!CallSelfHostedFunction(cx, cx->names().WeakSetConstructorInit, thisv, args2, args2.rval()))
if (!args2.init(1))
return false;
args2[0].set(keyVal);
if (!fig.call(cx, adderVal, setVal, &dummy))
return false;
}
}
}

Просмотреть файл

@ -25,8 +25,6 @@ class WeakSetObject : public NativeObject
static WeakSetObject* create(JSContext* cx, HandleObject proto = nullptr);
static MOZ_MUST_USE bool construct(JSContext* cx, unsigned argc, Value* vp);
static bool isBuiltinAdd(HandleValue add, JSContext* cx);
};
extern JSObject*

Просмотреть файл

@ -1578,20 +1578,14 @@ DecompileArgumentFromStack(JSContext* cx, int formalIndex, char** res)
return true;
/* Don't handle getters, setters or calls from fun.call/fun.apply. */
JSOp op = JSOp(*current);
if (op != JSOP_CALL && op != JSOP_NEW)
return true;
if (static_cast<unsigned>(formalIndex) >= GET_ARGC(current))
if (JSOp(*current) != JSOP_CALL || static_cast<unsigned>(formalIndex) >= GET_ARGC(current))
return true;
BytecodeParser parser(cx, script);
if (!parser.parse())
return false;
bool pushedNewTarget = op == JSOP_NEW;
int formalStackIndex = parser.stackDepthAtPC(current) - GET_ARGC(current) - pushedNewTarget +
formalIndex;
int formalStackIndex = parser.stackDepthAtPC(current) - GET_ARGC(current) + formalIndex;
MOZ_ASSERT(formalStackIndex >= 0);
if (uint32_t(formalStackIndex) >= parser.stackDepthAtPC(current))
return true;

Просмотреть файл

@ -767,7 +767,6 @@ selfhosted.inputs = [
'builtin/Sorting.js',
'builtin/TypedArray.js',
'builtin/TypedObject.js',
'builtin/WeakMap.js',
'builtin/WeakSet.js'
]

Просмотреть файл

@ -181,7 +181,6 @@
macro(locale, locale, "locale") \
macro(lookupGetter, lookupGetter, "__lookupGetter__") \
macro(lookupSetter, lookupSetter, "__lookupSetter__") \
macro(MapConstructorInit, MapConstructorInit, "MapConstructorInit") \
macro(MapIterator, MapIterator, "Map Iterator") \
macro(maximumFractionDigits, maximumFractionDigits, "maximumFractionDigits") \
macro(maximumSignificantDigits, maximumSignificantDigits, "maximumSignificantDigits") \
@ -263,7 +262,6 @@
macro(selfHosted, selfHosted, "self-hosted") \
macro(sensitivity, sensitivity, "sensitivity") \
macro(set, set, "set") \
macro(SetConstructorInit, SetConstructorInit, "SetConstructorInit") \
macro(SetIterator, SetIterator, "Set Iterator") \
macro(setPrefix, setPrefix, "set ") \
macro(setPrototypeOf, setPrototypeOf, "setPrototypeOf") \
@ -328,8 +326,6 @@
macro(void0, void0, "(void 0)") \
macro(wasm, wasm, "wasm") \
macro(watch, watch, "watch") \
macro(WeakMapConstructorInit, WeakMapConstructorInit, "WeakMapConstructorInit") \
macro(WeakSetConstructorInit, WeakSetConstructorInit, "WeakSetConstructorInit") \
macro(WeakSet_add, WeakSet_add, "WeakSet_add") \
macro(weekday, weekday, "weekday") \
macro(weekendEnd, weekendEnd, "weekendEnd") \

Просмотреть файл

@ -427,18 +427,6 @@ class GlobalObject : public NativeObject
return &global->getPrototype(key).toObject();
}
static NativeObject* getOrCreateSetPrototype(JSContext* cx, Handle<GlobalObject*> global) {
if (!ensureConstructor(cx, global, JSProto_Set))
return nullptr;
return &global->getPrototype(JSProto_Set).toObject().as<NativeObject>();
}
static NativeObject* getOrCreateWeakSetPrototype(JSContext* cx, Handle<GlobalObject*> global) {
if (!ensureConstructor(cx, global, JSProto_WeakSet))
return nullptr;
return &global->getPrototype(JSProto_WeakSet).toObject().as<NativeObject>();
}
JSObject* getOrCreateIntlObject(JSContext* cx) {
return getOrCreateObject(cx, APPLICATION_SLOTS + JSProto_Intl, initIntlObject);
}