| Index: src/objects-inl.h
|
| diff --git a/src/objects-inl.h b/src/objects-inl.h
|
| index 4a4b896381066414008ebf673f2672a0abcdd00e..b1808be3c405f3a475d12fa074f32d28f6b5cf43 100644
|
| --- a/src/objects-inl.h
|
| +++ b/src/objects-inl.h
|
| @@ -142,8 +142,8 @@
|
|
|
|
|
| bool Object::IsFixedArrayBase() const {
|
| - return IsFixedArray() || IsFixedDoubleArray() || IsFixedTypedArrayBase() ||
|
| - IsExternalArray();
|
| + return IsFixedArray() || IsFixedDoubleArray() || IsConstantPoolArray() ||
|
| + IsFixedTypedArrayBase() || IsExternalArray();
|
| }
|
|
|
|
|
| @@ -718,6 +718,7 @@
|
| TYPE_CHECKER(FixedArray, FIXED_ARRAY_TYPE)
|
| TYPE_CHECKER(FixedDoubleArray, FIXED_DOUBLE_ARRAY_TYPE)
|
| TYPE_CHECKER(WeakFixedArray, FIXED_ARRAY_TYPE)
|
| +TYPE_CHECKER(ConstantPoolArray, CONSTANT_POOL_ARRAY_TYPE)
|
|
|
|
|
| bool Object::IsJSWeakCollection() const {
|
| @@ -1535,6 +1536,8 @@
|
| // map-word).
|
| return ((type & kIsIndirectStringMask) != kIsIndirectStringTag);
|
| }
|
| + // The ConstantPoolArray contains heap pointers, but also raw values.
|
| + if (type == CONSTANT_POOL_ARRAY_TYPE) return true;
|
| return (type <= LAST_DATA_TYPE);
|
| }
|
|
|
| @@ -2417,6 +2420,387 @@
|
| }
|
|
|
|
|
| +void ConstantPoolArray::NumberOfEntries::increment(Type type) {
|
| + DCHECK(type < NUMBER_OF_TYPES);
|
| + element_counts_[type]++;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::NumberOfEntries::equals(
|
| + const ConstantPoolArray::NumberOfEntries& other) const {
|
| + for (int i = 0; i < NUMBER_OF_TYPES; i++) {
|
| + if (element_counts_[i] != other.element_counts_[i]) return false;
|
| + }
|
| + return true;
|
| +}
|
| +
|
| +
|
| +bool ConstantPoolArray::NumberOfEntries::is_empty() const {
|
| + return total_count() == 0;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::NumberOfEntries::count_of(Type type) const {
|
| + DCHECK(type < NUMBER_OF_TYPES);
|
| + return element_counts_[type];
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::NumberOfEntries::base_of(Type type) const {
|
| + int base = 0;
|
| + DCHECK(type < NUMBER_OF_TYPES);
|
| + for (int i = 0; i < type; i++) {
|
| + base += element_counts_[i];
|
| + }
|
| + return base;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::NumberOfEntries::total_count() const {
|
| + int count = 0;
|
| + for (int i = 0; i < NUMBER_OF_TYPES; i++) {
|
| + count += element_counts_[i];
|
| + }
|
| + return count;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::NumberOfEntries::are_in_range(int min, int max) const {
|
| + for (int i = FIRST_TYPE; i < NUMBER_OF_TYPES; i++) {
|
| + if (element_counts_[i] < min || element_counts_[i] > max) {
|
| + return false;
|
| + }
|
| + }
|
| + return true;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::Iterator::next_index() {
|
| + DCHECK(!is_finished());
|
| + int ret = next_index_++;
|
| + update_section();
|
| + return ret;
|
| +}
|
| +
|
| +
|
| +bool ConstantPoolArray::Iterator::is_finished() {
|
| + return next_index_ > array_->last_index(type_, final_section_);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::Iterator::update_section() {
|
| + if (next_index_ > array_->last_index(type_, current_section_) &&
|
| + current_section_ != final_section_) {
|
| + DCHECK(final_section_ == EXTENDED_SECTION);
|
| + current_section_ = EXTENDED_SECTION;
|
| + next_index_ = array_->first_index(type_, EXTENDED_SECTION);
|
| + }
|
| +}
|
| +
|
| +
|
| +bool ConstantPoolArray::is_extended_layout() {
|
| + uint32_t small_layout_1 = READ_UINT32_FIELD(this, kSmallLayout1Offset);
|
| + return IsExtendedField::decode(small_layout_1);
|
| +}
|
| +
|
| +
|
| +ConstantPoolArray::LayoutSection ConstantPoolArray::final_section() {
|
| + return is_extended_layout() ? EXTENDED_SECTION : SMALL_SECTION;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::first_extended_section_index() {
|
| + DCHECK(is_extended_layout());
|
| + uint32_t small_layout_2 = READ_UINT32_FIELD(this, kSmallLayout2Offset);
|
| + return TotalCountField::decode(small_layout_2);
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::get_extended_section_header_offset() {
|
| + return RoundUp(SizeFor(NumberOfEntries(this, SMALL_SECTION)), kInt64Size);
|
| +}
|
| +
|
| +
|
| +ConstantPoolArray::WeakObjectState ConstantPoolArray::get_weak_object_state() {
|
| + uint32_t small_layout_2 = READ_UINT32_FIELD(this, kSmallLayout2Offset);
|
| + return WeakObjectStateField::decode(small_layout_2);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set_weak_object_state(
|
| + ConstantPoolArray::WeakObjectState state) {
|
| + uint32_t small_layout_2 = READ_UINT32_FIELD(this, kSmallLayout2Offset);
|
| + small_layout_2 = WeakObjectStateField::update(small_layout_2, state);
|
| + WRITE_INT32_FIELD(this, kSmallLayout2Offset, small_layout_2);
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::first_index(Type type, LayoutSection section) {
|
| + int index = 0;
|
| + if (section == EXTENDED_SECTION) {
|
| + DCHECK(is_extended_layout());
|
| + index += first_extended_section_index();
|
| + }
|
| +
|
| + for (Type type_iter = FIRST_TYPE; type_iter < type;
|
| + type_iter = next_type(type_iter)) {
|
| + index += number_of_entries(type_iter, section);
|
| + }
|
| +
|
| + return index;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::last_index(Type type, LayoutSection section) {
|
| + return first_index(type, section) + number_of_entries(type, section) - 1;
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::number_of_entries(Type type, LayoutSection section) {
|
| + if (section == SMALL_SECTION) {
|
| + uint32_t small_layout_1 = READ_UINT32_FIELD(this, kSmallLayout1Offset);
|
| + uint32_t small_layout_2 = READ_UINT32_FIELD(this, kSmallLayout2Offset);
|
| + switch (type) {
|
| + case INT64:
|
| + return Int64CountField::decode(small_layout_1);
|
| + case CODE_PTR:
|
| + return CodePtrCountField::decode(small_layout_1);
|
| + case HEAP_PTR:
|
| + return HeapPtrCountField::decode(small_layout_1);
|
| + case INT32:
|
| + return Int32CountField::decode(small_layout_2);
|
| + default:
|
| + UNREACHABLE();
|
| + return 0;
|
| + }
|
| + } else {
|
| + DCHECK(section == EXTENDED_SECTION && is_extended_layout());
|
| + int offset = get_extended_section_header_offset();
|
| + switch (type) {
|
| + case INT64:
|
| + offset += kExtendedInt64CountOffset;
|
| + break;
|
| + case CODE_PTR:
|
| + offset += kExtendedCodePtrCountOffset;
|
| + break;
|
| + case HEAP_PTR:
|
| + offset += kExtendedHeapPtrCountOffset;
|
| + break;
|
| + case INT32:
|
| + offset += kExtendedInt32CountOffset;
|
| + break;
|
| + default:
|
| + UNREACHABLE();
|
| + }
|
| + return READ_INT_FIELD(this, offset);
|
| + }
|
| +}
|
| +
|
| +
|
| +bool ConstantPoolArray::offset_is_type(int offset, Type type) {
|
| + return (offset >= OffsetOfElementAt(first_index(type, SMALL_SECTION)) &&
|
| + offset <= OffsetOfElementAt(last_index(type, SMALL_SECTION))) ||
|
| + (is_extended_layout() &&
|
| + offset >= OffsetOfElementAt(first_index(type, EXTENDED_SECTION)) &&
|
| + offset <= OffsetOfElementAt(last_index(type, EXTENDED_SECTION)));
|
| +}
|
| +
|
| +
|
| +ConstantPoolArray::Type ConstantPoolArray::get_type(int index) {
|
| + LayoutSection section;
|
| + if (is_extended_layout() && index >= first_extended_section_index()) {
|
| + section = EXTENDED_SECTION;
|
| + } else {
|
| + section = SMALL_SECTION;
|
| + }
|
| +
|
| + Type type = FIRST_TYPE;
|
| + while (index > last_index(type, section)) {
|
| + type = next_type(type);
|
| + }
|
| + DCHECK(type <= LAST_TYPE);
|
| + return type;
|
| +}
|
| +
|
| +
|
| +int64_t ConstantPoolArray::get_int64_entry(int index) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == INT64);
|
| + return READ_INT64_FIELD(this, OffsetOfElementAt(index));
|
| +}
|
| +
|
| +
|
| +double ConstantPoolArray::get_int64_entry_as_double(int index) {
|
| + STATIC_ASSERT(kDoubleSize == kInt64Size);
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == INT64);
|
| + return READ_DOUBLE_FIELD(this, OffsetOfElementAt(index));
|
| +}
|
| +
|
| +
|
| +Address ConstantPoolArray::get_code_ptr_entry(int index) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == CODE_PTR);
|
| + return reinterpret_cast<Address>(READ_FIELD(this, OffsetOfElementAt(index)));
|
| +}
|
| +
|
| +
|
| +Object* ConstantPoolArray::get_heap_ptr_entry(int index) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == HEAP_PTR);
|
| + return READ_FIELD(this, OffsetOfElementAt(index));
|
| +}
|
| +
|
| +
|
| +int32_t ConstantPoolArray::get_int32_entry(int index) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == INT32);
|
| + return READ_INT32_FIELD(this, OffsetOfElementAt(index));
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set(int index, int64_t value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == INT64);
|
| + WRITE_INT64_FIELD(this, OffsetOfElementAt(index), value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set(int index, double value) {
|
| + STATIC_ASSERT(kDoubleSize == kInt64Size);
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == INT64);
|
| + WRITE_DOUBLE_FIELD(this, OffsetOfElementAt(index), value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set(int index, Address value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == CODE_PTR);
|
| + WRITE_FIELD(this, OffsetOfElementAt(index), reinterpret_cast<Object*>(value));
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set(int index, Object* value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(!GetHeap()->InNewSpace(value));
|
| + DCHECK(get_type(index) == HEAP_PTR);
|
| + WRITE_FIELD(this, OffsetOfElementAt(index), value);
|
| + WRITE_BARRIER(GetHeap(), this, OffsetOfElementAt(index), value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set(int index, int32_t value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(get_type(index) == INT32);
|
| + WRITE_INT32_FIELD(this, OffsetOfElementAt(index), value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set_at_offset(int offset, int32_t value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(offset_is_type(offset, INT32));
|
| + WRITE_INT32_FIELD(this, offset, value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set_at_offset(int offset, int64_t value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(offset_is_type(offset, INT64));
|
| + WRITE_INT64_FIELD(this, offset, value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set_at_offset(int offset, double value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(offset_is_type(offset, INT64));
|
| + WRITE_DOUBLE_FIELD(this, offset, value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set_at_offset(int offset, Address value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(offset_is_type(offset, CODE_PTR));
|
| + WRITE_FIELD(this, offset, reinterpret_cast<Object*>(value));
|
| + WRITE_BARRIER(GetHeap(), this, offset, reinterpret_cast<Object*>(value));
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::set_at_offset(int offset, Object* value) {
|
| + DCHECK(map() == GetHeap()->constant_pool_array_map());
|
| + DCHECK(!GetHeap()->InNewSpace(value));
|
| + DCHECK(offset_is_type(offset, HEAP_PTR));
|
| + WRITE_FIELD(this, offset, value);
|
| + WRITE_BARRIER(GetHeap(), this, offset, value);
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::Init(const NumberOfEntries& small) {
|
| + uint32_t small_layout_1 =
|
| + Int64CountField::encode(small.count_of(INT64)) |
|
| + CodePtrCountField::encode(small.count_of(CODE_PTR)) |
|
| + HeapPtrCountField::encode(small.count_of(HEAP_PTR)) |
|
| + IsExtendedField::encode(false);
|
| + uint32_t small_layout_2 =
|
| + Int32CountField::encode(small.count_of(INT32)) |
|
| + TotalCountField::encode(small.total_count()) |
|
| + WeakObjectStateField::encode(NO_WEAK_OBJECTS);
|
| + WRITE_UINT32_FIELD(this, kSmallLayout1Offset, small_layout_1);
|
| + WRITE_UINT32_FIELD(this, kSmallLayout2Offset, small_layout_2);
|
| + if (kHeaderSize != kFirstEntryOffset) {
|
| + DCHECK(kFirstEntryOffset - kHeaderSize == kInt32Size);
|
| + WRITE_UINT32_FIELD(this, kHeaderSize, 0); // Zero out header padding.
|
| + }
|
| +}
|
| +
|
| +
|
| +void ConstantPoolArray::InitExtended(const NumberOfEntries& small,
|
| + const NumberOfEntries& extended) {
|
| + // Initialize small layout fields first.
|
| + Init(small);
|
| +
|
| + // Set is_extended_layout field.
|
| + uint32_t small_layout_1 = READ_UINT32_FIELD(this, kSmallLayout1Offset);
|
| + small_layout_1 = IsExtendedField::update(small_layout_1, true);
|
| + WRITE_INT32_FIELD(this, kSmallLayout1Offset, small_layout_1);
|
| +
|
| + // Initialize the extended layout fields.
|
| + int extended_header_offset = get_extended_section_header_offset();
|
| + WRITE_INT32_FIELD(this, extended_header_offset + kExtendedInt64CountOffset,
|
| + extended.count_of(INT64));
|
| + WRITE_INT32_FIELD(this, extended_header_offset + kExtendedCodePtrCountOffset,
|
| + extended.count_of(CODE_PTR));
|
| + WRITE_INT32_FIELD(this, extended_header_offset + kExtendedHeapPtrCountOffset,
|
| + extended.count_of(HEAP_PTR));
|
| + WRITE_INT32_FIELD(this, extended_header_offset + kExtendedInt32CountOffset,
|
| + extended.count_of(INT32));
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::size() {
|
| + NumberOfEntries small(this, SMALL_SECTION);
|
| + if (!is_extended_layout()) {
|
| + return SizeFor(small);
|
| + } else {
|
| + NumberOfEntries extended(this, EXTENDED_SECTION);
|
| + return SizeForExtended(small, extended);
|
| + }
|
| +}
|
| +
|
| +
|
| +int ConstantPoolArray::length() {
|
| + uint32_t small_layout_2 = READ_UINT32_FIELD(this, kSmallLayout2Offset);
|
| + int length = TotalCountField::decode(small_layout_2);
|
| + if (is_extended_layout()) {
|
| + length += number_of_entries(INT64, EXTENDED_SECTION) +
|
| + number_of_entries(CODE_PTR, EXTENDED_SECTION) +
|
| + number_of_entries(HEAP_PTR, EXTENDED_SECTION) +
|
| + number_of_entries(INT32, EXTENDED_SECTION);
|
| + }
|
| + return length;
|
| +}
|
| +
|
| +
|
| WriteBarrierMode HeapObject::GetWriteBarrierMode(
|
| const DisallowHeapAllocation& promise) {
|
| Heap* heap = GetHeap();
|
| @@ -2428,7 +2812,8 @@
|
|
|
| AllocationAlignment HeapObject::RequiredAlignment() {
|
| #ifdef V8_HOST_ARCH_32_BIT
|
| - if ((IsFixedFloat64Array() || IsFixedDoubleArray()) &&
|
| + if ((IsFixedFloat64Array() || IsFixedDoubleArray() ||
|
| + IsConstantPoolArray()) &&
|
| FixedArrayBase::cast(this)->length() != 0) {
|
| return kDoubleAligned;
|
| }
|
| @@ -2952,6 +3337,7 @@
|
| CAST_ACCESSOR(CodeCacheHashTable)
|
| CAST_ACCESSOR(CompilationCacheTable)
|
| CAST_ACCESSOR(ConsString)
|
| +CAST_ACCESSOR(ConstantPoolArray)
|
| CAST_ACCESSOR(DeoptimizationInputData)
|
| CAST_ACCESSOR(DeoptimizationOutputData)
|
| CAST_ACCESSOR(DependentCode)
|
| @@ -4141,6 +4527,9 @@
|
| return FixedDoubleArray::SizeFor(
|
| reinterpret_cast<FixedDoubleArray*>(this)->length());
|
| }
|
| + if (instance_type == CONSTANT_POOL_ARRAY_TYPE) {
|
| + return reinterpret_cast<ConstantPoolArray*>(this)->size();
|
| + }
|
| if (instance_type >= FIRST_FIXED_TYPED_ARRAY_TYPE &&
|
| instance_type <= LAST_FIXED_TYPED_ARRAY_TYPE) {
|
| return reinterpret_cast<FixedTypedArrayBase*>(
|
| @@ -4743,15 +5132,15 @@
|
| }
|
|
|
|
|
| -Address Code::constant_pool() {
|
| - Address constant_pool = NULL;
|
| - if (FLAG_enable_embedded_constant_pool) {
|
| - int offset = constant_pool_offset();
|
| - if (offset < instruction_size()) {
|
| - constant_pool = FIELD_ADDR(this, kHeaderSize + offset);
|
| - }
|
| - }
|
| - return constant_pool;
|
| +ConstantPoolArray* Code::constant_pool() {
|
| + return ConstantPoolArray::cast(READ_FIELD(this, kConstantPoolOffset));
|
| +}
|
| +
|
| +
|
| +void Code::set_constant_pool(Object* value) {
|
| + DCHECK(value->IsConstantPoolArray());
|
| + WRITE_FIELD(this, kConstantPoolOffset, value);
|
| + WRITE_BARRIER(GetHeap(), this, kConstantPoolOffset, value);
|
| }
|
|
|
|
|
| @@ -5929,7 +6318,6 @@
|
|
|
| INT_ACCESSORS(Code, instruction_size, kInstructionSizeOffset)
|
| INT_ACCESSORS(Code, prologue_offset, kPrologueOffset)
|
| -INT_ACCESSORS(Code, constant_pool_offset, kConstantPoolOffset)
|
| ACCESSORS(Code, relocation_info, ByteArray, kRelocationInfoOffset)
|
| ACCESSORS(Code, handler_table, FixedArray, kHandlerTableOffset)
|
| ACCESSORS(Code, deoptimization_data, FixedArray, kDeoptimizationDataOffset)
|
| @@ -5941,6 +6329,7 @@
|
| WRITE_FIELD(this, kRelocationInfoOffset, NULL);
|
| WRITE_FIELD(this, kHandlerTableOffset, NULL);
|
| WRITE_FIELD(this, kDeoptimizationDataOffset, NULL);
|
| + WRITE_FIELD(this, kConstantPoolOffset, NULL);
|
| // Do not wipe out major/minor keys on a code stub or IC
|
| if (!READ_FIELD(this, kTypeFeedbackInfoOffset)->IsSmi()) {
|
| WRITE_FIELD(this, kTypeFeedbackInfoOffset, NULL);
|
|
|