| Index: src/runtime.cc
|
| diff --git a/src/runtime.cc b/src/runtime.cc
|
| index 67d7c64d1dff1b5f31aaa6069e1e3d5b21fcd1fd..017890580ed67f8716cc030ebe136225b7505110 100644
|
| --- a/src/runtime.cc
|
| +++ b/src/runtime.cc
|
| @@ -428,6 +428,23 @@ static Handle<Object> CreateObjectLiteralBoilerplate(
|
| }
|
|
|
|
|
| +MaybeObject* TransitionElements(Handle<Object> object,
|
| + ElementsKind to_kind,
|
| + Isolate* isolate) {
|
| + HandleScope scope(isolate);
|
| + if (!object->IsJSObject()) return isolate->ThrowIllegalOperation();
|
| + ElementsKind from_kind =
|
| + Handle<JSObject>::cast(object)->map()->elements_kind();
|
| + if (Map::IsValidElementsTransition(from_kind, to_kind)) {
|
| + Handle<Object> result = JSObject::TransitionElementsKind(
|
| + Handle<JSObject>::cast(object), to_kind);
|
| + if (result.is_null()) return isolate->ThrowIllegalOperation();
|
| + return *result;
|
| + }
|
| + return isolate->ThrowIllegalOperation();
|
| +}
|
| +
|
| +
|
| static const int kSmiOnlyLiteralMinimumLength = 1024;
|
|
|
|
|
| @@ -446,25 +463,13 @@ Handle<Object> Runtime::CreateArrayLiteralBoilerplate(
|
| Handle<FixedArrayBase> constant_elements_values(
|
| FixedArrayBase::cast(elements->get(1)));
|
|
|
| - ASSERT(FLAG_smi_only_arrays || constant_elements_kind == FAST_ELEMENTS ||
|
| - constant_elements_kind == FAST_SMI_ONLY_ELEMENTS);
|
| - bool allow_literal_kind_transition = FLAG_smi_only_arrays &&
|
| - constant_elements_kind > object->GetElementsKind();
|
| -
|
| - if (!FLAG_smi_only_arrays &&
|
| - constant_elements_values->length() > kSmiOnlyLiteralMinimumLength &&
|
| - constant_elements_kind != object->GetElementsKind()) {
|
| - allow_literal_kind_transition = true;
|
| - }
|
| -
|
| - // If the ElementsKind of the constant values of the array literal are less
|
| - // specific than the ElementsKind of the boilerplate array object, change the
|
| - // boilerplate array object's map to reflect that kind.
|
| - if (allow_literal_kind_transition) {
|
| - Handle<Map> transitioned_array_map =
|
| - isolate->factory()->GetElementsTransitionMap(object,
|
| - constant_elements_kind);
|
| - object->set_map(*transitioned_array_map);
|
| + Context* global_context = isolate->context()->global_context();
|
| + if (constant_elements_kind == FAST_SMI_ONLY_ELEMENTS) {
|
| + object->set_map(Map::cast(global_context->smi_js_array_map()));
|
| + } else if (constant_elements_kind == FAST_DOUBLE_ELEMENTS) {
|
| + object->set_map(Map::cast(global_context->double_js_array_map()));
|
| + } else {
|
| + object->set_map(Map::cast(global_context->object_js_array_map()));
|
| }
|
|
|
| Handle<FixedArrayBase> copied_elements_values;
|
| @@ -509,6 +514,16 @@ Handle<Object> Runtime::CreateArrayLiteralBoilerplate(
|
| }
|
| object->set_elements(*copied_elements_values);
|
| object->set_length(Smi::FromInt(copied_elements_values->length()));
|
| +
|
| + // Ensure that the boilerplate object has FAST_ELEMENTS, unless the flag is
|
| + // on or the object is larger than the threshold.
|
| + if (!FLAG_smi_only_arrays &&
|
| + constant_elements_values->length() < kSmiOnlyLiteralMinimumLength) {
|
| + if (object->GetElementsKind() != FAST_ELEMENTS) {
|
| + CHECK(!TransitionElements(object, FAST_ELEMENTS, isolate)->IsFailure());
|
| + }
|
| + }
|
| +
|
| return object;
|
| }
|
|
|
| @@ -4202,23 +4217,6 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetProperty) {
|
| }
|
|
|
|
|
| -MaybeObject* TransitionElements(Handle<Object> object,
|
| - ElementsKind to_kind,
|
| - Isolate* isolate) {
|
| - HandleScope scope(isolate);
|
| - if (!object->IsJSObject()) return isolate->ThrowIllegalOperation();
|
| - ElementsKind from_kind =
|
| - Handle<JSObject>::cast(object)->map()->elements_kind();
|
| - if (Map::IsValidElementsTransition(from_kind, to_kind)) {
|
| - Handle<Object> result = JSObject::TransitionElementsKind(
|
| - Handle<JSObject>::cast(object), to_kind);
|
| - if (result.is_null()) return isolate->ThrowIllegalOperation();
|
| - return *result;
|
| - }
|
| - return isolate->ThrowIllegalOperation();
|
| -}
|
| -
|
| -
|
| // KeyedStringGetProperty is called from KeyedLoadIC::GenerateGeneric.
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_KeyedGetProperty) {
|
| NoHandleAllocation ha;
|
| @@ -10231,7 +10229,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_MoveArrayContents) {
|
| } else {
|
| elements_kind = DICTIONARY_ELEMENTS;
|
| }
|
| - maybe_new_map = to->GetElementsTransitionMap(elements_kind);
|
| + maybe_new_map = to->GetElementsTransitionMap(isolate, elements_kind);
|
| Object* new_map;
|
| if (!maybe_new_map->ToObject(&new_map)) return maybe_new_map;
|
| to->set_map(Map::cast(new_map));
|
|
|