Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(829)

Side by Side Diff: src/objects.cc

Issue 1510083003: [cleanup] Introduce HasEnumerableElements() helper (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: added TODO as discussed Created 5 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/objects.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/objects.h" 5 #include "src/objects.h"
6 6
7 #include <cmath> 7 #include <cmath>
8 #include <iomanip> 8 #include <iomanip>
9 #include <sstream> 9 #include <sstream>
10 10
(...skipping 7983 matching lines...) Expand 10 before | Expand all | Expand 10 after
7994 Object); 7994 Object);
7995 if (result->IsPrimitive()) return result; 7995 if (result->IsPrimitive()) return result;
7996 } 7996 }
7997 } 7997 }
7998 THROW_NEW_ERROR(isolate, 7998 THROW_NEW_ERROR(isolate,
7999 NewTypeError(MessageTemplate::kCannotConvertToPrimitive), 7999 NewTypeError(MessageTemplate::kCannotConvertToPrimitive),
8000 Object); 8000 Object);
8001 } 8001 }
8002 8002
8003 8003
8004 // TODO(cbruni/jkummerow): Consider moving this into elements.cc.
8005 bool HasEnumerableElements(JSObject* object) {
8006 if (object->IsJSValue()) {
8007 Object* value = JSValue::cast(object)->value();
8008 if (value->IsString()) {
8009 if (String::cast(value)->length() > 0) return true;
8010 }
8011 }
8012 switch (object->GetElementsKind()) {
8013 case FAST_SMI_ELEMENTS:
8014 case FAST_ELEMENTS:
8015 case FAST_DOUBLE_ELEMENTS: {
8016 int length = object->IsJSArray()
8017 ? Smi::cast(JSArray::cast(object)->length())->value()
8018 : object->elements()->length();
8019 return length > 0;
8020 }
8021 case FAST_HOLEY_SMI_ELEMENTS:
8022 case FAST_HOLEY_ELEMENTS: {
8023 FixedArray* elements = FixedArray::cast(object->elements());
8024 int length = object->IsJSArray()
8025 ? Smi::cast(JSArray::cast(object)->length())->value()
8026 : elements->length();
8027 for (int i = 0; i < length; i++) {
8028 if (!elements->is_the_hole(i)) return true;
8029 }
8030 return false;
8031 }
8032 case FAST_HOLEY_DOUBLE_ELEMENTS: {
8033 FixedDoubleArray* elements = FixedDoubleArray::cast(object->elements());
8034 DCHECK(object->IsJSArray());
8035 int length = Smi::cast(JSArray::cast(object)->length())->value();
8036 for (int i = 0; i < length; i++) {
8037 if (!elements->is_the_hole(i)) return true;
8038 }
8039 return false;
8040 }
8041 #define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
8042 case TYPE##_ELEMENTS:
8043
8044 TYPED_ARRAYS(TYPED_ARRAY_CASE)
8045 #undef TYPED_ARRAY_CASE
8046 {
8047 int length = object->elements()->length();
8048 return length > 0;
8049 }
8050 case DICTIONARY_ELEMENTS: {
8051 SeededNumberDictionary* elements =
8052 SeededNumberDictionary::cast(object->elements());
8053 return elements->NumberOfElementsFilterAttributes(ONLY_ENUMERABLE) > 0;
8054 }
8055 case FAST_SLOPPY_ARGUMENTS_ELEMENTS:
8056 case SLOW_SLOPPY_ARGUMENTS_ELEMENTS:
8057 // We're approximating non-empty arguments objects here.
8058 return true;
8059 }
8060 UNREACHABLE();
8061 return true;
8062 }
8063
8064
8004 // Tests for the fast common case for property enumeration: 8065 // Tests for the fast common case for property enumeration:
8005 // - This object and all prototypes has an enum cache (which means that 8066 // - This object and all prototypes has an enum cache (which means that
8006 // it is no proxy, has no interceptors and needs no access checks). 8067 // it is no proxy, has no interceptors and needs no access checks).
8007 // - This object has no elements. 8068 // - This object has no elements.
8008 // - No prototype has enumerable properties/elements. 8069 // - No prototype has enumerable properties/elements.
8009 bool JSReceiver::IsSimpleEnum() { 8070 bool JSReceiver::IsSimpleEnum() {
8010 for (PrototypeIterator iter(GetIsolate(), this, 8071 for (PrototypeIterator iter(GetIsolate(), this,
8011 PrototypeIterator::START_AT_RECEIVER); 8072 PrototypeIterator::START_AT_RECEIVER);
8012 !iter.IsAtEnd(); iter.Advance()) { 8073 !iter.IsAtEnd(); iter.Advance()) {
8013 if (!iter.GetCurrent()->IsJSObject()) return false; 8074 if (!iter.GetCurrent()->IsJSObject()) return false;
8014 JSObject* current = iter.GetCurrent<JSObject>(); 8075 JSObject* current = iter.GetCurrent<JSObject>();
8015 int enum_length = current->map()->EnumLength(); 8076 int enum_length = current->map()->EnumLength();
8016 if (enum_length == kInvalidEnumCacheSentinel) return false; 8077 if (enum_length == kInvalidEnumCacheSentinel) return false;
8017 if (current->IsAccessCheckNeeded()) return false; 8078 if (current->IsAccessCheckNeeded()) return false;
8018 DCHECK(!current->HasNamedInterceptor()); 8079 DCHECK(!current->HasNamedInterceptor());
8019 DCHECK(!current->HasIndexedInterceptor()); 8080 DCHECK(!current->HasIndexedInterceptor());
8020 if (current->NumberOfEnumElements() > 0) return false; 8081 if (HasEnumerableElements(current)) return false;
8021 if (current != this && enum_length != 0) return false; 8082 if (current != this && enum_length != 0) return false;
8022 } 8083 }
8023 return true; 8084 return true;
8024 } 8085 }
8025 8086
8026 8087
8027 int Map::NumberOfDescribedProperties(DescriptorFlag which, 8088 int Map::NumberOfDescribedProperties(DescriptorFlag which,
8028 PropertyFilter filter) { 8089 PropertyFilter filter) {
8029 int result = 0; 8090 int result = 0;
8030 DescriptorArray* descs = instance_descriptors(); 8091 DescriptorArray* descs = instance_descriptors();
(...skipping 7936 matching lines...) Expand 10 before | Expand all | Expand 10 after
15967 ? static_cast<uint32_t>( 16028 ? static_cast<uint32_t>(
15968 Smi::cast(JSArray::cast(this)->length())->value()) 16029 Smi::cast(JSArray::cast(this)->length())->value())
15969 : static_cast<uint32_t>(FixedArrayBase::cast(elements())->length()); 16030 : static_cast<uint32_t>(FixedArrayBase::cast(elements())->length());
15970 if (length == 0) return 0; 16031 if (length == 0) return 0;
15971 } 16032 }
15972 // Compute the number of enumerable elements. 16033 // Compute the number of enumerable elements.
15973 return GetOwnElementKeys(NULL, filter); 16034 return GetOwnElementKeys(NULL, filter);
15974 } 16035 }
15975 16036
15976 16037
15977 int JSObject::NumberOfEnumElements() {
15978 return NumberOfOwnElements(ONLY_ENUMERABLE);
15979 }
15980
15981
15982 void JSObject::CollectOwnElementKeys(Handle<JSObject> object, 16038 void JSObject::CollectOwnElementKeys(Handle<JSObject> object,
15983 KeyAccumulator* keys, 16039 KeyAccumulator* keys,
15984 PropertyFilter filter) { 16040 PropertyFilter filter) {
15985 if (filter & SKIP_STRINGS) return; 16041 if (filter & SKIP_STRINGS) return;
15986 uint32_t string_keys = 0; 16042 uint32_t string_keys = 0;
15987 16043
15988 // If this is a String wrapper, add the string indices first, 16044 // If this is a String wrapper, add the string indices first,
15989 // as they're guaranteed to precede the elements in numerical order 16045 // as they're guaranteed to precede the elements in numerical order
15990 // and ascending order is required by ECMA-262, 6th, 9.1.12. 16046 // and ascending order is required by ECMA-262, 6th, 9.1.12.
15991 if (object->IsJSValue()) { 16047 if (object->IsJSValue()) {
(...skipping 3181 matching lines...) Expand 10 before | Expand all | Expand 10 after
19173 if (cell->value() != *new_value) { 19229 if (cell->value() != *new_value) {
19174 cell->set_value(*new_value); 19230 cell->set_value(*new_value);
19175 Isolate* isolate = cell->GetIsolate(); 19231 Isolate* isolate = cell->GetIsolate();
19176 cell->dependent_code()->DeoptimizeDependentCodeGroup( 19232 cell->dependent_code()->DeoptimizeDependentCodeGroup(
19177 isolate, DependentCode::kPropertyCellChangedGroup); 19233 isolate, DependentCode::kPropertyCellChangedGroup);
19178 } 19234 }
19179 } 19235 }
19180 19236
19181 } // namespace internal 19237 } // namespace internal
19182 } // namespace v8 19238 } // namespace v8
OLDNEW
« no previous file with comments | « src/objects.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698