Fix Spread (#421)

* spread is allocated on an array object in advance to know the entire length of array when it is used in array initializer
* spread array is fixed fast mode array which means that Array.prototype could not affect any array operation of spread array
* pass v8 TCs

Signed-off-by: HyukWoo Park <hyukwoo.park@samsung.com>
This commit is contained in:
Hyukwoo Park 2019-09-10 16:59:57 +09:00 committed by Boram Bae
commit c2352d1722
16 changed files with 379 additions and 338 deletions

View file

@ -28,14 +28,14 @@ namespace Escargot {
size_t g_arrayObjectTag;
ArrayObject::ArrayObject(ExecutionState& state, bool hasSpreadElement)
ArrayObject::ArrayObject(ExecutionState& state)
: Object(state, ESCARGOT_OBJECT_BUILTIN_PROPERTY_NUMBER + 1, true)
{
m_structure = state.context()->defaultStructureForArrayObject();
m_values[ESCARGOT_OBJECT_BUILTIN_PROPERTY_NUMBER] = Value(0);
Object::setPrototype(state, state.context()->globalObject()->arrayPrototype());
if (UNLIKELY(state.context()->vmInstance()->didSomePrototypeObjectDefineIndexedProperty() || hasSpreadElement)) {
if (UNLIKELY(state.context()->vmInstance()->didSomePrototypeObjectDefineIndexedProperty())) {
ensureObjectRareData()->m_isFastModeArrayObject = false;
}
}
@ -55,6 +55,18 @@ ArrayObject::ArrayObject(ExecutionState& state, double length)
(ObjectPropertyDescriptor::PresentAttribute)(ObjectPropertyDescriptor::WritablePresent | ObjectPropertyDescriptor::NonEnumerablePresent | ObjectPropertyDescriptor::NonConfigurablePresent)));
}
ArrayObject* ArrayObject::createSpreadArray(ExecutionState& state)
{
// SpreadArray is a Fixed Array which has no __proto__ property
// Array.Prototype should not affect any SpreadArray operation
ArrayObject* spreadArray = new ArrayObject(state);
spreadArray->ensureObjectRareData()->m_isFastModeArrayObject = true;
spreadArray->ensureObjectRareData()->m_isSpreadArrayObject = true;
spreadArray->ensureObjectRareData()->m_prototype = nullptr;
return spreadArray;
}
ObjectHasPropertyResult ArrayObject::hasProperty(ExecutionState& state, const ObjectPropertyName& P) ESCARGOT_OBJECT_SUBCLASS_MUST_REDEFINE
{
ObjectGetResult v = getFastModeValue(state, P);