#410, #413: M1370210 M1346217 partial

This commit is contained in:
Cameron Kaiser 2017-07-02 18:44:51 -07:00
parent d22246efad
commit 320e8fda0a
4 changed files with 47 additions and 49 deletions

View File

@ -18,7 +18,7 @@ namespace js {
/* 2^32-2, inclusive */ /* 2^32-2, inclusive */
const uint32_t MAX_ARRAY_INDEX = 4294967294u; const uint32_t MAX_ARRAY_INDEX = 4294967294u;
inline bool MOZ_ALWAYS_INLINE bool
IdIsIndex(jsid id, uint32_t* indexp) IdIsIndex(jsid id, uint32_t* indexp)
{ {
if (JSID_IS_INT(id)) { if (JSID_IS_INT(id)) {
@ -31,7 +31,11 @@ IdIsIndex(jsid id, uint32_t* indexp)
if (MOZ_UNLIKELY(!JSID_IS_STRING(id))) if (MOZ_UNLIKELY(!JSID_IS_STRING(id)))
return false; return false;
return js::StringIsArrayIndex(JSID_TO_ATOM(id), indexp); JSAtom* atom = JSID_TO_ATOM(id);
if (atom->length() == 0 || !JS7_ISDEC(atom->latin1OrTwoByteChar(0)))
return false;
return js::StringIsArrayIndex(atom, indexp);
} }
extern JSObject* extern JSObject*

View File

@ -50,6 +50,14 @@ AtomToId(JSAtom* atom)
inline bool inline bool
ValueToIdPure(const Value& v, jsid* id) ValueToIdPure(const Value& v, jsid* id)
{ {
if (v.isString()) {
if (v.toString()->isAtom()) {
*id = AtomToId(&v.toString()->asAtom());
return true;
}
return false;
}
int32_t i; int32_t i;
if (ValueFitsInInt32(v, &i) && INT_FITS_IN_JSID(i)) { if (ValueFitsInInt32(v, &i) && INT_FITS_IN_JSID(i)) {
*id = INT_TO_JSID(i); *id = INT_TO_JSID(i);
@ -61,11 +69,7 @@ ValueToIdPure(const Value& v, jsid* id)
return true; return true;
} }
if (!v.isString() || !v.toString()->isAtom()) return false;
return false;
*id = AtomToId(&v.toString()->asAtom());
return true;
} }
template <AllowGC allowGC> template <AllowGC allowGC>
@ -73,15 +77,23 @@ inline bool
ValueToId(ExclusiveContext* cx, typename MaybeRooted<Value, allowGC>::HandleType v, ValueToId(ExclusiveContext* cx, typename MaybeRooted<Value, allowGC>::HandleType v,
typename MaybeRooted<jsid, allowGC>::MutableHandleType idp) typename MaybeRooted<jsid, allowGC>::MutableHandleType idp)
{ {
int32_t i; if (v.isString()) {
if (ValueFitsInInt32(v, &i) && INT_FITS_IN_JSID(i)) { if (v.toString()->isAtom()) {
idp.set(INT_TO_JSID(i)); idp.set(AtomToId(&v.toString()->asAtom()));
return true; return true;
} }
// fall through
} else {
int32_t i;
if (ValueFitsInInt32(v, &i) && INT_FITS_IN_JSID(i)) {
idp.set(INT_TO_JSID(i));
return true;
}
if (js::IsSymbolOrSymbolWrapper(v)) { if (js::IsSymbolOrSymbolWrapper(v)) {
idp.set(SYMBOL_TO_JSID(js::ToSymbolPrimitive(v))); idp.set(SYMBOL_TO_JSID(js::ToSymbolPrimitive(v)));
return true; return true;
}
} }
JSAtom* atom = ToAtom<allowGC>(cx, v); JSAtom* atom = ToAtom<allowGC>(cx, v);

View File

@ -996,11 +996,12 @@ js::NativeLookupOwnProperty<NoGC>(ExclusiveContext* cx, NativeObject* obj, jsid
/*** [[DefineOwnProperty]] ***********************************************************************/ /*** [[DefineOwnProperty]] ***********************************************************************/
static inline bool static MOZ_ALWAYS_INLINE bool
CallAddPropertyHook(ExclusiveContext* cx, HandleNativeObject obj, HandleShape shape, CallAddPropertyHook(ExclusiveContext* cx, HandleNativeObject obj, HandleShape shape,
HandleValue value) HandleValue value)
{ {
if (JSAddPropertyOp addProperty = obj->getClass()->addProperty) { JSAddPropertyOp addProperty = obj->getClass()->addProperty;
if (MOZ_UNLIKELY(addProperty)) {
if (!cx->shouldBeJSContext()) if (!cx->shouldBeJSContext())
return false; return false;
@ -1013,7 +1014,7 @@ CallAddPropertyHook(ExclusiveContext* cx, HandleNativeObject obj, HandleShape sh
return true; return true;
} }
static inline bool static MOZ_ALWAYS_INLINE bool
CallAddPropertyHookDense(ExclusiveContext* cx, HandleNativeObject obj, uint32_t index, CallAddPropertyHookDense(ExclusiveContext* cx, HandleNativeObject obj, uint32_t index,
HandleValue value) HandleValue value)
{ {
@ -1026,7 +1027,8 @@ CallAddPropertyHookDense(ExclusiveContext* cx, HandleNativeObject obj, uint32_t
return true; return true;
} }
if (JSAddPropertyOp addProperty = obj->getClass()->addProperty) { JSAddPropertyOp addProperty = obj->getClass()->addProperty;
if (MOZ_UNLIKELY(addProperty)) {
if (!cx->shouldBeJSContext()) if (!cx->shouldBeJSContext())
return false; return false;
@ -1042,10 +1044,12 @@ CallAddPropertyHookDense(ExclusiveContext* cx, HandleNativeObject obj, uint32_t
return true; return true;
} }
static bool static MOZ_ALWAYS_INLINE void
UpdateShapeTypeAndValue(ExclusiveContext* cx, NativeObject* obj, Shape* shape, const Value& value) UpdateShapeTypeAndValue(ExclusiveContext* cx, NativeObject* obj, Shape* shape,
jsid id, const Value& value)
{ {
jsid id = shape->propid(); MOZ_ASSERT(id == shape->propid());
if (shape->hasSlot()) { if (shape->hasSlot()) {
obj->setSlotWithType(cx, shape, value, /* overwriting = */ false); obj->setSlotWithType(cx, shape, value, /* overwriting = */ false);
@ -1061,7 +1065,6 @@ UpdateShapeTypeAndValue(ExclusiveContext* cx, NativeObject* obj, Shape* shape, c
MarkTypePropertyNonData(cx, obj, id); MarkTypePropertyNonData(cx, obj, id);
if (!shape->writable()) if (!shape->writable())
MarkTypePropertyNonWritable(cx, obj, id); MarkTypePropertyNonWritable(cx, obj, id);
return true;
} }
static bool static bool
@ -1166,8 +1169,7 @@ AddOrChangeProperty(ExclusiveContext* cx, HandleNativeObject obj, HandleId id,
if (!shape) if (!shape)
return false; return false;
if (!UpdateShapeTypeAndValue(cx, obj, shape, desc.value())) UpdateShapeTypeAndValue(cx, obj, shape, id, desc.value());
return false;
// Clear any existing dense index after adding a sparse indexed property, // Clear any existing dense index after adding a sparse indexed property,
// and investigate converting the object to dense indexes. // and investigate converting the object to dense indexes.
@ -1396,10 +1398,8 @@ js::NativeDefineProperty(ExclusiveContext* cx, HandleNativeObject obj, HandleId
// type for this property that doesn't match the value in the slot. // type for this property that doesn't match the value in the slot.
// Update the type here, even though this DefineProperty call is // Update the type here, even though this DefineProperty call is
// otherwise a no-op. (See bug 1125624 comment 13.) // otherwise a no-op. (See bug 1125624 comment 13.)
if (!IsImplicitDenseOrTypedArrayElement(shape) && desc.hasValue()) { if (!IsImplicitDenseOrTypedArrayElement(shape) && desc.hasValue())
if (!UpdateShapeTypeAndValue(cx, obj, shape, desc.value())) UpdateShapeTypeAndValue(cx, obj, shape, id, desc.value());
return false;
}
return result.succeed(); return result.succeed();
} }

View File

@ -483,15 +483,7 @@ NativeObject::addProperty(ExclusiveContext* cx, HandleNativeObject obj, HandleId
MOZ_ASSERT(!JSID_IS_VOID(id)); MOZ_ASSERT(!JSID_IS_VOID(id));
MOZ_ASSERT(getter != JS_PropertyStub); MOZ_ASSERT(getter != JS_PropertyStub);
MOZ_ASSERT(setter != JS_StrictPropertyStub); MOZ_ASSERT(setter != JS_StrictPropertyStub);
MOZ_ASSERT(obj->nonProxyIsExtensible());
bool extensible;
if (!IsExtensible(cx, obj, &extensible))
return nullptr;
if (!extensible) {
if (cx->isJSContext())
obj->reportNotExtensible(cx->asJSContext());
return nullptr;
}
ShapeTable::Entry* entry = nullptr; ShapeTable::Entry* entry = nullptr;
if (obj->inDictionaryMode()) if (obj->inDictionaryMode())
@ -719,17 +711,7 @@ NativeObject::putProperty(ExclusiveContext* cx, HandleNativeObject obj, HandleId
* You can't add properties to a non-extensible object, but you can change * You can't add properties to a non-extensible object, but you can change
* attributes of properties in such objects. * attributes of properties in such objects.
*/ */
bool extensible; MOZ_ASSERT(obj->nonProxyIsExtensible());
if (!IsExtensible(cx, obj, &extensible))
return nullptr;
if (!extensible) {
if (cx->isJSContext())
obj->reportNotExtensible(cx->asJSContext());
return nullptr;
}
return addPropertyInternal(cx, obj, id, getter, setter, slot, attrs, flags, return addPropertyInternal(cx, obj, id, getter, setter, slot, attrs, flags,
entry, true); entry, true);
} }