From 05ae9effa312763fca1a51620ea937b23b0997d4 Mon Sep 17 00:00:00 2001 From: "sgjesse@chromium.org" Date: Thu, 25 Feb 2010 15:43:27 +0000 Subject: [PATCH] Revert r3952 TBR=ager@chromium.org Review URL: http://codereview.chromium.org/660086 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@3953 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/heap.cc | 18 +--- src/heap.h | 3 - src/objects-debug.cc | 18 ---- src/objects-inl.h | 15 +--- src/objects.cc | 239 +++++++-------------------------------------------- src/objects.h | 102 +--------------------- 6 files changed, 39 insertions(+), 356 deletions(-) diff --git a/src/heap.cc b/src/heap.cc index 31add7a..cfb786a 100644 --- a/src/heap.cc +++ b/src/heap.cc @@ -1206,7 +1206,7 @@ Object* Heap::AllocateMap(InstanceType instance_type, int instance_size) { map->set_inobject_properties(0); map->set_pre_allocated_property_fields(0); map->set_instance_descriptors(empty_descriptor_array()); - map->set_code_cache(undefined_value()); + map->set_code_cache(empty_fixed_array()); map->set_unused_property_fields(0); map->set_bit_field(0); map->set_bit_field2(1 << Map::kIsExtensible); @@ -1221,16 +1221,6 @@ Object* Heap::AllocateMap(InstanceType instance_type, int instance_size) { } -Object* Heap::AllocateCodeCache() { - Object* result = AllocateStruct(CODE_CACHE_TYPE); - if (result->IsFailure()) return result; - CodeCache* code_cache = CodeCache::cast(result); - code_cache->set_default_cache(empty_fixed_array()); - code_cache->set_normal_type_cache(undefined_value()); - return code_cache; -} - - const Heap::StringTypeTable Heap::string_type_table[] = { #define STRING_TYPE_ELEMENT(type, size, name, camel_name) \ {type, size, k##camel_name##MapRootIndex}, @@ -1287,13 +1277,13 @@ bool Heap::CreateInitialMaps() { // Fix the instance_descriptors for the existing maps. meta_map()->set_instance_descriptors(empty_descriptor_array()); - meta_map()->set_code_cache(undefined_value()); + meta_map()->set_code_cache(empty_fixed_array()); fixed_array_map()->set_instance_descriptors(empty_descriptor_array()); - fixed_array_map()->set_code_cache(undefined_value()); + fixed_array_map()->set_code_cache(empty_fixed_array()); oddball_map()->set_instance_descriptors(empty_descriptor_array()); - oddball_map()->set_code_cache(undefined_value()); + oddball_map()->set_code_cache(empty_fixed_array()); // Fix prototype object for existing maps. meta_map()->set_prototype(null_value()); diff --git a/src/heap.h b/src/heap.h index 05fcb5d..9948b96 100644 --- a/src/heap.h +++ b/src/heap.h @@ -345,9 +345,6 @@ class Heap : public AllStatic { // Allocate a map for the specified function static Object* AllocateInitialMap(JSFunction* fun); - // Allocates an empty code cache. - static Object* AllocateCodeCache(); - // Allocates and fully initializes a String. There are two String // encodings: ASCII and two byte. One should choose between the three string // allocation functions based on the encoding of the string buffer used to diff --git a/src/objects-debug.cc b/src/objects-debug.cc index 492b492..9415bc1 100644 --- a/src/objects-debug.cc +++ b/src/objects-debug.cc @@ -644,24 +644,6 @@ void Map::MapVerify() { } -void CodeCache::CodeCachePrint() { - HeapObject::PrintHeader("CodeCache"); - PrintF("\n - default_cache: "); - default_cache()->ShortPrint(); - PrintF("\n - normal_type_cache: "); - normal_type_cache()->ShortPrint(); -} - - -void CodeCache::CodeCacheVerify() { - VerifyHeapPointer(default_cache()); - VerifyHeapPointer(normal_type_cache()); - ASSERT(default_cache()->IsFixedArray()); - ASSERT(normal_type_cache()->IsUndefined() - || normal_type_cache()->IsCodeCacheHashTable()); -} - - void FixedArray::FixedArrayPrint() { HeapObject::PrintHeader("FixedArray"); PrintF(" - length: %d", length()); diff --git a/src/objects-inl.h b/src/objects-inl.h index 01b80f9..274fc76 100644 --- a/src/objects-inl.h +++ b/src/objects-inl.h @@ -564,11 +564,6 @@ bool Object::IsCompilationCacheTable() { } -bool Object::IsCodeCacheHashTable() { - return IsHashTable(); -} - - bool Object::IsMapCache() { return IsHashTable(); } @@ -1568,7 +1563,6 @@ CAST_ACCESSOR(FixedArray) CAST_ACCESSOR(DescriptorArray) CAST_ACCESSOR(SymbolTable) CAST_ACCESSOR(CompilationCacheTable) -CAST_ACCESSOR(CodeCacheHashTable) CAST_ACCESSOR(MapCache) CAST_ACCESSOR(String) CAST_ACCESSOR(SeqString) @@ -2261,7 +2255,7 @@ void Map::set_prototype(Object* value, WriteBarrierMode mode) { ACCESSORS(Map, instance_descriptors, DescriptorArray, kInstanceDescriptorsOffset) -ACCESSORS(Map, code_cache, Object, kCodeCacheOffset) +ACCESSORS(Map, code_cache, FixedArray, kCodeCacheOffset) ACCESSORS(Map, constructor, Object, kConstructorOffset) ACCESSORS(JSFunction, shared, SharedFunctionInfo, kSharedFunctionInfoOffset) @@ -2399,9 +2393,6 @@ INT_ACCESSORS(SharedFunctionInfo, this_property_assignments_count, kThisPropertyAssignmentsCountOffset) -ACCESSORS(CodeCache, default_cache, FixedArray, kDefaultCacheOffset) -ACCESSORS(CodeCache, normal_type_cache, Object, kNormalTypeCacheOffset) - bool Script::HasValidSource() { Object* src = this->source(); if (!src->IsString()) return true; @@ -3002,8 +2993,8 @@ void Map::ClearCodeCache() { // No write barrier is needed since empty_fixed_array is not in new space. // Please note this function is used during marking: // - MarkCompactCollector::MarkUnmarkedObject - ASSERT(!Heap::InNewSpace(Heap::undefined_value())); - WRITE_FIELD(this, kCodeCacheOffset, Heap::undefined_value()); + ASSERT(!Heap::InNewSpace(Heap::raw_unchecked_empty_fixed_array())); + WRITE_FIELD(this, kCodeCacheOffset, Heap::raw_unchecked_empty_fixed_array()); } diff --git a/src/objects.cc b/src/objects.cc index 13fbd69..53423af 100644 --- a/src/objects.cc +++ b/src/objects.cc @@ -3033,79 +3033,19 @@ Object* Map::CopyDropTransitions() { Object* Map::UpdateCodeCache(String* name, Code* code) { - // Allocate the code cache if not present. - if (code_cache()->IsUndefined()) { - Object* result = Heap::AllocateCodeCache(); - if (result->IsFailure()) return result; - set_code_cache(result); - } - - // Update the code cache. - return CodeCache::cast(code_cache())->Update(name, code); -} - - -Object* Map::FindInCodeCache(String* name, Code::Flags flags) { - // Do a lookup if a code cache exists. - if (!code_cache()->IsUndefined()) { - return CodeCache::cast(code_cache())->Lookup(name, flags); - } else { - return Heap::undefined_value(); - } -} - - -int Map::IndexInCodeCache(Code* code) { - // Get the internal index if a code cache exists. - if (!code_cache()->IsUndefined()) { - return CodeCache::cast(code_cache())->GetIndex(code); - } - return -1; -} - - -void Map::RemoveFromCodeCache(int index) { - // No GC is supposed to happen between a call to IndexInCodeCache and - // RemoveFromCodeCache so the code cache must be there. - ASSERT(!code_cache()->IsUndefined()); - return CodeCache::cast(code_cache())->RemoveByIndex(index); -} - - -Object* CodeCache::Update(String* name, Code* code) { ASSERT(code->ic_state() == MONOMORPHIC); + FixedArray* cache = code_cache(); - // The number of monomorphic stubs for normal load/store/call IC's can grow to - // a large number and therefore they need to go into a hash table. They are - // used to load global properties from cells. - if (code->type() == NORMAL) { - // Make sure that a hash table is allocated for the normal load code cache. - if (normal_type_cache()->IsUndefined()) { - Object* result = - CodeCacheHashTable::Allocate(CodeCacheHashTable::kInitialSize); - if (result->IsFailure()) return result; - set_normal_type_cache(result); - } - return UpdateNormalTypeCache(name, code); - } else { - ASSERT(default_cache()->IsFixedArray()); - return UpdateDefaultCache(name, code); - } -} - - -Object* CodeCache::UpdateDefaultCache(String* name, Code* code) { - // When updating the default code cache we disregard the type encoded in the + // When updating the code cache we disregard the type encoded in the // flags. This allows call constant stubs to overwrite call field // stubs, etc. Code::Flags flags = Code::RemoveTypeFromFlags(code->flags()); // First check whether we can update existing code cache without // extending it. - FixedArray* cache = default_cache(); int length = cache->length(); int deleted_index = -1; - for (int i = 0; i < length; i += kCodeCacheEntrySize) { + for (int i = 0; i < length; i += 2) { Object* key = cache->get(i); if (key->IsNull()) { if (deleted_index < 0) deleted_index = i; @@ -3113,15 +3053,14 @@ Object* CodeCache::UpdateDefaultCache(String* name, Code* code) { } if (key->IsUndefined()) { if (deleted_index >= 0) i = deleted_index; - cache->set(i + kCodeCacheEntryNameOffset, name); - cache->set(i + kCodeCacheEntryCodeOffset, code); + cache->set(i + 0, name); + cache->set(i + 1, code); return this; } if (name->Equals(String::cast(key))) { - Code::Flags found = - Code::cast(cache->get(i + kCodeCacheEntryCodeOffset))->flags(); + Code::Flags found = Code::cast(cache->get(i + 1))->flags(); if (Code::RemoveTypeFromFlags(found) == flags) { - cache->set(i + kCodeCacheEntryCodeOffset, code); + cache->set(i + 1, code); return this; } } @@ -3130,180 +3069,61 @@ Object* CodeCache::UpdateDefaultCache(String* name, Code* code) { // Reached the end of the code cache. If there were deleted // elements, reuse the space for the first of them. if (deleted_index >= 0) { - cache->set(deleted_index + kCodeCacheEntryNameOffset, name); - cache->set(deleted_index + kCodeCacheEntryCodeOffset, code); + cache->set(deleted_index + 0, name); + cache->set(deleted_index + 1, code); return this; } - // Extend the code cache with some new entries (at least one). Must be a - // multiple of the entry size. - int new_length = length + ((length >> 1)) + kCodeCacheEntrySize; - new_length = new_length - new_length % kCodeCacheEntrySize; - ASSERT((new_length % kCodeCacheEntrySize) == 0); + // Extend the code cache with some new entries (at least one). + int new_length = length + ((length >> 1) & ~1) + 2; + ASSERT((new_length & 1) == 0); // must be a multiple of two Object* result = cache->CopySize(new_length); if (result->IsFailure()) return result; // Add the (name, code) pair to the new cache. cache = FixedArray::cast(result); - cache->set(length + kCodeCacheEntryNameOffset, name); - cache->set(length + kCodeCacheEntryCodeOffset, code); - set_default_cache(cache); + cache->set(length + 0, name); + cache->set(length + 1, code); + set_code_cache(cache); return this; } -Object* CodeCache::UpdateNormalTypeCache(String* name, Code* code) { - // Adding a new entry can cause a new cache to be allocated. - CodeCacheHashTable* cache = CodeCacheHashTable::cast(normal_type_cache()); - Object* new_cache = cache->Put(name, code); - if (new_cache->IsFailure()) return new_cache; - set_normal_type_cache(new_cache); - return this; -} - - -Object* CodeCache::Lookup(String* name, Code::Flags flags) { - if (Code::ExtractTypeFromFlags(flags) == NORMAL) { - return LookupNormalTypeCache(name, flags); - } else { - return LookupDefaultCache(name, flags); - } -} - - -Object* CodeCache::LookupDefaultCache(String* name, Code::Flags flags) { - FixedArray* cache = default_cache(); +Object* Map::FindInCodeCache(String* name, Code::Flags flags) { + FixedArray* cache = code_cache(); int length = cache->length(); - for (int i = 0; i < length; i += kCodeCacheEntrySize) { - Object* key = cache->get(i + kCodeCacheEntryNameOffset); + for (int i = 0; i < length; i += 2) { + Object* key = cache->get(i); // Skip deleted elements. if (key->IsNull()) continue; if (key->IsUndefined()) return key; if (name->Equals(String::cast(key))) { - Code* code = Code::cast(cache->get(i + kCodeCacheEntryCodeOffset)); - if (code->flags() == flags) { - return code; - } + Code* code = Code::cast(cache->get(i + 1)); + if (code->flags() == flags) return code; } } return Heap::undefined_value(); } -Object* CodeCache::LookupNormalTypeCache(String* name, Code::Flags flags) { - if (!normal_type_cache()->IsUndefined()) { - CodeCacheHashTable* cache = CodeCacheHashTable::cast(normal_type_cache()); - return cache->Lookup(name, flags); - } else { - return Heap::undefined_value(); - } -} - - -int CodeCache::GetIndex(Code* code) { - // This is not used for normal load/store/call IC's. - ASSERT(code->type() != NORMAL); - - FixedArray* array = default_cache(); +int Map::IndexInCodeCache(Code* code) { + FixedArray* array = code_cache(); int len = array->length(); - for (int i = 0; i < len; i += kCodeCacheEntrySize) { - if (array->get(i + kCodeCacheEntryCodeOffset) == code) return i + 1; + for (int i = 0; i < len; i += 2) { + if (array->get(i + 1) == code) return i + 1; } return -1; } -void CodeCache::RemoveByIndex(int index) { - FixedArray* array = default_cache(); +void Map::RemoveFromCodeCache(int index) { + FixedArray* array = code_cache(); ASSERT(array->length() >= index && array->get(index)->IsCode()); // Use null instead of undefined for deleted elements to distinguish // deleted elements from unused elements. This distinction is used // when looking up in the cache and when updating the cache. - ASSERT_EQ(1, kCodeCacheEntryCodeOffset - kCodeCacheEntryNameOffset); - array->set_null(index - 1); // Name. - array->set_null(index); // Code. -} - - -// The key in the code cache hash table consists of the property name and the -// code object. The actual match is on the name and the code flags. If a key -// is created using the flags and not a code object it can only be used for -// lookup not to create a new entry. -class CodeCacheHashTableKey : public HashTableKey { - public: - CodeCacheHashTableKey(String* name, Code::Flags flags) - : name_(name), flags_(flags), code_(NULL) { } - - CodeCacheHashTableKey(String* name, Code* code) - : name_(name), - flags_(code->flags()), - code_(code) { } - - - bool IsMatch(Object* other) { - if (!other->IsFixedArray()) return false; - FixedArray* pair = FixedArray::cast(other); - String* name = String::cast(pair->get(0)); - Code::Flags flags = Code::cast(pair->get(1))->flags(); - if (flags != flags_) { - return false; - } - return name_->Equals(name); - } - - static uint32_t NameFlagsHashHelper(String* name, Code::Flags flags) { - return name->Hash() ^ flags; - } - - uint32_t Hash() { return NameFlagsHashHelper(name_, flags_); } - - uint32_t HashForObject(Object* obj) { - FixedArray* pair = FixedArray::cast(obj); - String* name = String::cast(pair->get(0)); - Code* code = Code::cast(pair->get(1)); - return NameFlagsHashHelper(name, code->flags()); - } - - Object* AsObject() { - ASSERT(code_ != NULL); - Object* obj = Heap::AllocateFixedArray(2); - if (obj->IsFailure()) return obj; - FixedArray* pair = FixedArray::cast(obj); - pair->set(0, name_); - pair->set(1, code_); - return pair; - } - - private: - String* name_; - Code::Flags flags_; - Code* code_; -}; - - -Object* CodeCacheHashTable::Lookup(String* name, Code::Flags flags) { - CodeCacheHashTableKey key(name, flags); - int entry = FindEntry(&key); - if (entry == kNotFound) return Heap::undefined_value(); - return get(EntryToIndex(entry) + 1); -} - - -Object* CodeCacheHashTable::Put(String* name, Code* code) { - CodeCacheHashTableKey key(name, code); - Object* obj = EnsureCapacity(1, &key); - - // Don't use this, as the table might have grown. - CodeCacheHashTable* cache = reinterpret_cast(obj); - - int entry = cache->FindInsertionEntry(key.Hash()); - Object* k = key.AsObject(); - if (k->IsFailure()) return k; - - cache->set(EntryToIndex(entry), k); - cache->set(EntryToIndex(entry) + 1, code); - cache->ElementAdded(); - return cache; + array->set_null(index - 1); // key + array->set_null(index); // code } @@ -7161,6 +6981,7 @@ Object* HashTable::EnsureCapacity(int n, Key key) { } + template uint32_t HashTable::FindInsertionEntry(uint32_t hash) { uint32_t capacity = Capacity(); diff --git a/src/objects.h b/src/objects.h index 60dad65..9d4cfd6 100644 --- a/src/objects.h +++ b/src/objects.h @@ -72,7 +72,6 @@ // - Dictionary // - SymbolTable // - CompilationCacheTable -// - CodeCacheHashTable // - MapCache // - Context // - GlobalContext @@ -103,7 +102,6 @@ // - TypeSwitchInfo // - DebugInfo // - BreakPointInfo -// - CodeCache // // Formats of Object*: // Smi: [31 bit signed int] 0 @@ -271,7 +269,6 @@ enum PropertyNormalizationMode { V(SIGNATURE_INFO_TYPE) \ V(TYPE_SWITCH_INFO_TYPE) \ V(SCRIPT_TYPE) \ - V(CODE_CACHE_TYPE) \ \ V(JS_VALUE_TYPE) \ V(JS_OBJECT_TYPE) \ @@ -367,8 +364,7 @@ enum PropertyNormalizationMode { V(OBJECT_TEMPLATE_INFO, ObjectTemplateInfo, object_template_info) \ V(SIGNATURE_INFO, SignatureInfo, signature_info) \ V(TYPE_SWITCH_INFO, TypeSwitchInfo, type_switch_info) \ - V(SCRIPT, Script, script) \ - V(CODE_CACHE, CodeCache, code_cache) + V(SCRIPT, Script, script) #ifdef ENABLE_DEBUGGER_SUPPORT #define STRUCT_LIST_DEBUGGER(V) \ @@ -472,7 +468,6 @@ enum InstanceType { SIGNATURE_INFO_TYPE, TYPE_SWITCH_INFO_TYPE, SCRIPT_TYPE, - CODE_CACHE_TYPE, #ifdef ENABLE_DEBUGGER_SUPPORT DEBUG_INFO_TYPE, BREAK_POINT_INFO_TYPE, @@ -606,7 +601,6 @@ class Object BASE_EMBEDDED { inline bool IsDictionary(); inline bool IsSymbolTable(); inline bool IsCompilationCacheTable(); - inline bool IsCodeCacheHashTable(); inline bool IsMapCache(); inline bool IsPrimitive(); inline bool IsGlobalObject(); @@ -2928,7 +2922,7 @@ class Map: public HeapObject { DECL_ACCESSORS(instance_descriptors, DescriptorArray) // [stub cache]: contains stubs compiled for this map. - DECL_ACCESSORS(code_cache, Object) + DECL_ACCESSORS(code_cache, FixedArray) Object* CopyDropDescriptors(); @@ -3032,11 +3026,6 @@ class Map: public HeapObject { static const int kNeedsLoading = 0; static const int kIsExtensible = 1; - // Layout of the default cache. It holds alternating name and code objects. - static const int kCodeCacheEntrySize = 2; - static const int kCodeCacheEntryNameOffset = 0; - static const int kCodeCacheEntryCodeOffset = 1; - private: DISALLOW_IMPLICIT_CONSTRUCTORS(Map); }; @@ -3722,93 +3711,6 @@ class CompilationCacheTable: public HashTableIsMatch(value); - } - - static inline uint32_t Hash(HashTableKey* key) { - return key->Hash(); - } - - static inline uint32_t HashForObject(HashTableKey* key, Object* object) { - return key->HashForObject(object); - } - - static Object* AsObject(HashTableKey* key) { - return key->AsObject(); - } - - static const int kPrefixSize = 0; - static const int kEntrySize = 2; -}; - - -class CodeCacheHashTable: public HashTable { - public: - Object* Lookup(String* name, Code::Flags flags); - Object* Put(String* name, Code* code); - - static inline CodeCacheHashTable* cast(Object* obj); - - // Initial size of the fixed array backing the hash table. - static const int kInitialSize = 64; - - private: - DISALLOW_IMPLICIT_CONSTRUCTORS(CodeCacheHashTable); -}; - - enum AllowNullsFlag {ALLOW_NULLS, DISALLOW_NULLS}; enum RobustnessFlag {ROBUST_STRING_TRAVERSAL, FAST_STRING_TRAVERSAL}; -- 2.7.4