| OLD | NEW |
| 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 <iomanip> | 5 #include <iomanip> |
| 6 #include <sstream> | 6 #include <sstream> |
| 7 | 7 |
| 8 #include "src/v8.h" | 8 #include "src/v8.h" |
| 9 | 9 |
| 10 #include "src/accessors.h" | 10 #include "src/accessors.h" |
| (...skipping 789 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 800 return context->symbol_function()->initial_map(); | 800 return context->symbol_function()->initial_map(); |
| 801 } | 801 } |
| 802 if (heap_object->IsBoolean()) { | 802 if (heap_object->IsBoolean()) { |
| 803 return context->boolean_function()->initial_map(); | 803 return context->boolean_function()->initial_map(); |
| 804 } | 804 } |
| 805 return isolate->heap()->null_value()->map(); | 805 return isolate->heap()->null_value()->map(); |
| 806 } | 806 } |
| 807 | 807 |
| 808 | 808 |
| 809 Object* Object::GetHash() { | 809 Object* Object::GetHash() { |
| 810 // The object is either a number, a name, an odd-ball, | 810 // The object is either a Smi, a HeapNumber, a name, an odd-ball, |
| 811 // a real JS object, or a Harmony proxy. | 811 // a real JS object, or a Harmony proxy. |
| 812 if (IsSmi()) { | 812 if (IsSmi()) { |
| 813 int num = Smi::cast(this)->value(); | 813 uint32_t hash = ComputeIntegerHash(Smi::cast(this)->value(), kZeroHashSeed); |
| 814 uint32_t hash = ComputeLongHash(double_to_uint64(static_cast<double>(num))); | |
| 815 return Smi::FromInt(hash & Smi::kMaxValue); | 814 return Smi::FromInt(hash & Smi::kMaxValue); |
| 816 } | 815 } |
| 817 if (IsHeapNumber()) { | 816 if (IsHeapNumber()) { |
| 818 double num = HeapNumber::cast(this)->value(); | 817 double num = HeapNumber::cast(this)->value(); |
| 819 if (std::isnan(num)) return Smi::FromInt(Smi::kMaxValue); | 818 if (std::isnan(num)) return Smi::FromInt(Smi::kMaxValue); |
| 820 if (i::IsMinusZero(num)) num = 0; | 819 if (i::IsMinusZero(num)) num = 0; |
| 820 if (IsSmiDouble(num)) { |
| 821 return Smi::FromInt(FastD2I(num))->GetHash(); |
| 822 } |
| 821 uint32_t hash = ComputeLongHash(double_to_uint64(num)); | 823 uint32_t hash = ComputeLongHash(double_to_uint64(num)); |
| 822 return Smi::FromInt(hash & Smi::kMaxValue); | 824 return Smi::FromInt(hash & Smi::kMaxValue); |
| 823 } | 825 } |
| 824 if (IsName()) { | 826 if (IsName()) { |
| 825 uint32_t hash = Name::cast(this)->Hash(); | 827 uint32_t hash = Name::cast(this)->Hash(); |
| 826 return Smi::FromInt(hash); | 828 return Smi::FromInt(hash); |
| 827 } | 829 } |
| 828 if (IsOddball()) { | 830 if (IsOddball()) { |
| 829 uint32_t hash = Oddball::cast(this)->to_string()->Hash(); | 831 uint32_t hash = Oddball::cast(this)->to_string()->Hash(); |
| 830 return Smi::FromInt(hash); | 832 return Smi::FromInt(hash); |
| (...skipping 15420 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 16251 table->GetHeap()->InNewSpace(*table) ? NOT_TENURED : TENURED); | 16253 table->GetHeap()->InNewSpace(*table) ? NOT_TENURED : TENURED); |
| 16252 | 16254 |
| 16253 table->SetNextTable(*new_table); | 16255 table->SetNextTable(*new_table); |
| 16254 table->SetNumberOfDeletedElements(kClearedTableSentinel); | 16256 table->SetNumberOfDeletedElements(kClearedTableSentinel); |
| 16255 | 16257 |
| 16256 return new_table; | 16258 return new_table; |
| 16257 } | 16259 } |
| 16258 | 16260 |
| 16259 | 16261 |
| 16260 template<class Derived, class Iterator, int entrysize> | 16262 template<class Derived, class Iterator, int entrysize> |
| 16261 Handle<Derived> OrderedHashTable<Derived, Iterator, entrysize>::Remove( | |
| 16262 Handle<Derived> table, Handle<Object> key, bool* was_present) { | |
| 16263 int entry = table->FindEntry(key); | |
| 16264 if (entry == kNotFound) { | |
| 16265 *was_present = false; | |
| 16266 return table; | |
| 16267 } | |
| 16268 *was_present = true; | |
| 16269 table->RemoveEntry(entry); | |
| 16270 return Shrink(table); | |
| 16271 } | |
| 16272 | |
| 16273 | |
| 16274 template<class Derived, class Iterator, int entrysize> | |
| 16275 Handle<Derived> OrderedHashTable<Derived, Iterator, entrysize>::Rehash( | 16263 Handle<Derived> OrderedHashTable<Derived, Iterator, entrysize>::Rehash( |
| 16276 Handle<Derived> table, int new_capacity) { | 16264 Handle<Derived> table, int new_capacity) { |
| 16277 DCHECK(!table->IsObsolete()); | 16265 DCHECK(!table->IsObsolete()); |
| 16278 | 16266 |
| 16279 Handle<Derived> new_table = | 16267 Handle<Derived> new_table = |
| 16280 Allocate(table->GetIsolate(), | 16268 Allocate(table->GetIsolate(), |
| 16281 new_capacity, | 16269 new_capacity, |
| 16282 table->GetHeap()->InNewSpace(*table) ? NOT_TENURED : TENURED); | 16270 table->GetHeap()->InNewSpace(*table) ? NOT_TENURED : TENURED); |
| 16283 int nof = table->NumberOfElements(); | 16271 int nof = table->NumberOfElements(); |
| 16284 int nod = table->NumberOfDeletedElements(); | 16272 int nod = table->NumberOfDeletedElements(); |
| (...skipping 24 matching lines...) Expand all Loading... |
| 16309 | 16297 |
| 16310 DCHECK_EQ(nod, removed_holes_index); | 16298 DCHECK_EQ(nod, removed_holes_index); |
| 16311 | 16299 |
| 16312 new_table->SetNumberOfElements(nof); | 16300 new_table->SetNumberOfElements(nof); |
| 16313 table->SetNextTable(*new_table); | 16301 table->SetNextTable(*new_table); |
| 16314 | 16302 |
| 16315 return new_table; | 16303 return new_table; |
| 16316 } | 16304 } |
| 16317 | 16305 |
| 16318 | 16306 |
| 16319 template <class Derived, class Iterator, int entrysize> | |
| 16320 int OrderedHashTable<Derived, Iterator, entrysize>::FindEntry( | |
| 16321 Handle<Object> key, int hash) { | |
| 16322 DCHECK(!IsObsolete()); | |
| 16323 | |
| 16324 DisallowHeapAllocation no_gc; | |
| 16325 DCHECK(!key->IsTheHole()); | |
| 16326 for (int entry = HashToEntry(hash); entry != kNotFound; | |
| 16327 entry = ChainAt(entry)) { | |
| 16328 Object* candidate = KeyAt(entry); | |
| 16329 if (candidate->SameValueZero(*key)) | |
| 16330 return entry; | |
| 16331 } | |
| 16332 return kNotFound; | |
| 16333 } | |
| 16334 | |
| 16335 | |
| 16336 template <class Derived, class Iterator, int entrysize> | |
| 16337 int OrderedHashTable<Derived, Iterator, entrysize>::FindEntry( | |
| 16338 Handle<Object> key) { | |
| 16339 DisallowHeapAllocation no_gc; | |
| 16340 Object* hash = key->GetHash(); | |
| 16341 if (!hash->IsSmi()) return kNotFound; | |
| 16342 return FindEntry(key, Smi::cast(hash)->value()); | |
| 16343 } | |
| 16344 | |
| 16345 | |
| 16346 template <class Derived, class Iterator, int entrysize> | |
| 16347 int OrderedHashTable<Derived, Iterator, entrysize>::AddEntry(int hash) { | |
| 16348 DCHECK(!IsObsolete()); | |
| 16349 | |
| 16350 int entry = UsedCapacity(); | |
| 16351 int bucket = HashToBucket(hash); | |
| 16352 int index = EntryToIndex(entry); | |
| 16353 Object* chain_entry = get(kHashTableStartIndex + bucket); | |
| 16354 set(kHashTableStartIndex + bucket, Smi::FromInt(entry)); | |
| 16355 set(index + kChainOffset, chain_entry); | |
| 16356 SetNumberOfElements(NumberOfElements() + 1); | |
| 16357 return index; | |
| 16358 } | |
| 16359 | |
| 16360 | |
| 16361 template<class Derived, class Iterator, int entrysize> | |
| 16362 void OrderedHashTable<Derived, Iterator, entrysize>::RemoveEntry(int entry) { | |
| 16363 DCHECK(!IsObsolete()); | |
| 16364 | |
| 16365 int index = EntryToIndex(entry); | |
| 16366 for (int i = 0; i < entrysize; ++i) { | |
| 16367 set_the_hole(index + i); | |
| 16368 } | |
| 16369 SetNumberOfElements(NumberOfElements() - 1); | |
| 16370 SetNumberOfDeletedElements(NumberOfDeletedElements() + 1); | |
| 16371 } | |
| 16372 | |
| 16373 | |
| 16374 template Handle<OrderedHashSet> | 16307 template Handle<OrderedHashSet> |
| 16375 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Allocate( | 16308 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Allocate( |
| 16376 Isolate* isolate, int capacity, PretenureFlag pretenure); | 16309 Isolate* isolate, int capacity, PretenureFlag pretenure); |
| 16377 | 16310 |
| 16378 template Handle<OrderedHashSet> | 16311 template Handle<OrderedHashSet> |
| 16379 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::EnsureGrowable( | 16312 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::EnsureGrowable( |
| 16380 Handle<OrderedHashSet> table); | 16313 Handle<OrderedHashSet> table); |
| 16381 | 16314 |
| 16382 template Handle<OrderedHashSet> | 16315 template Handle<OrderedHashSet> |
| 16383 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Shrink( | 16316 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Shrink( |
| 16384 Handle<OrderedHashSet> table); | 16317 Handle<OrderedHashSet> table); |
| 16385 | 16318 |
| 16386 template Handle<OrderedHashSet> | 16319 template Handle<OrderedHashSet> |
| 16387 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Clear( | 16320 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Clear( |
| 16388 Handle<OrderedHashSet> table); | 16321 Handle<OrderedHashSet> table); |
| 16389 | 16322 |
| 16390 template Handle<OrderedHashSet> | |
| 16391 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::Remove( | |
| 16392 Handle<OrderedHashSet> table, Handle<Object> key, bool* was_present); | |
| 16393 | |
| 16394 template int OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::FindEntry( | |
| 16395 Handle<Object> key, int hash); | |
| 16396 template int OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::FindEntry( | |
| 16397 Handle<Object> key); | |
| 16398 | |
| 16399 template int | |
| 16400 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::AddEntry(int hash); | |
| 16401 | |
| 16402 template void | |
| 16403 OrderedHashTable<OrderedHashSet, JSSetIterator, 1>::RemoveEntry(int entry); | |
| 16404 | |
| 16405 | 16323 |
| 16406 template Handle<OrderedHashMap> | 16324 template Handle<OrderedHashMap> |
| 16407 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Allocate( | 16325 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Allocate( |
| 16408 Isolate* isolate, int capacity, PretenureFlag pretenure); | 16326 Isolate* isolate, int capacity, PretenureFlag pretenure); |
| 16409 | 16327 |
| 16410 template Handle<OrderedHashMap> | 16328 template Handle<OrderedHashMap> |
| 16411 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::EnsureGrowable( | 16329 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::EnsureGrowable( |
| 16412 Handle<OrderedHashMap> table); | 16330 Handle<OrderedHashMap> table); |
| 16413 | 16331 |
| 16414 template Handle<OrderedHashMap> | 16332 template Handle<OrderedHashMap> |
| 16415 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Shrink( | 16333 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Shrink( |
| 16416 Handle<OrderedHashMap> table); | 16334 Handle<OrderedHashMap> table); |
| 16417 | 16335 |
| 16418 template Handle<OrderedHashMap> | 16336 template Handle<OrderedHashMap> |
| 16419 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Clear( | 16337 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Clear( |
| 16420 Handle<OrderedHashMap> table); | 16338 Handle<OrderedHashMap> table); |
| 16421 | 16339 |
| 16422 template Handle<OrderedHashMap> | |
| 16423 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::Remove( | |
| 16424 Handle<OrderedHashMap> table, Handle<Object> key, bool* was_present); | |
| 16425 | |
| 16426 template int OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::FindEntry( | |
| 16427 Handle<Object> key, int hash); | |
| 16428 template int OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::FindEntry( | |
| 16429 Handle<Object> key); | |
| 16430 | |
| 16431 template int | |
| 16432 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::AddEntry(int hash); | |
| 16433 | |
| 16434 template void | |
| 16435 OrderedHashTable<OrderedHashMap, JSMapIterator, 2>::RemoveEntry(int entry); | |
| 16436 | |
| 16437 | |
| 16438 bool OrderedHashSet::Contains(Handle<Object> key) { | |
| 16439 return FindEntry(key) != kNotFound; | |
| 16440 } | |
| 16441 | |
| 16442 | |
| 16443 Handle<OrderedHashSet> OrderedHashSet::Add(Handle<OrderedHashSet> table, | |
| 16444 Handle<Object> key) { | |
| 16445 int hash = GetOrCreateHash(table->GetIsolate(), key)->value(); | |
| 16446 if (table->FindEntry(key, hash) != kNotFound) return table; | |
| 16447 | |
| 16448 table = EnsureGrowable(table); | |
| 16449 | |
| 16450 int index = table->AddEntry(hash); | |
| 16451 table->set(index, *key); | |
| 16452 return table; | |
| 16453 } | |
| 16454 | |
| 16455 | |
| 16456 Object* OrderedHashMap::Lookup(Handle<Object> key) { | |
| 16457 DisallowHeapAllocation no_gc; | |
| 16458 int entry = FindEntry(key); | |
| 16459 if (entry == kNotFound) return GetHeap()->the_hole_value(); | |
| 16460 return ValueAt(entry); | |
| 16461 } | |
| 16462 | |
| 16463 | |
| 16464 Handle<OrderedHashMap> OrderedHashMap::Put(Handle<OrderedHashMap> table, | |
| 16465 Handle<Object> key, | |
| 16466 Handle<Object> value) { | |
| 16467 DCHECK(!key->IsTheHole()); | |
| 16468 | |
| 16469 int hash = GetOrCreateHash(table->GetIsolate(), key)->value(); | |
| 16470 int entry = table->FindEntry(key, hash); | |
| 16471 | |
| 16472 if (entry != kNotFound) { | |
| 16473 table->set(table->EntryToIndex(entry) + kValueOffset, *value); | |
| 16474 return table; | |
| 16475 } | |
| 16476 | |
| 16477 table = EnsureGrowable(table); | |
| 16478 | |
| 16479 int index = table->AddEntry(hash); | |
| 16480 table->set(index, *key); | |
| 16481 table->set(index + kValueOffset, *value); | |
| 16482 return table; | |
| 16483 } | |
| 16484 | |
| 16485 | 16340 |
| 16486 template<class Derived, class TableType> | 16341 template<class Derived, class TableType> |
| 16487 void OrderedHashTableIterator<Derived, TableType>::Transition() { | 16342 void OrderedHashTableIterator<Derived, TableType>::Transition() { |
| 16488 DisallowHeapAllocation no_allocation; | 16343 DisallowHeapAllocation no_allocation; |
| 16489 TableType* table = TableType::cast(this->table()); | 16344 TableType* table = TableType::cast(this->table()); |
| 16490 if (!table->IsObsolete()) return; | 16345 if (!table->IsObsolete()) return; |
| 16491 | 16346 |
| 16492 int index = Smi::cast(this->index())->value(); | 16347 int index = Smi::cast(this->index())->value(); |
| 16493 while (table->IsObsolete()) { | 16348 while (table->IsObsolete()) { |
| 16494 TableType* next_table = table->NextTable(); | 16349 TableType* next_table = table->NextTable(); |
| (...skipping 686 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 17181 CompilationInfo* info) { | 17036 CompilationInfo* info) { |
| 17182 Handle<DependentCode> codes = DependentCode::InsertCompilationInfo( | 17037 Handle<DependentCode> codes = DependentCode::InsertCompilationInfo( |
| 17183 handle(cell->dependent_code(), info->isolate()), | 17038 handle(cell->dependent_code(), info->isolate()), |
| 17184 DependentCode::kPropertyCellChangedGroup, info->object_wrapper()); | 17039 DependentCode::kPropertyCellChangedGroup, info->object_wrapper()); |
| 17185 if (*codes != cell->dependent_code()) cell->set_dependent_code(*codes); | 17040 if (*codes != cell->dependent_code()) cell->set_dependent_code(*codes); |
| 17186 info->dependencies(DependentCode::kPropertyCellChangedGroup)->Add( | 17041 info->dependencies(DependentCode::kPropertyCellChangedGroup)->Add( |
| 17187 cell, info->zone()); | 17042 cell, info->zone()); |
| 17188 } | 17043 } |
| 17189 | 17044 |
| 17190 } } // namespace v8::internal | 17045 } } // namespace v8::internal |
| OLD | NEW |