Skip to content

Commit 476f915

Browse files
mralephCommit Queue
authored andcommitted
[vm] Cache arg descriptors used by stubs
This reverts commit c5d973d and commit 5e77a23 because the later breaks hot reload constant rehashing which can't handle constant set which include vm-isolate objects. Instead we expand standalone cache to cache descriptors with 1 type argument and 0, 1 or 2 arguments. This covers all descriptors used in stubs. Fixes b/429384250 TEST=ci Cq-Include-Trybots: luci.dart.try:vm-aot-linux-debug-x64-try,vm-linux-debug-x64-try Change-Id: I2058d3da9609821c1b3272db2f1ed4d9d3c3216a Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/438720 Reviewed-by: Martin Kustermann <[email protected]> Commit-Queue: Slava Egorov <[email protected]>
1 parent 120337d commit 476f915

File tree

4 files changed

+63
-34
lines changed

4 files changed

+63
-34
lines changed

runtime/vm/compiler/backend/il_serializer.cc

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -102,24 +102,26 @@ void ArgumentsDescriptor::Write(FlowGraphSerializer* s) const {
102102
if (IsCached()) {
103103
// Simple argument descriptors are cached in the VM isolate.
104104
// Write them as arguments count and query cache during deserialization.
105-
ASSERT(TypeArgsLen() == 0);
106105
ASSERT(NamedCount() == 0);
107106
ASSERT(Count() == Size());
108107
ASSERT(array_.InVMIsolateHeap());
108+
s->Write<intptr_t>(TypeArgsLen());
109109
s->Write<intptr_t>(Count());
110110
} else {
111111
ASSERT(array_.IsCanonical());
112+
ASSERT(!array_.InVMIsolateHeap());
112113
s->Write<intptr_t>(-1);
113114
s->Write<const Array&>(array_);
114115
}
115116
}
116117

117118
ArrayPtr ArgumentsDescriptor::Read(FlowGraphDeserializer* d) {
118-
const intptr_t num_args = d->Read<intptr_t>();
119-
if (num_args < 0) {
119+
const intptr_t num_type_args = d->Read<intptr_t>();
120+
if (num_type_args < 0) {
120121
return d->Read<const Array&>().ptr();
121122
}
122-
return NewBoxed(0, num_args);
123+
const intptr_t num_args = d->Read<intptr_t>();
124+
return NewBoxed(num_type_args, num_args);
123125
}
124126

125127
void BlockEntryInstr::WriteTo(FlowGraphSerializer* s) {

runtime/vm/dart_entry.cc

Lines changed: 42 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44

55
#include "vm/dart_entry.h"
66

7+
#include <array>
8+
79
#include "platform/safe_stack.h"
810
#include "vm/class_finalizer.h"
911
#include "vm/debugger.h"
@@ -458,10 +460,33 @@ const char* ArgumentsDescriptor::ToCString() const {
458460
return buf.buffer();
459461
}
460462

463+
intptr_t ArgumentsDescriptor::CacheIndexFor(intptr_t type_args_len,
464+
intptr_t num_arguments) {
465+
static constexpr auto kOffsetTo = []() {
466+
std::array<intptr_t, kMaxTypeArgsForCachedDescriptor + 1> offset;
467+
offset[0] = 0;
468+
for (intptr_t i = 1; i <= kMaxTypeArgsForCachedDescriptor; i++) {
469+
offset[i] =
470+
offset[i - 1] + (kMaxNumArgumentsForCachedDescriptor[i - 1] + 1);
471+
}
472+
return offset;
473+
}();
474+
475+
return kOffsetTo[type_args_len] + num_arguments;
476+
}
477+
478+
bool ArgumentsDescriptor::CanUseCachedDescriptor(intptr_t type_args_len,
479+
intptr_t num_arguments) {
480+
return (type_args_len <= kMaxTypeArgsForCachedDescriptor) &&
481+
(num_arguments <= kMaxNumArgumentsForCachedDescriptor[type_args_len]);
482+
}
483+
461484
bool ArgumentsDescriptor::IsCached() const {
485+
const intptr_t num_type_arguments = TypeArgsLen();
462486
const intptr_t num_arguments = Count();
463-
return (num_arguments < kCachedDescriptorCount) &&
464-
(array_.ptr() == cached_args_descriptors_[num_arguments]);
487+
return CanUseCachedDescriptor(num_type_arguments, num_arguments) &&
488+
(array_.ptr() == cached_args_descriptors_[CacheIndexFor(
489+
num_type_arguments, num_arguments)]);
465490
}
466491

467492
ArrayPtr ArgumentsDescriptor::New(intptr_t type_args_len,
@@ -541,9 +566,10 @@ ArrayPtr ArgumentsDescriptor::New(intptr_t type_args_len,
541566
ASSERT(type_args_len >= 0);
542567
ASSERT(num_arguments >= 0);
543568

544-
if ((type_args_len == 0) && (num_arguments < kCachedDescriptorCount) &&
545-
(num_arguments == size_arguments)) {
546-
return cached_args_descriptors_[num_arguments];
569+
if (num_arguments == size_arguments &&
570+
CanUseCachedDescriptor(type_args_len, num_arguments)) {
571+
return cached_args_descriptors_[CacheIndexFor(type_args_len,
572+
num_arguments)];
547573
}
548574
return NewNonCached(type_args_len, num_arguments, size_arguments, true,
549575
space);
@@ -590,10 +616,18 @@ ArrayPtr ArgumentsDescriptor::NewNonCached(intptr_t type_args_len,
590616
}
591617

592618
void ArgumentsDescriptor::Init() {
593-
for (int i = 0; i < kCachedDescriptorCount; i++) {
594-
cached_args_descriptors_[i] =
595-
NewNonCached(/*type_args_len=*/0, i, i, false, Heap::kOld);
619+
intptr_t cache_index = 0;
620+
for (intptr_t type_args_len = 0;
621+
type_args_len <= kMaxTypeArgsForCachedDescriptor; type_args_len++) {
622+
for (intptr_t num_arguments = 0;
623+
num_arguments <= kMaxNumArgumentsForCachedDescriptor[type_args_len];
624+
num_arguments++) {
625+
cached_args_descriptors_[cache_index++] =
626+
NewNonCached(type_args_len, num_arguments, num_arguments,
627+
/*canonicalize=*/false, Heap::kOld);
628+
}
596629
}
630+
ASSERT(cache_index == kCachedDescriptorCount);
597631
}
598632

599633
void ArgumentsDescriptor::Cleanup() {

runtime/vm/dart_entry.h

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,17 @@ class ArgumentsDescriptor : public ValueObject {
126126
// Clear the preallocated fixed length arguments descriptors cache.
127127
static void Cleanup();
128128

129-
enum { kCachedDescriptorCount = 32 };
129+
static constexpr intptr_t kMaxTypeArgsForCachedDescriptor = 1;
130+
static constexpr intptr_t
131+
kMaxNumArgumentsForCachedDescriptor[kMaxTypeArgsForCachedDescriptor + 1] =
132+
{31, 2};
133+
static constexpr intptr_t kCachedDescriptorCount = []() -> intptr_t {
134+
intptr_t result = 0;
135+
for (intptr_t i = 0; i <= kMaxTypeArgsForCachedDescriptor; ++i) {
136+
result += kMaxNumArgumentsForCachedDescriptor[i] + 1;
137+
}
138+
return result;
139+
}();
130140

131141
// For creating ArgumentDescriptor Slots.
132142
static constexpr bool ContainsCompressedPointers() {
@@ -181,6 +191,10 @@ class ArgumentsDescriptor : public ValueObject {
181191

182192
bool IsCached() const;
183193

194+
static intptr_t CacheIndexFor(intptr_t type_args_len, intptr_t num_arguments);
195+
static bool CanUseCachedDescriptor(intptr_t type_args_len,
196+
intptr_t num_arguments);
197+
184198
const Array& array_;
185199

186200
// A cache of VM heap allocated arguments descriptors.

runtime/vm/object.cc

Lines changed: 0 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1808,11 +1808,8 @@ ErrorPtr Object::Init(IsolateGroup* isolate_group,
18081808
SafepointWriteRwLocker ml(thread, isolate_group->program_lock());
18091809

18101810
Class& cls = Class::Handle(zone);
1811-
Class& vm_isolate_cls = Class::Handle(zone);
18121811
Type& type = Type::Handle(zone);
1813-
Object& obj = Object::Handle(zone);
18141812
Array& array = Array::Handle(zone);
1815-
Array& array2 = Array::Handle(zone);
18161813
WeakArray& weak_array = WeakArray::Handle(zone);
18171814
Library& lib = Library::Handle(zone);
18181815
TypeArguments& type_args = TypeArguments::Handle(zone);
@@ -1941,24 +1938,6 @@ ErrorPtr Object::Init(IsolateGroup* isolate_group,
19411938
pending_classes.Add(cls);
19421939

19431940
cls = Class::New<Array, RTN::Array>(kImmutableArrayCid, isolate_group);
1944-
1945-
// Carry over immutable array constants from vm-isolate: vm-isolate contains
1946-
// stubs and those use argument descriptor objects represented as
1947-
// canonical immutable arrays. To avoid duplicating these again prepopulate
1948-
// constants set by copying it over from vm-isolate.
1949-
vm_isolate_cls =
1950-
Dart::vm_isolate_group()->object_store()->immutable_array_class();
1951-
array = vm_isolate_cls.constants();
1952-
if (!array.IsNull()) {
1953-
const auto length = array.Length();
1954-
array2 = Array::New(length, Heap::kOld);
1955-
for (intptr_t i = 0; i < length; i++) {
1956-
obj = array.At(i);
1957-
array2.SetAt(i, obj);
1958-
}
1959-
cls.set_constants(array2);
1960-
}
1961-
19621941
object_store->set_immutable_array_class(cls);
19631942
cls.set_type_arguments_field_offset(Array::type_arguments_offset(),
19641943
RTN::Array::type_arguments_offset());

0 commit comments

Comments
 (0)