[ptr-compr] Make IsolateData be the bottleneck for root-relative accesses

Bug: v8:8182
Change-Id: I4dadd9cab071ecd4314c370be5f444e36acb708e
Reviewed-on: https://chromium-review.googlesource.com/c/1297317
Reviewed-by: Jakob Gruber <jgruber@chromium.org>
Reviewed-by: Jaroslav Sevcik <jarin@chromium.org>
Reviewed-by: Michael Starzinger <mstarzinger@chromium.org>
Commit-Queue: Igor Sheludko <ishell@chromium.org>
Cr-Commit-Position: refs/heads/master@{#56973}
This commit is contained in:
Igor Sheludko 2018-10-25 00:52:04 +02:00 committed by Commit Bot
parent 339bb225c8
commit 0e09760881
30 changed files with 184 additions and 149 deletions

View File

@ -1905,6 +1905,7 @@ v8_source_set("v8_base") {
"src/compiler/zone-stats.h", "src/compiler/zone-stats.h",
"src/constant-pool.cc", "src/constant-pool.cc",
"src/constant-pool.h", "src/constant-pool.h",
"src/constants-arch.h",
"src/contexts-inl.h", "src/contexts-inl.h",
"src/contexts.cc", "src/contexts.cc",
"src/contexts.h", "src/contexts.h",

View File

@ -1912,10 +1912,8 @@ void MacroAssembler::LoadNativeContextSlot(int index, Register dst) {
void TurboAssembler::InitializeRootRegister() { void TurboAssembler::InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); mov(kRootRegister, Operand(isolate_root));
mov(kRootRegister, Operand(roots_array_start));
add(kRootRegister, kRootRegister, Operand(kRootRegisterBias));
} }
void MacroAssembler::SmiTag(Register reg, SBit s) { void MacroAssembler::SmiTag(Register reg, SBit s) {

View File

@ -1021,10 +1021,8 @@ void TurboAssembler::Uxtw(const Register& rd, const Register& rn) {
} }
void TurboAssembler::InitializeRootRegister() { void TurboAssembler::InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); Mov(kRootRegister, Operand(isolate_root));
Mov(kRootRegister, Operand(roots_array_start));
Add(kRootRegister, kRootRegister, kRootRegisterBias);
} }

View File

@ -23,13 +23,13 @@ class WasmBuiltinsAssembler : public CodeStubAssembler {
TNode<Code> LoadBuiltinFromFrame(Builtins::Name id) { TNode<Code> LoadBuiltinFromFrame(Builtins::Name id) {
TNode<Object> instance = LoadInstanceFromFrame(); TNode<Object> instance = LoadInstanceFromFrame();
TNode<IntPtrT> roots = UncheckedCast<IntPtrT>( TNode<IntPtrT> isolate_root = UncheckedCast<IntPtrT>(
Load(MachineType::Pointer(), instance, Load(MachineType::Pointer(), instance,
IntPtrConstant(WasmInstanceObject::kRootsArrayAddressOffset - IntPtrConstant(WasmInstanceObject::kIsolateRootOffset -
kHeapObjectTag))); kHeapObjectTag)));
TNode<Code> target = UncheckedCast<Code>(Load( TNode<Code> target = UncheckedCast<Code>(
MachineType::TaggedPointer(), roots, Load(MachineType::TaggedPointer(), isolate_root,
IntPtrConstant(IsolateData::kBuiltinsTableOffset + id * kPointerSize))); IntPtrConstant(IsolateData::builtin_slot_offset(id))));
return target; return target;
} }

View File

@ -1459,18 +1459,18 @@ TNode<IntPtrT> CodeStubAssembler::LoadAndUntagSmi(Node* base, int index) {
TNode<Int32T> CodeStubAssembler::LoadAndUntagToWord32Root( TNode<Int32T> CodeStubAssembler::LoadAndUntagToWord32Root(
RootIndex root_index) { RootIndex root_index) {
Node* roots_array_start = Node* isolate_root =
ExternalConstant(ExternalReference::roots_array_start(isolate())); ExternalConstant(ExternalReference::isolate_root(isolate()));
int offset = static_cast<int>(root_index) * kPointerSize; int offset = IsolateData::root_slot_offset(root_index);
if (SmiValuesAre32Bits()) { if (SmiValuesAre32Bits()) {
#if V8_TARGET_LITTLE_ENDIAN #if V8_TARGET_LITTLE_ENDIAN
offset += kPointerSize / 2; offset += kPointerSize / 2;
#endif #endif
return UncheckedCast<Int32T>( return UncheckedCast<Int32T>(
Load(MachineType::Int32(), roots_array_start, IntPtrConstant(offset))); Load(MachineType::Int32(), isolate_root, IntPtrConstant(offset)));
} else { } else {
return SmiToInt32(Load(MachineType::AnyTagged(), roots_array_start, return SmiToInt32(
IntPtrConstant(offset))); Load(MachineType::AnyTagged(), isolate_root, IntPtrConstant(offset)));
} }
} }

View File

@ -994,11 +994,11 @@ TNode<Object> CodeAssembler::LoadRoot(RootIndex root_index) {
// TODO(jgruber): In theory we could generate better code for this by // TODO(jgruber): In theory we could generate better code for this by
// letting the macro assembler decide how to load from the roots list. In most // letting the macro assembler decide how to load from the roots list. In most
// cases, it would boil down to loading from a fixed kRootRegister offset. // cases, it would boil down to loading from a fixed kRootRegister offset.
Node* roots_array_start = Node* isolate_root =
ExternalConstant(ExternalReference::roots_array_start(isolate())); ExternalConstant(ExternalReference::isolate_root(isolate()));
size_t offset = static_cast<size_t>(root_index) * kPointerSize; int offset = IsolateData::root_slot_offset(root_index);
return UncheckedCast<Object>(Load(MachineType::AnyTagged(), roots_array_start, return UncheckedCast<Object>(
IntPtrConstant(offset))); Load(MachineType::AnyTagged(), isolate_root, IntPtrConstant(offset)));
} }
Node* CodeAssembler::Store(Node* base, Node* value) { Node* CodeAssembler::Store(Node* base, Node* value) {
@ -1058,10 +1058,10 @@ Node* CodeAssembler::AtomicCompareExchange(MachineType type, Node* base,
Node* CodeAssembler::StoreRoot(RootIndex root_index, Node* value) { Node* CodeAssembler::StoreRoot(RootIndex root_index, Node* value) {
DCHECK(!RootsTable::IsImmortalImmovable(root_index)); DCHECK(!RootsTable::IsImmortalImmovable(root_index));
Node* roots_array_start = Node* isolate_root =
ExternalConstant(ExternalReference::roots_array_start(isolate())); ExternalConstant(ExternalReference::isolate_root(isolate()));
size_t offset = static_cast<size_t>(root_index) * kPointerSize; int offset = IsolateData::root_slot_offset(root_index);
return StoreNoWriteBarrier(MachineRepresentation::kTagged, roots_array_start, return StoreNoWriteBarrier(MachineRepresentation::kTagged, isolate_root,
IntPtrConstant(offset), value); IntPtrConstant(offset), value);
} }

View File

@ -682,8 +682,7 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
__ push(eax); __ push(eax);
frame_access_state()->IncreaseSPDelta(1); frame_access_state()->IncreaseSPDelta(1);
Operand virtual_call_target_register( Operand virtual_call_target_register(
kRootRegister, kRootRegister, IsolateData::virtual_call_target_register_offset());
IsolateData::kVirtualCallTargetRegisterOffset - kRootRegisterBias);
__ mov(eax, i.InputOperand(0)); __ mov(eax, i.InputOperand(0));
__ add(eax, Immediate(Code::kHeaderSize - kHeapObjectTag)); __ add(eax, Immediate(Code::kHeaderSize - kHeapObjectTag));
__ mov(virtual_call_target_register, eax); __ mov(virtual_call_target_register, eax);

View File

@ -2998,10 +2998,10 @@ Node* WasmGraphBuilder::CurrentMemoryPages() {
Node* WasmGraphBuilder::BuildLoadBuiltinFromInstance(int builtin_index) { Node* WasmGraphBuilder::BuildLoadBuiltinFromInstance(int builtin_index) {
DCHECK(Builtins::IsBuiltinId(builtin_index)); DCHECK(Builtins::IsBuiltinId(builtin_index));
Node* roots = Node* isolate_root =
LOAD_INSTANCE_FIELD(RootsArrayAddress, MachineType::TaggedPointer()); LOAD_INSTANCE_FIELD(IsolateRoot, MachineType::TaggedPointer());
return LOAD_TAGGED_POINTER( return LOAD_TAGGED_POINTER(isolate_root,
roots, IsolateData::kBuiltinsTableOffset + builtin_index * kPointerSize); IsolateData::builtin_slot_offset(builtin_index));
} }
// Only call this function for code which is not reused across instantiations, // Only call this function for code which is not reused across instantiations,

28
src/constants-arch.h Normal file
View File

@ -0,0 +1,28 @@
// Copyright 2018 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef V8_CONSTANTS_ARCH_H_
#define V8_CONSTANTS_ARCH_H_
#if V8_TARGET_ARCH_ARM
#include "src/arm/constants-arm.h" // NOLINT
#elif V8_TARGET_ARCH_ARM64
#include "src/arm64/constants-arm64.h" // NOLINT
#elif V8_TARGET_ARCH_IA32
#include "src/ia32/constants-ia32.h" // NOLINT
#elif V8_TARGET_ARCH_MIPS
#include "src/mips/constants-mips.h" // NOLINT
#elif V8_TARGET_ARCH_MIPS64
#include "src/mips64/constants-mips64.h" // NOLINT
#elif V8_TARGET_ARCH_PPC
#include "src/ppc/constants-ppc.h" // NOLINT
#elif V8_TARGET_ARCH_S390
#include "src/s390/constants-s390.h" // NOLINT
#elif V8_TARGET_ARCH_X64
#include "src/x64/constants-x64.h" // NOLINT
#else
#error Unsupported target architecture.
#endif
#endif // V8_CONSTANTS_ARCH_H_

View File

@ -815,12 +815,9 @@ void Deoptimizer::DoComputeOutputFrames() {
constexpr bool kShouldInitializeRootRegister = true; constexpr bool kShouldInitializeRootRegister = true;
#endif #endif
if (kShouldInitializeRootRegister) { if (kShouldInitializeRootRegister) {
Address root_pointer =
reinterpret_cast<Address>(isolate()->roots_array_start()) +
kRootRegisterBias;
FrameDescription* topmost = output_[count - 1]; FrameDescription* topmost = output_[count - 1];
topmost->GetRegisterValues()->SetRegister(kRootRegister.code(), topmost->GetRegisterValues()->SetRegister(kRootRegister.code(),
root_pointer); isolate()->isolate_root());
} }
// Print some helpful diagnostic information. // Print some helpful diagnostic information.

View File

@ -24,8 +24,8 @@ class NameConverter {
virtual const char* NameOfConstant(byte* addr) const; virtual const char* NameOfConstant(byte* addr) const;
virtual const char* NameInCode(byte* addr) const; virtual const char* NameInCode(byte* addr) const;
// Given a root-relative offset, returns either a name or nullptr if none is // Given a root-register-relative offset, returns either a name or nullptr if
// found. // none is found.
// TODO(jgruber,v8:7989): This is a temporary solution until we can preserve // TODO(jgruber,v8:7989): This is a temporary solution until we can preserve
// code comments through snapshotting. // code comments through snapshotting.
virtual const char* RootRelativeName(int offset) const { UNREACHABLE(); } virtual const char* RootRelativeName(int offset) const { UNREACHABLE(); }

View File

@ -61,13 +61,12 @@ void V8NameConverter::InitExternalRefsCache() const {
base::AddressRegion addressable_region = base::AddressRegion addressable_region =
isolate_->root_register_addressable_region(); isolate_->root_register_addressable_region();
Address roots_start = Address isolate_root = isolate_->isolate_root();
reinterpret_cast<Address>(isolate_->roots_array_start());
for (uint32_t i = 0; i < external_reference_table->size(); i++) { for (uint32_t i = 0; i < external_reference_table->size(); i++) {
Address address = external_reference_table->address(i); Address address = external_reference_table->address(i);
if (addressable_region.contains(address)) { if (addressable_region.contains(address)) {
int offset = static_cast<int>(address - roots_start); int offset = static_cast<int>(address - isolate_root);
const char* name = external_reference_table->name(i); const char* name = external_reference_table->name(i);
directly_accessed_external_refs_.insert({offset, name}); directly_accessed_external_refs_.insert({offset, name});
} }
@ -117,15 +116,15 @@ const char* V8NameConverter::NameInCode(byte* addr) const {
const char* V8NameConverter::RootRelativeName(int offset) const { const char* V8NameConverter::RootRelativeName(int offset) const {
if (isolate_ == nullptr) return nullptr; if (isolate_ == nullptr) return nullptr;
const int kRootsStart = IsolateData::kRootsTableOffset; const int kRootsTableStart = IsolateData::roots_table_offset();
const int kRootsEnd = IsolateData::kRootsTableEndOffset; const unsigned kRootsTableSize = sizeof(RootsTable);
const int kExtRefsStart = IsolateData::kExternalReferenceTableOffset; const int kExtRefsTableStart = IsolateData::external_reference_table_offset();
const int kExtRefsEnd = IsolateData::kExternalReferenceTableEndOffset; const unsigned kExtRefsTableSize = ExternalReferenceTable::SizeInBytes();
const int kBuiltinsStart = IsolateData::kBuiltinsTableOffset; const int kBuiltinsTableStart = IsolateData::builtins_table_offset();
const int kBuiltinsEnd = IsolateData::kBuiltinsTableEndOffset; const unsigned kBuiltinsTableSize = Builtins::builtin_count * kPointerSize;
if (kRootsStart <= offset && offset < kRootsEnd) { if (static_cast<unsigned>(offset - kRootsTableStart) < kRootsTableSize) {
uint32_t offset_in_roots_table = offset - kRootsStart; uint32_t offset_in_roots_table = offset - kRootsTableStart;
// Fail safe in the unlikely case of an arbitrary root-relative offset. // Fail safe in the unlikely case of an arbitrary root-relative offset.
if (offset_in_roots_table % kPointerSize != 0) return nullptr; if (offset_in_roots_table % kPointerSize != 0) return nullptr;
@ -141,8 +140,9 @@ const char* V8NameConverter::RootRelativeName(int offset) const {
SNPrintF(v8_buffer_, "root (%s)", obj_name.get()); SNPrintF(v8_buffer_, "root (%s)", obj_name.get());
return v8_buffer_.start(); return v8_buffer_.start();
} else if (kExtRefsStart <= offset && offset < kExtRefsEnd) { } else if (static_cast<unsigned>(offset - kExtRefsTableStart) <
uint32_t offset_in_extref_table = offset - kExtRefsStart; kExtRefsTableSize) {
uint32_t offset_in_extref_table = offset - kExtRefsTableStart;
// Fail safe in the unlikely case of an arbitrary root-relative offset. // Fail safe in the unlikely case of an arbitrary root-relative offset.
if (offset_in_extref_table % ExternalReferenceTable::EntrySize() != 0) { if (offset_in_extref_table % ExternalReferenceTable::EntrySize() != 0) {
@ -159,8 +159,9 @@ const char* V8NameConverter::RootRelativeName(int offset) const {
offset_in_extref_table)); offset_in_extref_table));
return v8_buffer_.start(); return v8_buffer_.start();
} else if (kBuiltinsStart <= offset && offset < kBuiltinsEnd) { } else if (static_cast<unsigned>(offset - kBuiltinsTableStart) <
uint32_t offset_in_builtins_table = (offset - kBuiltinsStart); kBuiltinsTableSize) {
uint32_t offset_in_builtins_table = (offset - kBuiltinsTableStart);
Builtins::Name builtin_id = Builtins::Name builtin_id =
static_cast<Builtins::Name>(offset_in_builtins_table / kPointerSize); static_cast<Builtins::Name>(offset_in_builtins_table / kPointerSize);

View File

@ -383,8 +383,8 @@ ExternalReference ExternalReference::log_leave_external_function() {
return ExternalReference(Redirect(FUNCTION_ADDR(Logger::LeaveExternal))); return ExternalReference(Redirect(FUNCTION_ADDR(Logger::LeaveExternal)));
} }
ExternalReference ExternalReference::roots_array_start(Isolate* isolate) { ExternalReference ExternalReference::isolate_root(Isolate* isolate) {
return ExternalReference(isolate->roots_array_start()); return ExternalReference(isolate->isolate_root());
} }
ExternalReference ExternalReference::allocation_sites_list_address( ExternalReference ExternalReference::allocation_sites_list_address(

View File

@ -32,7 +32,7 @@ class StatsCounter;
V(date_cache_stamp, "date_cache_stamp") \ V(date_cache_stamp, "date_cache_stamp") \
V(stress_deopt_count, "Isolate::stress_deopt_count_address()") \ V(stress_deopt_count, "Isolate::stress_deopt_count_address()") \
V(force_slow_path, "Isolate::force_slow_path_address()") \ V(force_slow_path, "Isolate::force_slow_path_address()") \
V(roots_array_start, "Heap::roots_array_start()") \ V(isolate_root, "Isolate::isolate_root()") \
V(allocation_sites_list_address, "Heap::allocation_sites_list_address()") \ V(allocation_sites_list_address, "Heap::allocation_sites_list_address()") \
V(address_of_stack_limit, "StackGuard::address_of_jslimit()") \ V(address_of_stack_limit, "StackGuard::address_of_jslimit()") \
V(address_of_real_stack_limit, "StackGuard::address_of_real_jslimit()") \ V(address_of_real_stack_limit, "StackGuard::address_of_real_jslimit()") \

View File

@ -50,10 +50,8 @@ void TurboAssembler::InitializeRootRegister() {
// removed. // removed.
if (!FLAG_embedded_builtins) return; if (!FLAG_embedded_builtins) return;
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); Move(kRootRegister, Immediate(isolate_root));
Move(kRootRegister, Immediate(roots_array_start));
add(kRootRegister, Immediate(kRootRegisterBias));
} }
void TurboAssembler::VerifyRootRegister() { void TurboAssembler::VerifyRootRegister() {
@ -62,8 +60,7 @@ void TurboAssembler::VerifyRootRegister() {
DCHECK(FLAG_embedded_builtins); DCHECK(FLAG_embedded_builtins);
Label root_register_ok; Label root_register_ok;
cmp(Operand(kRootRegister, cmp(Operand(kRootRegister, IsolateData::magic_number_offset()),
IsolateData::kMagicNumberOffset - kRootRegisterBias),
Immediate(IsolateData::kRootRegisterSentinel)); Immediate(IsolateData::kRootRegisterSentinel));
j(equal, &root_register_ok); j(equal, &root_register_ok);
int3(); int3();
@ -89,12 +86,10 @@ void TurboAssembler::LoadRoot(Register destination, RootIndex index) {
return; return;
} }
} }
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate());
mov(destination, Immediate(static_cast<int>(index)));
lea(destination, lea(destination,
Operand(destination, times_pointer_size, roots_array_start.address(), Operand(isolate_root.address(), RelocInfo::EXTERNAL_REFERENCE));
RelocInfo::EXTERNAL_REFERENCE)); mov(destination, Operand(destination, RootRegisterOffsetForRootIndex(index)));
} }
void TurboAssembler::CompareRoot(Register with, Register scratch, void TurboAssembler::CompareRoot(Register with, Register scratch,
@ -105,11 +100,9 @@ void TurboAssembler::CompareRoot(Register with, Register scratch,
return; return;
} }
#endif // V8_EMBEDDED_BUILTINS #endif // V8_EMBEDDED_BUILTINS
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); lea(scratch, Operand(isolate_root.address(), RelocInfo::EXTERNAL_REFERENCE));
mov(scratch, Immediate(static_cast<int>(index))); cmp(with, Operand(scratch, RootRegisterOffsetForRootIndex(index)));
cmp(with, Operand(scratch, times_pointer_size, roots_array_start.address(),
RelocInfo::EXTERNAL_REFERENCE));
} }
void TurboAssembler::CompareRoot(Register with, RootIndex index) { void TurboAssembler::CompareRoot(Register with, RootIndex index) {

View File

@ -6,6 +6,7 @@
#define V8_ISOLATE_DATA_H_ #define V8_ISOLATE_DATA_H_
#include "src/builtins/builtins.h" #include "src/builtins/builtins.h"
#include "src/constants-arch.h"
#include "src/external-reference-table.h" #include "src/external-reference-table.h"
#include "src/roots.h" #include "src/roots.h"
#include "src/utils.h" #include "src/utils.h"
@ -26,26 +27,52 @@ class IsolateData final {
public: public:
IsolateData() = default; IsolateData() = default;
// Layout description. // The value of the kRootRegister.
#define FIELDS(V) \ Address isolate_root() const {
/* roots_ */ \ return reinterpret_cast<Address>(this) + kIsolateRootBias;
V(kRootsTableOffset, RootsTable::kEntriesCount* kPointerSize) \ }
V(kRootsTableEndOffset, 0) \
/* external_reference_table_ */ \
V(kExternalReferenceTableOffset, ExternalReferenceTable::SizeInBytes()) \
V(kExternalReferenceTableEndOffset, 0) \
/* builtins_ */ \
V(kBuiltinsTableOffset, Builtins::builtin_count* kPointerSize) \
V(kBuiltinsTableEndOffset, 0) \
/* magic_number_ */ \
V(kMagicNumberOffset, kIntptrSize) \
/* virtual_call_target_register_ */ \
V(kVirtualCallTargetRegisterOffset, kPointerSize) \
/* Total size. */ \
V(kSize, 0)
DEFINE_FIELD_OFFSET_CONSTANTS(0, FIELDS) // Root-register-relative offset of the roots table.
#undef FIELDS static constexpr int roots_table_offset() {
return kRootsTableOffset - kIsolateRootBias;
}
// Root-register-relative offset of the given root table entry.
static constexpr int root_slot_offset(RootIndex root_index) {
return roots_table_offset() + RootsTable::offset_of(root_index);
}
// Root-register-relative offset of the external reference table.
static constexpr int external_reference_table_offset() {
return kExternalReferenceTableOffset - kIsolateRootBias;
}
// Root-register-relative offset of the builtins table.
static constexpr int builtins_table_offset() {
return kBuiltinsTableOffset - kIsolateRootBias;
}
// Root-register-relative offset of the given builtin table entry.
// TODO(ishell): remove in favour of typified id version.
static int builtin_slot_offset(int builtin_index) {
DCHECK(Builtins::IsBuiltinId(builtin_index));
return builtins_table_offset() + builtin_index * kPointerSize;
}
// Root-register-relative offset of the builtin table entry.
static int builtin_slot_offset(Builtins::Name id) {
return builtins_table_offset() + id * kPointerSize;
}
// Root-register-relative offset of the magic number value.
static constexpr int magic_number_offset() {
return kMagicNumberOffset - kIsolateRootBias;
}
// Root-register-relative offset of the virtual call target register value.
static constexpr int virtual_call_target_register_offset() {
return kVirtualCallTargetRegisterOffset - kIsolateRootBias;
}
// Returns true if this address points to data stored in this instance. // Returns true if this address points to data stored in this instance.
// If it's the case then the value can be accessed indirectly through the // If it's the case then the value can be accessed indirectly through the
@ -70,6 +97,21 @@ class IsolateData final {
static constexpr intptr_t kRootRegisterSentinel = 0xcafeca11; static constexpr intptr_t kRootRegisterSentinel = 0xcafeca11;
private: private:
static constexpr intptr_t kIsolateRootBias = kRootRegisterBias;
// Static layout definition.
#define FIELDS(V) \
V(kRootsTableOffset, RootsTable::kEntriesCount* kPointerSize) \
V(kExternalReferenceTableOffset, ExternalReferenceTable::SizeInBytes()) \
V(kBuiltinsTableOffset, Builtins::builtin_count* kPointerSize) \
V(kMagicNumberOffset, kIntptrSize) \
V(kVirtualCallTargetRegisterOffset, kPointerSize) \
/* Total size. */ \
V(kSize, 0)
DEFINE_FIELD_OFFSET_CONSTANTS(0, FIELDS)
#undef FIELDS
RootsTable roots_; RootsTable roots_;
ExternalReferenceTable external_reference_table_; ExternalReferenceTable external_reference_table_;

View File

@ -1002,10 +1002,12 @@ class Isolate : private HiddenFactory {
const IsolateData* isolate_data() const { return heap_.isolate_data(); } const IsolateData* isolate_data() const { return heap_.isolate_data(); }
IsolateData* isolate_data() { return heap_.isolate_data(); } IsolateData* isolate_data() { return heap_.isolate_data(); }
RootsTable& roots_table() { return isolate_data()->roots(); } // Generated code can embed this address to get access to the isolate-specific
// data (for example, roots, external references, builtins, etc.).
// The kRootRegister is set to this value.
Address isolate_root() const { return isolate_data()->isolate_root(); }
// Generated code can embed this address to get access to the roots. RootsTable& roots_table() { return isolate_data()->roots(); }
Object** roots_array_start() { return roots_table().roots_; }
// kRootRegister may be used to address any location that falls into this // kRootRegister may be used to address any location that falls into this
// region. Fields outside this region are not guaranteed to live at a static // region. Fields outside this region are not guaranteed to live at a static

View File

@ -136,10 +136,8 @@ class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
void Prologue(); void Prologue();
void InitializeRootRegister() { void InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); li(kRootRegister, Operand(isolate_root));
li(kRootRegister, Operand(roots_array_start));
Addu(kRootRegister, kRootRegister, kRootRegisterBias);
} }
// Jump unconditionally to given label. // Jump unconditionally to given label.

View File

@ -158,10 +158,8 @@ class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
void Prologue(); void Prologue();
void InitializeRootRegister() { void InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); li(kRootRegister, Operand(isolate_root));
li(kRootRegister, Operand(roots_array_start));
daddiu(kRootRegister, kRootRegister, kRootRegisterBias);
} }
// Jump unconditionally to given label. // Jump unconditionally to given label.

View File

@ -17,6 +17,7 @@
#include "src/base/flags.h" #include "src/base/flags.h"
#include "src/base/logging.h" #include "src/base/logging.h"
#include "src/checks.h" #include "src/checks.h"
#include "src/constants-arch.h"
#include "src/elements-kind.h" #include "src/elements-kind.h"
#include "src/field-index.h" #include "src/field-index.h"
#include "src/flags.h" #include "src/flags.h"
@ -26,19 +27,6 @@
#include "src/roots.h" #include "src/roots.h"
#include "src/utils.h" #include "src/utils.h"
#if V8_TARGET_ARCH_ARM
#include "src/arm/constants-arm.h" // NOLINT
#elif V8_TARGET_ARCH_ARM64
#include "src/arm64/constants-arm64.h" // NOLINT
#elif V8_TARGET_ARCH_MIPS
#include "src/mips/constants-mips.h" // NOLINT
#elif V8_TARGET_ARCH_MIPS64
#include "src/mips64/constants-mips64.h" // NOLINT
#elif V8_TARGET_ARCH_PPC
#include "src/ppc/constants-ppc.h" // NOLINT
#elif V8_TARGET_ARCH_S390
#include "src/s390/constants-s390.h" // NOLINT
#endif
// Has to be the last include (doesn't have include guards): // Has to be the last include (doesn't have include guards):
#include "src/objects/object-macros.h" #include "src/objects/object-macros.h"

View File

@ -168,10 +168,8 @@ class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
static int ActivationFrameAlignment(); static int ActivationFrameAlignment();
void InitializeRootRegister() { void InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); mov(kRootRegister, Operand(isolate_root));
mov(kRootRegister, Operand(roots_array_start));
addi(kRootRegister, kRootRegister, Operand(kRootRegisterBias));
} }
// These exist to provide portability between 32 and 64bit // These exist to provide portability between 32 and 64bit

View File

@ -420,6 +420,10 @@ class RootsTable {
return root_names_[index]; return root_names_[index];
} }
static constexpr int offset_of(RootIndex root_index) {
return static_cast<int>(root_index) * kPointerSize;
}
static RootIndex RootIndexForFixedTypedArray(ExternalArrayType array_type); static RootIndex RootIndexForFixedTypedArray(ExternalArrayType array_type);
static RootIndex RootIndexForFixedTypedArray(ElementsKind elements_kind); static RootIndex RootIndexForFixedTypedArray(ElementsKind elements_kind);
static RootIndex RootIndexForEmptyFixedTypedArray(ElementsKind elements_kind); static RootIndex RootIndexForEmptyFixedTypedArray(ElementsKind elements_kind);

View File

@ -648,10 +648,8 @@ class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
void RestoreFrameStateForTailCall(); void RestoreFrameStateForTailCall();
void InitializeRootRegister() { void InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); mov(kRootRegister, Operand(isolate_root));
mov(kRootRegister, Operand(roots_array_start));
AddP(kRootRegister, kRootRegister, Operand(kRootRegisterBias));
} }
// If the value is a NaN, canonicalize the value else, do nothing. // If the value is a NaN, canonicalize the value else, do nothing.

View File

@ -81,22 +81,19 @@ void TurboAssemblerBase::IndirectLoadExternalReference(
// static // static
int32_t TurboAssemblerBase::RootRegisterOffsetForRootIndex( int32_t TurboAssemblerBase::RootRegisterOffsetForRootIndex(
RootIndex root_index) { RootIndex root_index) {
return (static_cast<int32_t>(root_index) << kPointerSizeLog2) - return IsolateData::root_slot_offset(root_index);
kRootRegisterBias;
} }
// static // static
int32_t TurboAssemblerBase::RootRegisterOffsetForBuiltinIndex( int32_t TurboAssemblerBase::RootRegisterOffsetForBuiltinIndex(
int builtin_index) { int builtin_index) {
return IsolateData::kBuiltinsTableOffset - kRootRegisterBias + return IsolateData::builtin_slot_offset(builtin_index);
builtin_index * kPointerSize;
} }
// static // static
intptr_t TurboAssemblerBase::RootRegisterOffsetForExternalReference( intptr_t TurboAssemblerBase::RootRegisterOffsetForExternalReference(
Isolate* isolate, const ExternalReference& reference) { Isolate* isolate, const ExternalReference& reference) {
return static_cast<intptr_t>(reference.address()) - kRootRegisterBias - return static_cast<intptr_t>(reference.address() - isolate->isolate_root());
reinterpret_cast<intptr_t>(isolate->roots_array_start());
} }
// static // static
@ -108,7 +105,7 @@ int32_t TurboAssemblerBase::RootRegisterOffsetForExternalReferenceTableEntry(
ExternalReferenceEncoder::Value v = encoder.Encode(reference.address()); ExternalReferenceEncoder::Value v = encoder.Encode(reference.address());
CHECK(!v.is_from_api()); CHECK(!v.is_from_api());
return IsolateData::kExternalReferenceTableOffset - kRootRegisterBias + return IsolateData::external_reference_table_offset() +
ExternalReferenceTable::OffsetOfEntry(v.index()); ExternalReferenceTable::OffsetOfEntry(v.index());
} }

View File

@ -142,8 +142,8 @@ void WasmGlobalObject::SetF64(double value) {
PRIMITIVE_ACCESSORS(WasmInstanceObject, memory_start, byte*, kMemoryStartOffset) PRIMITIVE_ACCESSORS(WasmInstanceObject, memory_start, byte*, kMemoryStartOffset)
PRIMITIVE_ACCESSORS(WasmInstanceObject, memory_size, size_t, kMemorySizeOffset) PRIMITIVE_ACCESSORS(WasmInstanceObject, memory_size, size_t, kMemorySizeOffset)
PRIMITIVE_ACCESSORS(WasmInstanceObject, memory_mask, size_t, kMemoryMaskOffset) PRIMITIVE_ACCESSORS(WasmInstanceObject, memory_mask, size_t, kMemoryMaskOffset)
PRIMITIVE_ACCESSORS(WasmInstanceObject, roots_array_address, Address, PRIMITIVE_ACCESSORS(WasmInstanceObject, isolate_root, Address,
kRootsArrayAddressOffset) kIsolateRootOffset)
PRIMITIVE_ACCESSORS(WasmInstanceObject, stack_limit_address, Address, PRIMITIVE_ACCESSORS(WasmInstanceObject, stack_limit_address, Address,
kStackLimitAddressOffset) kStackLimitAddressOffset)
PRIMITIVE_ACCESSORS(WasmInstanceObject, real_stack_limit_address, Address, PRIMITIVE_ACCESSORS(WasmInstanceObject, real_stack_limit_address, Address,

View File

@ -1282,8 +1282,7 @@ Handle<WasmInstanceObject> WasmInstanceObject::New(
instance->set_centry_stub(*centry_stub); instance->set_centry_stub(*centry_stub);
instance->SetRawMemory(nullptr, 0); instance->SetRawMemory(nullptr, 0);
instance->set_roots_array_address( instance->set_isolate_root(isolate->isolate_root());
reinterpret_cast<Address>(isolate->roots_array_start()));
instance->set_stack_limit_address( instance->set_stack_limit_address(
isolate->stack_guard()->address_of_jslimit()); isolate->stack_guard()->address_of_jslimit());
instance->set_real_stack_limit_address( instance->set_real_stack_limit_address(

View File

@ -395,7 +395,7 @@ class WasmInstanceObject : public JSObject {
DECL_PRIMITIVE_ACCESSORS(memory_start, byte*) DECL_PRIMITIVE_ACCESSORS(memory_start, byte*)
DECL_PRIMITIVE_ACCESSORS(memory_size, size_t) DECL_PRIMITIVE_ACCESSORS(memory_size, size_t)
DECL_PRIMITIVE_ACCESSORS(memory_mask, size_t) DECL_PRIMITIVE_ACCESSORS(memory_mask, size_t)
DECL_PRIMITIVE_ACCESSORS(roots_array_address, Address) DECL_PRIMITIVE_ACCESSORS(isolate_root, Address)
DECL_PRIMITIVE_ACCESSORS(stack_limit_address, Address) DECL_PRIMITIVE_ACCESSORS(stack_limit_address, Address)
DECL_PRIMITIVE_ACCESSORS(real_stack_limit_address, Address) DECL_PRIMITIVE_ACCESSORS(real_stack_limit_address, Address)
DECL_PRIMITIVE_ACCESSORS(imported_function_targets, Address*) DECL_PRIMITIVE_ACCESSORS(imported_function_targets, Address*)
@ -431,7 +431,7 @@ class WasmInstanceObject : public JSObject {
V(kMemoryStartOffset, kPointerSize) /* untagged */ \ V(kMemoryStartOffset, kPointerSize) /* untagged */ \
V(kMemorySizeOffset, kSizetSize) /* untagged */ \ V(kMemorySizeOffset, kSizetSize) /* untagged */ \
V(kMemoryMaskOffset, kSizetSize) /* untagged */ \ V(kMemoryMaskOffset, kSizetSize) /* untagged */ \
V(kRootsArrayAddressOffset, kPointerSize) /* untagged */ \ V(kIsolateRootOffset, kPointerSize) /* untagged */ \
V(kStackLimitAddressOffset, kPointerSize) /* untagged */ \ V(kStackLimitAddressOffset, kPointerSize) /* untagged */ \
V(kRealStackLimitAddressOffset, kPointerSize) /* untagged */ \ V(kRealStackLimitAddressOffset, kPointerSize) /* untagged */ \
V(kImportedFunctionTargetsOffset, kPointerSize) /* untagged */ \ V(kImportedFunctionTargetsOffset, kPointerSize) /* untagged */ \

View File

@ -580,7 +580,7 @@ int DisassemblerX64::PrintRightOperandHelper(
disp < 0 ? -disp : disp); disp < 0 ? -disp : disp);
if (rm == i::kRootRegister.code()) { if (rm == i::kRootRegister.code()) {
// For root-relative accesses, try to append a description. // For root-relative accesses, try to append a description.
TryAppendRootRelativeName(i::kRootRegisterBias + disp); TryAppendRootRelativeName(disp);
} }
return (mod == 2) ? 5 : 2; return (mod == 2) ? 5 : 2;
} }

View File

@ -466,10 +466,8 @@ class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
void CallRuntimeWithCEntry(Runtime::FunctionId fid, Register centry); void CallRuntimeWithCEntry(Runtime::FunctionId fid, Register centry);
void InitializeRootRegister() { void InitializeRootRegister() {
ExternalReference roots_array_start = ExternalReference isolate_root = ExternalReference::isolate_root(isolate());
ExternalReference::roots_array_start(isolate()); Move(kRootRegister, isolate_root);
Move(kRootRegister, roots_array_start);
addp(kRootRegister, Immediate(kRootRegisterBias));
} }
void SaveRegisters(RegList registers); void SaveRegisters(RegList registers);

View File

@ -4542,9 +4542,8 @@ TEST_F(InstructionSelectorTest, ExternalReferenceLoad1) {
const int64_t kOffsets[] = {0, 1, 4, INT32_MIN, INT32_MAX}; const int64_t kOffsets[] = {0, 1, 4, INT32_MIN, INT32_MAX};
TRACED_FOREACH(int64_t, offset, kOffsets) { TRACED_FOREACH(int64_t, offset, kOffsets) {
StreamBuilder m(this, MachineType::Int64()); StreamBuilder m(this, MachineType::Int64());
ExternalReference reference = bit_cast<ExternalReference>( ExternalReference reference =
reinterpret_cast<intptr_t>(isolate()->roots_array_start()) + offset + bit_cast<ExternalReference>(isolate()->isolate_root() + offset);
kRootRegisterBias);
Node* const value = Node* const value =
m.Load(MachineType::Int64(), m.ExternalConstant(reference)); m.Load(MachineType::Int64(), m.ExternalConstant(reference));
m.Return(value); m.Return(value);
@ -4564,9 +4563,8 @@ TEST_F(InstructionSelectorTest, ExternalReferenceLoad2) {
// Offset too large, we cannot use kMode_Root. // Offset too large, we cannot use kMode_Root.
StreamBuilder m(this, MachineType::Int64()); StreamBuilder m(this, MachineType::Int64());
int64_t offset = 0x100000000; int64_t offset = 0x100000000;
ExternalReference reference = bit_cast<ExternalReference>( ExternalReference reference =
reinterpret_cast<intptr_t>(isolate()->roots_array_start()) + offset + bit_cast<ExternalReference>(isolate()->isolate_root() + offset);
kRootRegisterBias);
Node* const value = Node* const value =
m.Load(MachineType::Int64(), m.ExternalConstant(reference)); m.Load(MachineType::Int64(), m.ExternalConstant(reference));
m.Return(value); m.Return(value);