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

Side by Side Diff: src/objects.cc

Issue 28027: Speed up access to global variables from eval scopes. Traverse the... (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 11 years, 10 months 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 | Annotate | Revision Log
OLDNEW
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. 1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 5832 matching lines...) Expand 10 before | Expand all | Expand 10 after
5843 return counter; 5843 return counter;
5844 } 5844 }
5845 5845
5846 5846
5847 int JSObject::GetEnumElementKeys(FixedArray* storage) { 5847 int JSObject::GetEnumElementKeys(FixedArray* storage) {
5848 return GetLocalElementKeys(storage, 5848 return GetLocalElementKeys(storage,
5849 static_cast<PropertyAttributes>(DONT_ENUM)); 5849 static_cast<PropertyAttributes>(DONT_ENUM));
5850 } 5850 }
5851 5851
5852 5852
5853 // Thomas Wang, Integer Hash Functions.
5854 // http://www.concentric.net/~Ttwang/tech/inthash.htm
5855 static uint32_t ComputeIntegerHash(uint32_t key) {
5856 uint32_t hash = key;
5857 hash = ~hash + (hash << 15); // hash = (hash << 15) - hash - 1;
5858 hash = hash ^ (hash >> 12);
5859 hash = hash + (hash << 2);
5860 hash = hash ^ (hash >> 4);
5861 hash = hash * 2057; // hash = (hash + (hash << 3)) + (hash << 11);
5862 hash = hash ^ (hash >> 16);
5863 return hash;
5864 }
5865
5866
5853 // The NumberKey uses carries the uint32_t as key. 5867 // The NumberKey uses carries the uint32_t as key.
5854 // This avoids allocation in HasProperty. 5868 // This avoids allocation in HasProperty.
5855 class NumberKey : public HashTableKey { 5869 class NumberKey : public HashTableKey {
5856 public: 5870 public:
5857 explicit NumberKey(uint32_t number) : number_(number) { } 5871 explicit NumberKey(uint32_t number) : number_(number) { }
5858 5872
5859 private: 5873 private:
5860 bool IsMatch(Object* number) { 5874 bool IsMatch(Object* number) {
5861 return number_ == ToUint32(number); 5875 return number_ == ToUint32(number);
5862 } 5876 }
5863 5877
5864 // Thomas Wang, Integer Hash Functions. 5878 uint32_t Hash() { return ComputeIntegerHash(number_); }
5865 // http://www.concentric.net/~Ttwang/tech/inthash.htm
5866 static uint32_t ComputeHash(uint32_t key) {
5867 uint32_t hash = key;
5868 hash = ~hash + (hash << 15); // hash = (hash << 15) - hash - 1;
5869 hash = hash ^ (hash >> 12);
5870 hash = hash + (hash << 2);
5871 hash = hash ^ (hash >> 4);
5872 hash = hash * 2057; // hash = (hash + (hash << 3)) + (hash << 11);
5873 hash = hash ^ (hash >> 16);
5874 return hash;
5875 }
5876
5877 uint32_t Hash() { return ComputeHash(number_); }
5878 5879
5879 HashFunction GetHashFunction() { return NumberHash; } 5880 HashFunction GetHashFunction() { return NumberHash; }
5880 5881
5881 Object* GetObject() { 5882 Object* GetObject() {
5882 return Heap::NumberFromDouble(number_); 5883 return Heap::NumberFromDouble(number_);
5883 } 5884 }
5884 5885
5885 static uint32_t NumberHash(Object* obj) { 5886 static uint32_t NumberHash(Object* obj) {
5886 return ComputeHash(ToUint32(obj)); 5887 return ComputeIntegerHash(ToUint32(obj));
5887 } 5888 }
5888 5889
5889 static uint32_t ToUint32(Object* obj) { 5890 static uint32_t ToUint32(Object* obj) {
5890 ASSERT(obj->IsNumber()); 5891 ASSERT(obj->IsNumber());
5891 return static_cast<uint32_t>(obj->Number()); 5892 return static_cast<uint32_t>(obj->Number());
5892 } 5893 }
5893 5894
5894 bool IsStringKey() { return false; } 5895 bool IsStringKey() { return false; }
5895 5896
5896 uint32_t number_; 5897 uint32_t number_;
(...skipping 17 matching lines...) Expand all
5914 5915
5915 static uint32_t StringHash(Object* obj) { 5916 static uint32_t StringHash(Object* obj) {
5916 return String::cast(obj)->Hash(); 5917 return String::cast(obj)->Hash();
5917 } 5918 }
5918 5919
5919 bool IsStringKey() { return true; } 5920 bool IsStringKey() { return true; }
5920 5921
5921 String* string_; 5922 String* string_;
5922 }; 5923 };
5923 5924
5925
5926 // StringSharedKeys are used as keys in the eval cache.
5927 class StringSharedKey : public HashTableKey {
5928 public:
5929 StringSharedKey(String* source, SharedFunctionInfo* shared)
5930 : source_(source), shared_(shared) { }
5931
5932 bool IsMatch(Object* other) {
5933 if (!other->IsFixedArray()) return false;
5934 FixedArray* pair = FixedArray::cast(other);
5935 SharedFunctionInfo* shared = SharedFunctionInfo::cast(pair->get(0));
5936 if (shared != shared_) return false;
5937 String* source = String::cast(pair->get(1));
5938 return source->Equals(source_);
5939 }
5940
5941 typedef uint32_t (*HashFunction)(Object* obj);
5942
5943 virtual HashFunction GetHashFunction() { return StringSharedHash; }
5944
5945 static uint32_t StringSharedHashHelper(String* source,
5946 SharedFunctionInfo* shared) {
5947 uint32_t hash = source->Hash();
5948 if (shared->HasSourceCode()) {
5949 // Instead of using the SharedFunctionInfo pointer in the hash
5950 // code computation, we use a combination of the hash of the
5951 // script source code and the start and end positions. We do
5952 // this to ensure that the cache entries can survive garbage
5953 // collection.
5954 Script* script = Script::cast(shared->script());
5955 hash ^= String::cast(script->source())->Hash();
Kasper Lund 2009/02/24 11:21:08 It's not clear that this is a great way of mixing
5956 hash ^= ((shared->start_position() << 16) | shared->end_position());
5957 }
5958 return hash;
5959 }
5960
5961 static uint32_t StringSharedHash(Object* obj) {
5962 FixedArray* pair = FixedArray::cast(obj);
5963 SharedFunctionInfo* shared = SharedFunctionInfo::cast(pair->get(0));
5964 String* source = String::cast(pair->get(1));
5965 return StringSharedHashHelper(source, shared);
5966 }
5967
5968 virtual uint32_t Hash() {
5969 return StringSharedHashHelper(source_, shared_);
5970 }
5971
5972 virtual Object* GetObject() {
5973 Object* obj = Heap::AllocateFixedArray(2);
5974 if (obj->IsFailure()) return obj;
5975 FixedArray* pair = FixedArray::cast(obj);
5976 pair->set(0, shared_);
5977 pair->set(1, source_);
5978 return pair;
5979 }
5980
5981 virtual bool IsStringKey() { return false; }
5982
5983 private:
5984 String* source_;
5985 SharedFunctionInfo* shared_;
5986 };
5987
5988
5924 // RegExpKey carries the source and flags of a regular expression as key. 5989 // RegExpKey carries the source and flags of a regular expression as key.
5925 class RegExpKey : public HashTableKey { 5990 class RegExpKey : public HashTableKey {
5926 public: 5991 public:
5927 RegExpKey(String* string, JSRegExp::Flags flags) 5992 RegExpKey(String* string, JSRegExp::Flags flags)
5928 : string_(string), 5993 : string_(string),
5929 flags_(Smi::FromInt(flags.value())) { } 5994 flags_(Smi::FromInt(flags.value())) { }
5930 5995
5931 bool IsMatch(Object* obj) { 5996 bool IsMatch(Object* obj) {
5932 FixedArray* val = FixedArray::cast(obj); 5997 FixedArray* val = FixedArray::cast(obj);
5933 return string_->Equals(String::cast(val->get(JSRegExp::kSourceIndex))) 5998 return string_->Equals(String::cast(val->get(JSRegExp::kSourceIndex)))
(...skipping 293 matching lines...) Expand 10 before | Expand all | Expand 10 after
6227 6292
6228 6293
6229 Object* CompilationCacheTable::Lookup(String* src) { 6294 Object* CompilationCacheTable::Lookup(String* src) {
6230 StringKey key(src); 6295 StringKey key(src);
6231 int entry = FindEntry(&key); 6296 int entry = FindEntry(&key);
6232 if (entry == -1) return Heap::undefined_value(); 6297 if (entry == -1) return Heap::undefined_value();
6233 return get(EntryToIndex(entry) + 1); 6298 return get(EntryToIndex(entry) + 1);
6234 } 6299 }
6235 6300
6236 6301
6302 Object* CompilationCacheTable::LookupEval(String* src, Context* context) {
6303 StringSharedKey key(src, context->closure()->shared());
6304 int entry = FindEntry(&key);
6305 if (entry == -1) return Heap::undefined_value();
6306 return get(EntryToIndex(entry) + 1);
6307 }
6308
6309
6237 Object* CompilationCacheTable::LookupRegExp(String* src, 6310 Object* CompilationCacheTable::LookupRegExp(String* src,
6238 JSRegExp::Flags flags) { 6311 JSRegExp::Flags flags) {
6239 RegExpKey key(src, flags); 6312 RegExpKey key(src, flags);
6240 int entry = FindEntry(&key); 6313 int entry = FindEntry(&key);
6241 if (entry == -1) return Heap::undefined_value(); 6314 if (entry == -1) return Heap::undefined_value();
6242 return get(EntryToIndex(entry) + 1); 6315 return get(EntryToIndex(entry) + 1);
6243 } 6316 }
6244 6317
6245 6318
6246 Object* CompilationCacheTable::Put(String* src, Object* value) { 6319 Object* CompilationCacheTable::Put(String* src, Object* value) {
6247 StringKey key(src); 6320 StringKey key(src);
6248 Object* obj = EnsureCapacity(1, &key); 6321 Object* obj = EnsureCapacity(1, &key);
6249 if (obj->IsFailure()) return obj; 6322 if (obj->IsFailure()) return obj;
6250 6323
6251 CompilationCacheTable* cache = 6324 CompilationCacheTable* cache =
6252 reinterpret_cast<CompilationCacheTable*>(obj); 6325 reinterpret_cast<CompilationCacheTable*>(obj);
6253 int entry = cache->FindInsertionEntry(src, key.Hash()); 6326 int entry = cache->FindInsertionEntry(src, key.Hash());
6254 cache->set(EntryToIndex(entry), src); 6327 cache->set(EntryToIndex(entry), src);
6255 cache->set(EntryToIndex(entry) + 1, value); 6328 cache->set(EntryToIndex(entry) + 1, value);
6256 cache->ElementAdded(); 6329 cache->ElementAdded();
6257 return cache; 6330 return cache;
6258 } 6331 }
6259 6332
6260 6333
6334 Object* CompilationCacheTable::PutEval(String* src,
6335 Context* context,
6336 Object* value) {
6337 StringSharedKey key(src, context->closure()->shared());
6338 Object* obj = EnsureCapacity(1, &key);
6339 if (obj->IsFailure()) return obj;
6340
6341 CompilationCacheTable* cache =
6342 reinterpret_cast<CompilationCacheTable*>(obj);
6343 int entry = cache->FindInsertionEntry(src, key.Hash());
6344
6345 Object* k = key.GetObject();
6346 if (k->IsFailure()) return k;
6347
6348 cache->set(EntryToIndex(entry), k);
6349 cache->set(EntryToIndex(entry) + 1, value);
6350 cache->ElementAdded();
6351 return cache;
6352 }
6353
6354
6261 Object* CompilationCacheTable::PutRegExp(String* src, 6355 Object* CompilationCacheTable::PutRegExp(String* src,
6262 JSRegExp::Flags flags, 6356 JSRegExp::Flags flags,
6263 FixedArray* value) { 6357 FixedArray* value) {
6264 RegExpKey key(src, flags); 6358 RegExpKey key(src, flags);
6265 Object* obj = EnsureCapacity(1, &key); 6359 Object* obj = EnsureCapacity(1, &key);
6266 if (obj->IsFailure()) return obj; 6360 if (obj->IsFailure()) return obj;
6267 6361
6268 CompilationCacheTable* cache = 6362 CompilationCacheTable* cache =
6269 reinterpret_cast<CompilationCacheTable*>(obj); 6363 reinterpret_cast<CompilationCacheTable*>(obj);
6270 int entry = cache->FindInsertionEntry(value, key.Hash()); 6364 int entry = cache->FindInsertionEntry(value, key.Hash());
(...skipping 886 matching lines...) Expand 10 before | Expand all | Expand 10 after
7157 // No break point. 7251 // No break point.
7158 if (break_point_objects()->IsUndefined()) return 0; 7252 if (break_point_objects()->IsUndefined()) return 0;
7159 // Single beak point. 7253 // Single beak point.
7160 if (!break_point_objects()->IsFixedArray()) return 1; 7254 if (!break_point_objects()->IsFixedArray()) return 1;
7161 // Multiple break points. 7255 // Multiple break points.
7162 return FixedArray::cast(break_point_objects())->length(); 7256 return FixedArray::cast(break_point_objects())->length();
7163 } 7257 }
7164 7258
7165 7259
7166 } } // namespace v8::internal 7260 } } // namespace v8::internal
OLDNEW
« src/compilation-cache.h ('K') | « src/objects.h ('k') | src/runtime.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698