Commit e72f7f53 authored by Sathya Gunasekaran's avatar Sathya Gunasekaran Committed by Commit Bot

[hashtable] Port SmallOrderedHashTableAllocate to CSA

Bug: v8:6443, v8:7569
Change-Id: Ia7e1ed9ab7e85ac366349688278ba59507d38b7e
Reviewed-on: https://chromium-review.googlesource.com/1098474
Commit-Queue: Sathya Gunasekaran <gsathya@chromium.org>
Reviewed-by: 's avatarCamillo Bruni <cbruni@chromium.org>
Cr-Commit-Position: refs/heads/master@{#54068}
parent a617bf52
...@@ -2433,6 +2433,13 @@ Node* CodeStubAssembler::LoadSharedFunctionInfoBytecodeArray(Node* shared) { ...@@ -2433,6 +2433,13 @@ Node* CodeStubAssembler::LoadSharedFunctionInfoBytecodeArray(Node* shared) {
return var_result.value(); return var_result.value();
} }
void CodeStubAssembler::StoreObjectByteNoWriteBarrier(TNode<HeapObject> object,
int offset,
TNode<Word32T> value) {
StoreNoWriteBarrier(MachineRepresentation::kWord8, object,
IntPtrConstant(offset - kHeapObjectTag), value);
}
void CodeStubAssembler::StoreHeapNumberValue(SloppyTNode<HeapNumber> object, void CodeStubAssembler::StoreHeapNumberValue(SloppyTNode<HeapNumber> object,
SloppyTNode<Float64T> value) { SloppyTNode<Float64T> value) {
StoreObjectFieldNoWriteBarrier(object, HeapNumber::kValueOffset, value, StoreObjectFieldNoWriteBarrier(object, HeapNumber::kValueOffset, value,
...@@ -3256,6 +3263,87 @@ Node* CodeStubAssembler::AllocateOrderedHashTable() { ...@@ -3256,6 +3263,87 @@ Node* CodeStubAssembler::AllocateOrderedHashTable() {
template Node* CodeStubAssembler::AllocateOrderedHashTable<OrderedHashMap>(); template Node* CodeStubAssembler::AllocateOrderedHashTable<OrderedHashMap>();
template Node* CodeStubAssembler::AllocateOrderedHashTable<OrderedHashSet>(); template Node* CodeStubAssembler::AllocateOrderedHashTable<OrderedHashSet>();
template <typename CollectionType>
TNode<CollectionType> CodeStubAssembler::AllocateSmallOrderedHashTable(
TNode<IntPtrT> capacity) {
CSA_ASSERT(this, WordIsPowerOfTwo(capacity));
CSA_ASSERT(this, IntPtrLessThan(
capacity, IntPtrConstant(CollectionType::kMaxCapacity)));
TNode<IntPtrT> data_table_start_offset =
IntPtrConstant(CollectionType::kDataTableStartOffset);
TNode<IntPtrT> data_table_size = IntPtrMul(
capacity, IntPtrConstant(CollectionType::kEntrySize * kPointerSize));
TNode<Int32T> hash_table_size =
Int32Div(TruncateIntPtrToInt32(capacity),
Int32Constant(CollectionType::kLoadFactor));
TNode<IntPtrT> hash_table_start_offset =
IntPtrAdd(data_table_start_offset, data_table_size);
TNode<IntPtrT> hash_table_and_chain_table_size =
IntPtrAdd(ChangeInt32ToIntPtr(hash_table_size), capacity);
TNode<IntPtrT> total_size =
IntPtrAdd(hash_table_start_offset, hash_table_and_chain_table_size);
TNode<IntPtrT> total_size_word_aligned =
IntPtrAdd(total_size, IntPtrConstant(kPointerSize - 1));
total_size_word_aligned = ChangeInt32ToIntPtr(
Int32Div(TruncateIntPtrToInt32(total_size_word_aligned),
Int32Constant(kPointerSize)));
total_size_word_aligned =
UncheckedCast<IntPtrT>(TimesPointerSize(total_size_word_aligned));
// Allocate the table and add the proper map.
TNode<Map> small_ordered_hash_map = CAST(LoadRoot(
static_cast<Heap::RootListIndex>(CollectionType::GetMapRootIndex())));
TNode<Object> table_obj = CAST(AllocateInNewSpace(total_size_word_aligned));
StoreMapNoWriteBarrier(table_obj, small_ordered_hash_map);
TNode<CollectionType> table = UncheckedCast<CollectionType>(table_obj);
// Initialize the SmallOrderedHashTable fields.
StoreObjectByteNoWriteBarrier(
table, CollectionType::kNumberOfBucketsOffset,
Word32And(Int32Constant(0xFF), hash_table_size));
StoreObjectByteNoWriteBarrier(table, CollectionType::kNumberOfElementsOffset,
Int32Constant(0));
StoreObjectByteNoWriteBarrier(
table, CollectionType::kNumberOfDeletedElementsOffset, Int32Constant(0));
TNode<IntPtrT> table_address =
IntPtrSub(BitcastTaggedToWord(table), IntPtrConstant(kHeapObjectTag));
TNode<IntPtrT> hash_table_start_address =
IntPtrAdd(table_address, hash_table_start_offset);
// Initialize the HashTable part.
Node* memset = ExternalConstant(ExternalReference::libc_memset_function());
CallCFunction3(MachineType::AnyTagged(), MachineType::Pointer(),
MachineType::IntPtr(), MachineType::UintPtr(), memset,
hash_table_start_address, IntPtrConstant(0xFF),
hash_table_and_chain_table_size);
// Initialize the DataTable part.
TNode<HeapObject> filler = TheHoleConstant();
TNode<WordT> data_table_start_address =
IntPtrAdd(table_address, data_table_start_offset);
TNode<WordT> data_table_end_address =
IntPtrAdd(data_table_start_address, data_table_size);
StoreFieldsNoWriteBarrier(data_table_start_address, data_table_end_address,
filler);
return table;
}
template TNode<SmallOrderedHashMap>
CodeStubAssembler::AllocateSmallOrderedHashTable<SmallOrderedHashMap>(
TNode<IntPtrT> capacity);
template TNode<SmallOrderedHashSet>
CodeStubAssembler::AllocateSmallOrderedHashTable<SmallOrderedHashSet>(
TNode<IntPtrT> capacity);
template <typename CollectionType> template <typename CollectionType>
void CodeStubAssembler::FindOrderedHashTableEntry( void CodeStubAssembler::FindOrderedHashTableEntry(
Node* table, Node* hash, Node* table, Node* hash,
...@@ -4700,7 +4788,7 @@ TNode<UintPtrT> CodeStubAssembler::ChangeNonnegativeNumberToUintPtr( ...@@ -4700,7 +4788,7 @@ TNode<UintPtrT> CodeStubAssembler::ChangeNonnegativeNumberToUintPtr(
return result.value(); return result.value();
} }
Node* CodeStubAssembler::TimesPointerSize(Node* value) { SloppyTNode<WordT> CodeStubAssembler::TimesPointerSize(Node* value) {
return WordShl(value, IntPtrConstant(kPointerSizeLog2)); return WordShl(value, IntPtrConstant(kPointerSizeLog2));
} }
......
...@@ -1072,6 +1072,9 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler { ...@@ -1072,6 +1072,9 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler {
Node* LoadSharedFunctionInfoBytecodeArray(Node* shared); Node* LoadSharedFunctionInfoBytecodeArray(Node* shared);
void StoreObjectByteNoWriteBarrier(TNode<HeapObject> object, int offset,
TNode<Word32T> value);
// Store the floating point value of a HeapNumber. // Store the floating point value of a HeapNumber.
void StoreHeapNumberValue(SloppyTNode<HeapNumber> object, void StoreHeapNumberValue(SloppyTNode<HeapNumber> object,
SloppyTNode<Float64T> value); SloppyTNode<Float64T> value);
...@@ -1254,6 +1257,9 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler { ...@@ -1254,6 +1257,9 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler {
std::function<void(Node*, Label*, Label*)> key_compare, std::function<void(Node*, Label*, Label*)> key_compare,
Variable* entry_start_position, Label* entry_found, Label* not_found); Variable* entry_start_position, Label* entry_found, Label* not_found);
template <typename CollectionType>
TNode<CollectionType> AllocateSmallOrderedHashTable(TNode<IntPtrT> capacity);
Node* AllocateStruct(Node* map, AllocationFlags flags = kNone); Node* AllocateStruct(Node* map, AllocationFlags flags = kNone);
void InitializeStructBody(Node* object, Node* map, Node* size, void InitializeStructBody(Node* object, Node* map, Node* size,
int start_offset = Struct::kHeaderSize); int start_offset = Struct::kHeaderSize);
...@@ -1554,7 +1560,7 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler { ...@@ -1554,7 +1560,7 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler {
Variable* var_numeric, Variable* var_numeric,
Variable* var_feedback); Variable* var_feedback);
Node* TimesPointerSize(Node* value); SloppyTNode<WordT> TimesPointerSize(Node* value);
// Type conversions. // Type conversions.
// Throws a TypeError for {method_name} if {value} is not coercible to Object, // Throws a TypeError for {method_name} if {value} is not coercible to Object,
......
...@@ -725,9 +725,9 @@ ExternalReference ExternalReference::libc_memmove_function() { ...@@ -725,9 +725,9 @@ ExternalReference ExternalReference::libc_memmove_function() {
return ExternalReference(Redirect(FUNCTION_ADDR(libc_memmove))); return ExternalReference(Redirect(FUNCTION_ADDR(libc_memmove)));
} }
void* libc_memset(void* dest, int byte, size_t n) { void* libc_memset(void* dest, int value, size_t n) {
DCHECK_EQ(static_cast<char>(byte), byte); DCHECK_EQ(static_cast<byte>(value), value);
return memset(dest, byte, n); return memset(dest, value, n);
} }
ExternalReference ExternalReference::libc_memset_function() { ExternalReference ExternalReference::libc_memset_function() {
......
...@@ -235,7 +235,7 @@ class SmallOrderedHashTable<Derived>::BodyDescriptor final ...@@ -235,7 +235,7 @@ class SmallOrderedHashTable<Derived>::BodyDescriptor final
ObjectVisitor* v) { ObjectVisitor* v) {
Derived* table = reinterpret_cast<Derived*>(obj); Derived* table = reinterpret_cast<Derived*>(obj);
int offset = kHeaderSize + kDataTableStartOffset; int offset = kDataTableStartOffset;
int entry = 0; int entry = 0;
for (int i = 0; i < table->Capacity(); i++) { for (int i = 0; i < table->Capacity(); i++) {
for (int j = 0; j < Derived::kEntrySize; j++) { for (int j = 0; j < Derived::kEntrySize; j++) {
......
...@@ -2705,8 +2705,7 @@ void Foreign::set_foreign_address(Address value) { ...@@ -2705,8 +2705,7 @@ void Foreign::set_foreign_address(Address value) {
template <class Derived> template <class Derived>
void SmallOrderedHashTable<Derived>::SetDataEntry(int entry, int relative_index, void SmallOrderedHashTable<Derived>::SetDataEntry(int entry, int relative_index,
Object* value) { Object* value) {
Address entry_offset = Address entry_offset = GetDataEntryOffset(entry, relative_index);
kHeaderSize + GetDataEntryOffset(entry, relative_index);
RELAXED_WRITE_FIELD(this, entry_offset, value); RELAXED_WRITE_FIELD(this, entry_offset, value);
WRITE_BARRIER(Heap::FromWritableHeapObject(this), this, WRITE_BARRIER(Heap::FromWritableHeapObject(this), this,
static_cast<int>(entry_offset), value); static_cast<int>(entry_offset), value);
......
...@@ -19,6 +19,14 @@ int OrderedHashMap::GetMapRootIndex() { ...@@ -19,6 +19,14 @@ int OrderedHashMap::GetMapRootIndex() {
return Heap::kOrderedHashMapMapRootIndex; return Heap::kOrderedHashMapMapRootIndex;
} }
int SmallOrderedHashMap::GetMapRootIndex() {
return Heap::kSmallOrderedHashMapMapRootIndex;
}
int SmallOrderedHashSet::GetMapRootIndex() {
return Heap::kSmallOrderedHashSetMapRootIndex;
}
inline Object* OrderedHashMap::ValueAt(int entry) { inline Object* OrderedHashMap::ValueAt(int entry) {
DCHECK_LT(entry, this->UsedCapacity()); DCHECK_LT(entry, this->UsedCapacity());
return get(EntryToIndex(entry) + kValueOffset); return get(EntryToIndex(entry) + kValueOffset);
......
...@@ -337,7 +337,7 @@ void SmallOrderedHashTable<Derived>::Initialize(Isolate* isolate, ...@@ -337,7 +337,7 @@ void SmallOrderedHashTable<Derived>::Initialize(Isolate* isolate,
num_buckets + num_chains); num_buckets + num_chains);
if (isolate->heap()->InNewSpace(this)) { if (isolate->heap()->InNewSpace(this)) {
MemsetPointer(RawField(this, kHeaderSize + kDataTableStartOffset), MemsetPointer(RawField(this, kDataTableStartOffset),
isolate->heap()->the_hole_value(), isolate->heap()->the_hole_value(),
capacity * Derived::kEntrySize); capacity * Derived::kEntrySize);
} else { } else {
......
...@@ -338,10 +338,10 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -338,10 +338,10 @@ class SmallOrderedHashTable : public HeapObject {
int data_table_size = DataTableSizeFor(capacity); int data_table_size = DataTableSizeFor(capacity);
int hash_table_size = capacity / kLoadFactor; int hash_table_size = capacity / kLoadFactor;
int chain_table_size = capacity; int chain_table_size = capacity;
int total_size = kHeaderSize + kDataTableStartOffset + data_table_size + int total_size = kDataTableStartOffset + data_table_size + hash_table_size +
hash_table_size + chain_table_size; chain_table_size;
return ((total_size + kPointerSize - 1) / kPointerSize) * kPointerSize; return RoundUp(total_size, kPointerSize);
} }
// Returns the number elements that can fit into the allocated table. // Returns the number elements that can fit into the allocated table.
...@@ -355,20 +355,20 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -355,20 +355,20 @@ class SmallOrderedHashTable : public HeapObject {
// Returns the number elements that are present in the table. // Returns the number elements that are present in the table.
int NumberOfElements() const { int NumberOfElements() const {
int nof_elements = getByte(0, kNumberOfElementsByteIndex); int nof_elements = getByte(kNumberOfElementsOffset, 0);
DCHECK_LE(nof_elements, Capacity()); DCHECK_LE(nof_elements, Capacity());
return nof_elements; return nof_elements;
} }
int NumberOfDeletedElements() const { int NumberOfDeletedElements() const {
int nof_deleted_elements = getByte(0, kNumberOfDeletedElementsByteIndex); int nof_deleted_elements = getByte(kNumberOfDeletedElementsOffset, 0);
DCHECK_LE(nof_deleted_elements, Capacity()); DCHECK_LE(nof_deleted_elements, Capacity());
return nof_deleted_elements; return nof_deleted_elements;
} }
int NumberOfBuckets() const { return getByte(0, kNumberOfBucketsByteIndex); } int NumberOfBuckets() const { return getByte(kNumberOfBucketsOffset, 0); }
DECL_VERIFIER(SmallOrderedHashTable) DECL_VERIFIER(SmallOrderedHashTable)
...@@ -407,8 +407,7 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -407,8 +407,7 @@ class SmallOrderedHashTable : public HeapObject {
} }
Address GetHashTableStartAddress(int capacity) const { Address GetHashTableStartAddress(int capacity) const {
return FIELD_ADDR( return FIELD_ADDR(this, kDataTableStartOffset + DataTableSizeFor(capacity));
this, kHeaderSize + kDataTableStartOffset + DataTableSizeFor(capacity));
} }
void SetFirstEntry(int bucket, byte value) { void SetFirstEntry(int bucket, byte value) {
...@@ -449,13 +448,13 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -449,13 +448,13 @@ class SmallOrderedHashTable : public HeapObject {
DCHECK_LT(entry, Capacity()); DCHECK_LT(entry, Capacity());
DCHECK_LE(static_cast<unsigned>(relative_index), Derived::kEntrySize); DCHECK_LE(static_cast<unsigned>(relative_index), Derived::kEntrySize);
Offset entry_offset = GetDataEntryOffset(entry, relative_index); Offset entry_offset = GetDataEntryOffset(entry, relative_index);
return READ_FIELD(this, kHeaderSize + entry_offset); return READ_FIELD(this, entry_offset);
} }
Object* KeyAt(int entry) const { Object* KeyAt(int entry) const {
DCHECK_LT(entry, Capacity()); DCHECK_LT(entry, Capacity());
Offset entry_offset = GetDataEntryOffset(entry, Derived::kKeyIndex); Offset entry_offset = GetDataEntryOffset(entry, Derived::kKeyIndex);
return READ_FIELD(this, kHeaderSize + entry_offset); return READ_FIELD(this, entry_offset);
} }
int HashToBucket(int hash) const { return hash & (NumberOfBuckets() - 1); } int HashToBucket(int hash) const { return hash & (NumberOfBuckets() - 1); }
...@@ -467,18 +466,16 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -467,18 +466,16 @@ class SmallOrderedHashTable : public HeapObject {
return entry; return entry;
} }
void SetNumberOfBuckets(int num) { void SetNumberOfBuckets(int num) { setByte(kNumberOfBucketsOffset, 0, num); }
setByte(0, kNumberOfBucketsByteIndex, num);
}
void SetNumberOfElements(int num) { void SetNumberOfElements(int num) {
DCHECK_LE(static_cast<unsigned>(num), Capacity()); DCHECK_LE(static_cast<unsigned>(num), Capacity());
setByte(0, kNumberOfElementsByteIndex, num); setByte(kNumberOfElementsOffset, 0, num);
} }
void SetNumberOfDeletedElements(int num) { void SetNumberOfDeletedElements(int num) {
DCHECK_LE(static_cast<unsigned>(num), Capacity()); DCHECK_LE(static_cast<unsigned>(num), Capacity());
setByte(0, kNumberOfDeletedElementsByteIndex, num); setByte(kNumberOfDeletedElementsOffset, 0, num);
} }
int FindEntry(Isolate* isolate, Object* key) { int FindEntry(Isolate* isolate, Object* key) {
...@@ -497,11 +494,14 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -497,11 +494,14 @@ class SmallOrderedHashTable : public HeapObject {
return kNotFound; return kNotFound;
} }
static const int kNumberOfElementsByteIndex = 0; static const Offset kNumberOfElementsOffset = kHeaderSize;
static const int kNumberOfDeletedElementsByteIndex = 1; static const Offset kNumberOfDeletedElementsOffset =
static const int kNumberOfBucketsByteIndex = 2; kNumberOfElementsOffset + kOneByteSize;
static const Offset kNumberOfBucketsOffset =
kNumberOfDeletedElementsOffset + kOneByteSize;
static const constexpr Offset kDataTableStartOffset =
RoundUp<kPointerSize>(kNumberOfBucketsOffset);
static const Offset kDataTableStartOffset = kPointerSize;
static constexpr int DataTableSizeFor(int capacity) { static constexpr int DataTableSizeFor(int capacity) {
return capacity * Derived::kEntrySize * kPointerSize; return capacity * Derived::kEntrySize * kPointerSize;
} }
...@@ -510,13 +510,12 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -510,13 +510,12 @@ class SmallOrderedHashTable : public HeapObject {
// structure. // structure.
byte getByte(Offset offset, ByteIndex index) const { byte getByte(Offset offset, ByteIndex index) const {
DCHECK(offset < kDataTableStartOffset || offset >= GetBucketsStartOffset()); DCHECK(offset < kDataTableStartOffset || offset >= GetBucketsStartOffset());
return READ_BYTE_FIELD(this, kHeaderSize + offset + (index * kOneByteSize)); return READ_BYTE_FIELD(this, offset + (index * kOneByteSize));
} }
void setByte(Offset offset, ByteIndex index, byte value) { void setByte(Offset offset, ByteIndex index, byte value) {
DCHECK(offset < kDataTableStartOffset || offset >= GetBucketsStartOffset()); DCHECK(offset < kDataTableStartOffset || offset >= GetBucketsStartOffset());
WRITE_BYTE_FIELD(this, kHeaderSize + offset + (index * kOneByteSize), WRITE_BYTE_FIELD(this, offset + (index * kOneByteSize), value);
value);
} }
Offset GetDataEntryOffset(int entry, int relative_index) const { Offset GetDataEntryOffset(int entry, int relative_index) const {
...@@ -536,6 +535,7 @@ class SmallOrderedHashTable : public HeapObject { ...@@ -536,6 +535,7 @@ class SmallOrderedHashTable : public HeapObject {
private: private:
friend class OrderedHashMapHandler; friend class OrderedHashMapHandler;
friend class OrderedHashSetHandler; friend class OrderedHashSetHandler;
friend class CodeStubAssembler;
}; };
class SmallOrderedHashSet : public SmallOrderedHashTable<SmallOrderedHashSet> { class SmallOrderedHashSet : public SmallOrderedHashTable<SmallOrderedHashSet> {
...@@ -554,6 +554,7 @@ class SmallOrderedHashSet : public SmallOrderedHashTable<SmallOrderedHashSet> { ...@@ -554,6 +554,7 @@ class SmallOrderedHashSet : public SmallOrderedHashTable<SmallOrderedHashSet> {
Handle<SmallOrderedHashSet> table, Handle<SmallOrderedHashSet> table,
Handle<Object> key); Handle<Object> key);
static inline bool Is(Handle<HeapObject> table); static inline bool Is(Handle<HeapObject> table);
static inline int GetMapRootIndex();
}; };
class SmallOrderedHashMap : public SmallOrderedHashTable<SmallOrderedHashMap> { class SmallOrderedHashMap : public SmallOrderedHashTable<SmallOrderedHashMap> {
...@@ -574,6 +575,7 @@ class SmallOrderedHashMap : public SmallOrderedHashTable<SmallOrderedHashMap> { ...@@ -574,6 +575,7 @@ class SmallOrderedHashMap : public SmallOrderedHashTable<SmallOrderedHashMap> {
Handle<Object> key, Handle<Object> key,
Handle<Object> value); Handle<Object> value);
static inline bool Is(Handle<HeapObject> table); static inline bool Is(Handle<HeapObject> table);
static inline int GetMapRootIndex();
}; };
// TODO(gsathya): Rename this to OrderedHashTable, after we rename // TODO(gsathya): Rename this to OrderedHashTable, after we rename
......
...@@ -3314,6 +3314,80 @@ TEST(SingleInputPhiElimination) { ...@@ -3314,6 +3314,80 @@ TEST(SingleInputPhiElimination) {
// single-input phi is properly eliminated. // single-input phi is properly eliminated.
} }
TEST(SmallOrderedHashMapAllocate) {
Isolate* isolate(CcTest::InitIsolateOnce());
const int kNumParams = 1;
CodeAssemblerTester asm_tester(isolate, kNumParams);
{
CodeStubAssembler m(asm_tester.state());
TNode<Smi> capacity = m.CAST(m.Parameter(0));
m.Return(m.AllocateSmallOrderedHashTable<SmallOrderedHashMap>(
m.SmiToIntPtr(capacity)));
}
FunctionTester ft(asm_tester.GenerateCode(), kNumParams);
Factory* factory = isolate->factory();
int capacity = SmallOrderedHashMap::kMinCapacity;
while (capacity <= SmallOrderedHashMap::kMaxCapacity) {
Handle<SmallOrderedHashMap> expected =
factory->NewSmallOrderedHashMap(capacity);
Handle<Object> result_raw =
ft.Call(Handle<Smi>(Smi::FromInt(capacity), isolate)).ToHandleChecked();
Handle<SmallOrderedHashMap> actual = Handle<SmallOrderedHashMap>(
SmallOrderedHashMap::cast(*result_raw), isolate);
CHECK_EQ(capacity, actual->Capacity());
CHECK_EQ(0, actual->NumberOfElements());
CHECK_EQ(0, actual->NumberOfDeletedElements());
CHECK_EQ(capacity / SmallOrderedHashMap::kLoadFactor,
actual->NumberOfBuckets());
CHECK(memcmp(*expected, *actual, SmallOrderedHashMap::SizeFor(capacity)));
#ifdef VERIFY_HEAP
actual->SmallOrderedHashTableVerify(isolate);
#endif
capacity = capacity << 1;
}
#ifdef VERIFY_HEAP
isolate->heap()->Verify();
#endif
}
TEST(SmallOrderedHashSetAllocate) {
Isolate* isolate(CcTest::InitIsolateOnce());
const int kNumParams = 1;
CodeAssemblerTester asm_tester(isolate, kNumParams);
{
CodeStubAssembler m(asm_tester.state());
TNode<Smi> capacity = m.CAST(m.Parameter(0));
m.Return(m.AllocateSmallOrderedHashTable<SmallOrderedHashSet>(
m.SmiToIntPtr(capacity)));
}
FunctionTester ft(asm_tester.GenerateCode(), kNumParams);
int capacity = SmallOrderedHashSet::kMinCapacity;
Factory* factory = isolate->factory();
while (capacity <= SmallOrderedHashSet::kMaxCapacity) {
Handle<SmallOrderedHashSet> expected =
factory->NewSmallOrderedHashSet(capacity);
Handle<Object> result_raw =
ft.Call(Handle<Smi>(Smi::FromInt(capacity), isolate)).ToHandleChecked();
Handle<SmallOrderedHashSet> actual = Handle<SmallOrderedHashSet>(
SmallOrderedHashSet::cast(*result_raw), isolate);
CHECK_EQ(capacity, actual->Capacity());
CHECK_EQ(0, actual->NumberOfElements());
CHECK_EQ(0, actual->NumberOfDeletedElements());
CHECK_EQ(capacity / SmallOrderedHashSet::kLoadFactor,
actual->NumberOfBuckets());
CHECK(memcmp(*expected, *actual, SmallOrderedHashSet::SizeFor(capacity)));
#ifdef VERIFY_HEAP
actual->SmallOrderedHashTableVerify(isolate);
#endif
capacity = capacity << 1;
}
#ifdef VERIFY_HEAP
isolate->heap()->Verify();
#endif
}
TEST(IsDoubleElementsKind) { TEST(IsDoubleElementsKind) {
Isolate* isolate(CcTest::InitIsolateOnce()); Isolate* isolate(CcTest::InitIsolateOnce());
const int kNumParams = 2; const int kNumParams = 2;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment