| Index: src/runtime.cc
|
| diff --git a/src/runtime.cc b/src/runtime.cc
|
| index 1f52a225de9ceee3a4cefc1d0e1d1e8b785da2e4..74dfae89880ffe6a3ef274811d4f0d0d14084e02 100644
|
| --- a/src/runtime.cc
|
| +++ b/src/runtime.cc
|
| @@ -422,6 +422,9 @@ static Handle<Object> CreateObjectLiteralBoilerplate(
|
| }
|
|
|
|
|
| +static const int kSmiOnlyLiteralMinimumLength = 1024;
|
| +
|
| +
|
| static Handle<Object> CreateArrayLiteralBoilerplate(
|
| Isolate* isolate,
|
| Handle<FixedArray> literals,
|
| @@ -431,6 +434,13 @@ static Handle<Object> CreateArrayLiteralBoilerplate(
|
| JSFunction::GlobalContextFromLiterals(*literals)->array_function());
|
| Handle<Object> object = isolate->factory()->NewJSObject(constructor);
|
|
|
| + if (elements->length() > kSmiOnlyLiteralMinimumLength) {
|
| + Handle<Map> smi_array_map = isolate->factory()->GetElementsTransitionMap(
|
| + Handle<JSObject>::cast(object),
|
| + FAST_SMI_ONLY_ELEMENTS);
|
| + HeapObject::cast(*object)->set_map(*smi_array_map);
|
| + }
|
| +
|
| const bool is_cow =
|
| (elements->map() == isolate->heap()->fixed_cow_array_map());
|
| Handle<FixedArray> copied_elements =
|
| @@ -440,21 +450,18 @@ static Handle<Object> CreateArrayLiteralBoilerplate(
|
| bool has_non_smi = false;
|
| if (is_cow) {
|
| // Copy-on-write arrays must be shallow (and simple).
|
| - if (FLAG_smi_only_arrays) {
|
| - for (int i = 0; i < content->length(); i++) {
|
| - Object* current = content->get(i);
|
| - ASSERT(!current->IsFixedArray());
|
| - if (!current->IsSmi() && !current->IsTheHole()) {
|
| - has_non_smi = true;
|
| - }
|
| + for (int i = 0; i < content->length(); i++) {
|
| + Object* current = content->get(i);
|
| + ASSERT(!current->IsFixedArray());
|
| + if (!current->IsSmi() && !current->IsTheHole()) {
|
| + has_non_smi = true;
|
| }
|
| - } else {
|
| + }
|
| #if DEBUG
|
| - for (int i = 0; i < content->length(); i++) {
|
| - ASSERT(!content->get(i)->IsFixedArray());
|
| - }
|
| -#endif
|
| + for (int i = 0; i < content->length(); i++) {
|
| + ASSERT(!content->get(i)->IsFixedArray());
|
| }
|
| +#endif
|
| } else {
|
| for (int i = 0; i < content->length(); i++) {
|
| Object* current = content->get(i);
|
| @@ -479,10 +486,8 @@ static Handle<Object> CreateArrayLiteralBoilerplate(
|
| Handle<JSArray> js_object(Handle<JSArray>::cast(object));
|
| isolate->factory()->SetContent(js_object, content);
|
|
|
| - if (FLAG_smi_only_arrays) {
|
| - if (has_non_smi && js_object->HasFastSmiOnlyElements()) {
|
| - isolate->factory()->EnsureCanContainNonSmiElements(js_object);
|
| - }
|
| + if (has_non_smi && js_object->HasFastSmiOnlyElements()) {
|
| + isolate->factory()->EnsureCanContainNonSmiElements(js_object);
|
| }
|
|
|
| return object;
|
| @@ -1661,7 +1666,7 @@ RUNTIME_FUNCTION(MaybeObject*,
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_NonSmiElementStored) {
|
| ASSERT(args.length() == 1);
|
| CONVERT_ARG_CHECKED(JSObject, object, 0);
|
| - if (FLAG_smi_only_arrays && object->HasFastSmiOnlyElements()) {
|
| + if (object->HasFastSmiOnlyElements()) {
|
| MaybeObject* maybe_map = object->GetElementsTransitionMap(FAST_ELEMENTS);
|
| Map* map;
|
| if (!maybe_map->To<Map>(&map)) return maybe_map;
|
| @@ -9748,6 +9753,33 @@ static bool IterateElements(Isolate* isolate,
|
| }
|
| break;
|
| }
|
| + case FAST_DOUBLE_ELEMENTS: {
|
| + // Run through the elements FixedArray and use HasElement and GetElement
|
| + // to check the prototype for missing elements.
|
| + Handle<FixedDoubleArray> elements(
|
| + FixedDoubleArray::cast(receiver->elements()));
|
| + int fast_length = static_cast<int>(length);
|
| + ASSERT(fast_length <= elements->length());
|
| + for (int j = 0; j < fast_length; j++) {
|
| + HandleScope loop_scope(isolate);
|
| + if (!elements->is_the_hole(j)) {
|
| + MaybeObject* maybe_double_object = elements->get(j);
|
| + Object* double_object;
|
| + if (!maybe_double_object->ToObject(&double_object)) {
|
| + return false;
|
| + }
|
| + Handle<Object> element_value(double_object, isolate);
|
| + visitor->visit(j, element_value);
|
| + } else if (receiver->HasElement(j)) {
|
| + // Call GetElement on receiver, not its prototype, or getters won't
|
| + // have the correct receiver.
|
| + Handle<Object> element_value = GetElement(receiver, j);
|
| + if (element_value.is_null()) return false;
|
| + visitor->visit(j, element_value);
|
| + }
|
| + }
|
| + break;
|
| + }
|
| case DICTIONARY_ELEMENTS: {
|
| Handle<NumberDictionary> dict(receiver->element_dictionary());
|
| List<uint32_t> indices(dict->Capacity() / 2);
|
|
|