Skip to content

Commit 7a44485

Browse files
aamCommit Queue
authored andcommitted
[vm] Move catch_entry_cache, handler_info_cache to IsolateGroup.
This should help speeding up new isolate creation (or running dart code on mutator thread when it is supported). TEST=ci Change-Id: I88b5deeb33e72694cb3e2727cf5668ce15fd8c6b Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/420361 Reviewed-by: Slava Egorov <[email protected]> Commit-Queue: Alexander Aprelev <[email protected]>
1 parent 56ccf43 commit 7a44485

File tree

6 files changed

+87
-88
lines changed

6 files changed

+87
-88
lines changed

runtime/vm/exceptions.cc

Lines changed: 3 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -137,7 +137,6 @@ class ExceptionHandlerFinder : public StackResource {
137137
uword temp_handler_pc = kUwordMax;
138138
bool is_optimized = false;
139139
code_ = nullptr;
140-
catch_entry_moves_cache_ = thread_->isolate()->catch_entry_moves_cache();
141140

142141
while (!frame->IsEntryFrame()) {
143142
if (frame->IsDartFrame()) {
@@ -154,14 +153,6 @@ class ExceptionHandlerFinder : public StackResource {
154153
StubCode::AsyncExceptionHandler().EntryPoint())) {
155154
pc_ = frame->pc();
156155
code_ = &Code::Handle(frame->LookupDartCode());
157-
CatchEntryMovesRefPtr* cached_catch_entry_moves =
158-
catch_entry_moves_cache_->Lookup(pc_);
159-
if (cached_catch_entry_moves != nullptr) {
160-
cached_catch_entry_moves_ = *cached_catch_entry_moves;
161-
}
162-
if (cached_catch_entry_moves_.IsEmpty()) {
163-
ReadCompressedCatchEntryMoves();
164-
}
165156
}
166157
}
167158
if (needs_stacktrace || is_catch_all) {
@@ -190,15 +181,9 @@ class ExceptionHandlerFinder : public StackResource {
190181
if (code_ == nullptr || !code_->is_optimized()) {
191182
return;
192183
}
193-
194-
if (cached_catch_entry_moves_.IsEmpty()) {
195-
catch_entry_moves_cache_->Insert(
196-
pc_, CatchEntryMovesRefPtr(catch_entry_moves_));
197-
} else {
198-
catch_entry_moves_ = &cached_catch_entry_moves_.moves();
199-
}
200-
201-
ExecuteCatchEntryMoves(*catch_entry_moves_);
184+
thread_->isolate_group()->RunWithCachedCatchEntryMoves(
185+
*code_, pc_,
186+
[&](const CatchEntryMoves& moves) { ExecuteCatchEntryMoves(moves); });
202187
}
203188

204189
void ExecuteCatchEntryMoves(const CatchEntryMoves& moves) {
@@ -295,14 +280,6 @@ class ExceptionHandlerFinder : public StackResource {
295280
}
296281
}
297282

298-
void ReadCompressedCatchEntryMoves() {
299-
const intptr_t pc_offset = pc_ - code_->PayloadStart();
300-
const auto& td = TypedData::Handle(code_->catch_entry_moves_maps());
301-
302-
CatchEntryMovesMapReader reader(td);
303-
catch_entry_moves_ = reader.ReadMovesForPcOffset(pc_offset);
304-
}
305-
306283
bool needs_stacktrace;
307284
uword handler_pc;
308285
uword handler_sp;
@@ -325,10 +302,6 @@ class ExceptionHandlerFinder : public StackResource {
325302
Code* code_;
326303
bool handler_pc_set_;
327304
intptr_t pc_; // Current pc in the handler frame.
328-
329-
const CatchEntryMoves* catch_entry_moves_ = nullptr;
330-
CatchEntryMovesCache* catch_entry_moves_cache_ = nullptr;
331-
CatchEntryMovesRefPtr cached_catch_entry_moves_;
332305
};
333306

334307
CatchEntryMove CatchEntryMove::ReadFrom(ReadStream* stream) {

runtime/vm/exceptions.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -329,9 +329,9 @@ class CatchEntryMovesRefPtr {
329329
return *this;
330330
}
331331

332-
bool IsEmpty() { return ref_count_ == nullptr; }
332+
bool IsEmpty() const { return ref_count_ == nullptr; }
333333

334-
const CatchEntryMoves& moves() { return *moves_; }
334+
const CatchEntryMoves& moves() const { return *moves_; }
335335

336336
private:
337337
void Destroy() {

runtime/vm/heap/heap.cc

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -545,12 +545,8 @@ void Heap::CollectOldSpaceGarbage(Thread* thread,
545545
#endif
546546

547547
// Some Code objects may have been collected so invalidate handler cache.
548-
thread->isolate_group()->ForEachIsolate(
549-
[&](Isolate* isolate) {
550-
isolate->handler_info_cache()->Clear();
551-
isolate->catch_entry_moves_cache()->Clear();
552-
},
553-
/*at_safepoint=*/true);
548+
thread->isolate_group()->handler_info_cache()->Clear();
549+
thread->isolate_group()->ClearCatchEntryMovesCache();
554550
assume_scavenge_will_fail_ = false;
555551
}
556552
}

runtime/vm/isolate.cc

Lines changed: 29 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -372,12 +372,13 @@ IsolateGroup::IsolateGroup(std::shared_ptr<IsolateGroupSource> source,
372372
boxed_field_list_(GrowableObjectArray::null()),
373373
program_lock_(new SafepointRwLock(SafepointLevel::kGCAndDeopt)),
374374
active_mutators_monitor_(new Monitor()),
375-
max_active_mutators_(Scavenger::MaxMutatorThreadCount())
375+
max_active_mutators_(Scavenger::MaxMutatorThreadCount()),
376376
#if !defined(PRODUCT)
377-
,
378-
debugger_(new GroupDebugger(this))
377+
debugger_(new GroupDebugger(this)),
379378
#endif
380-
{
379+
cache_mutex_(),
380+
handler_info_cache_(),
381+
catch_entry_moves_cache_() {
381382
FlagsCopyFrom(api_flags);
382383
if (!is_vm_isolate) {
383384
intptr_t max_worker_threads;
@@ -927,6 +928,30 @@ void IsolateGroup::ExitTemporaryIsolate() {
927928
Dart::ShutdownIsolate(thread);
928929
}
929930

931+
void IsolateGroup::RunWithCachedCatchEntryMoves(
932+
const Code& code,
933+
intptr_t pc,
934+
std::function<void(const CatchEntryMoves&)> action) {
935+
SafepointMutexLocker ml(&cache_mutex_);
936+
const CatchEntryMovesRefPtr* ref = catch_entry_moves_cache_.Lookup(pc);
937+
if (ref != nullptr) {
938+
action(ref->moves());
939+
} else {
940+
const intptr_t pc_offset = pc - code.PayloadStart();
941+
const auto& td = TypedData::Handle(code.catch_entry_moves_maps());
942+
943+
CatchEntryMovesMapReader reader(td);
944+
const CatchEntryMoves* moves = reader.ReadMovesForPcOffset(pc_offset);
945+
catch_entry_moves_cache_.Insert(pc, CatchEntryMovesRefPtr(moves));
946+
action(*moves);
947+
}
948+
}
949+
950+
void IsolateGroup::ClearCatchEntryMovesCache() {
951+
SafepointMutexLocker ml(&cache_mutex_);
952+
catch_entry_moves_cache_.Clear();
953+
}
954+
930955
void IsolateGroup::RehashConstants(Become* become) {
931956
// Even though no individual constant contains a cycle, there can be "cycles"
932957
// between the canonical tables if some const instances of A have fields that
@@ -1816,8 +1841,6 @@ Isolate::Isolate(IsolateGroup* isolate_group,
18161841
tag_table_(GrowableObjectArray::null()),
18171842
sticky_error_(Error::null()),
18181843
spawn_count_monitor_(),
1819-
handler_info_cache_(),
1820-
catch_entry_moves_cache_(),
18211844
wake_pause_event_handler_count_(0),
18221845
loaded_prefixes_set_storage_(nullptr) {
18231846
FlagsCopyFrom(api_flags);

runtime/vm/isolate.h

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -776,11 +776,20 @@ class IsolateGroup : public IntrusiveDListEntry<IsolateGroup> {
776776
Isolate* EnterTemporaryIsolate();
777777
static void ExitTemporaryIsolate();
778778

779+
void RunWithCachedCatchEntryMoves(
780+
const Code& code,
781+
intptr_t pc,
782+
std::function<void(const CatchEntryMoves&)> action);
783+
void ClearCatchEntryMovesCache();
784+
779785
void SetNativeAssetsCallbacks(NativeAssetsApi* native_assets_api) {
780786
native_assets_api_ = *native_assets_api;
781787
}
782788
NativeAssetsApi* native_assets_api() { return &native_assets_api_; }
783789

790+
Mutex* cache_mutex() { return &cache_mutex_; }
791+
HandlerInfoCache* handler_info_cache() { return &handler_info_cache_; }
792+
784793
private:
785794
friend class Dart; // For `object_store_ = ` in Dart::Init
786795
friend class Heap;
@@ -931,6 +940,10 @@ class IsolateGroup : public IntrusiveDListEntry<IsolateGroup> {
931940
NOT_IN_PRODUCT(GroupDebugger* debugger_ = nullptr);
932941

933942
NativeAssetsApi native_assets_api_;
943+
944+
Mutex cache_mutex_;
945+
HandlerInfoCache handler_info_cache_;
946+
CatchEntryMovesCache catch_entry_moves_cache_;
934947
};
935948

936949
// When an isolate sends-and-exits this class represent things that it passed
@@ -1447,12 +1460,6 @@ class Isolate : public IntrusiveDListEntry<Isolate> {
14471460
}
14481461
static bool IsVMInternalIsolate(const Isolate* isolate);
14491462

1450-
HandlerInfoCache* handler_info_cache() { return &handler_info_cache_; }
1451-
1452-
CatchEntryMovesCache* catch_entry_moves_cache() {
1453-
return &catch_entry_moves_cache_;
1454-
}
1455-
14561463
// The weak table used in the snapshot writer for the purpose of fast message
14571464
// sending.
14581465
WeakTable* forward_table_new() { return forward_table_new_.get(); }
@@ -1697,9 +1704,6 @@ class Isolate : public IntrusiveDListEntry<Isolate> {
16971704
Monitor spawn_count_monitor_;
16981705
intptr_t spawn_count_ = 0;
16991706

1700-
HandlerInfoCache handler_info_cache_;
1701-
CatchEntryMovesCache catch_entry_moves_cache_;
1702-
17031707
// Used during message sending of messages between isolates.
17041708
std::unique_ptr<WeakTable> forward_table_new_;
17051709
std::unique_ptr<WeakTable> forward_table_old_;

runtime/vm/stack_frame.cc

Lines changed: 38 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -469,47 +469,50 @@ bool StackFrame::FindExceptionHandler(Thread* thread,
469469
descriptors = code.pc_descriptors();
470470
*is_optimized = code.is_optimized();
471471
}
472-
HandlerInfoCache* cache = thread->isolate()->handler_info_cache();
473-
ExceptionHandlerInfo* info = cache->Lookup(pc());
474-
if (info != nullptr) {
475-
*handler_pc = start + info->handler_pc_offset;
476-
*needs_stacktrace = (info->needs_stacktrace != 0);
477-
*has_catch_all = (info->has_catch_all != 0);
478-
return true;
479-
}
472+
{
473+
SafepointMutexLocker ml(thread->isolate_group()->cache_mutex());
474+
HandlerInfoCache* cache = thread->isolate_group()->handler_info_cache();
475+
ExceptionHandlerInfo* info = cache->Lookup(pc());
476+
if (info != nullptr) {
477+
*handler_pc = start + info->handler_pc_offset;
478+
*needs_stacktrace = (info->needs_stacktrace != 0);
479+
*has_catch_all = (info->has_catch_all != 0);
480+
return true;
481+
}
480482

481-
intptr_t try_index = -1;
482-
if (handlers.num_entries() != 0) {
483-
if (is_interpreted()) {
484-
try_index = bytecode.GetTryIndexAtPc(pc());
485-
} else {
486-
uword pc_offset = pc() - code.PayloadStart();
487-
PcDescriptors::Iterator iter(descriptors,
488-
UntaggedPcDescriptors::kAnyKind);
489-
while (iter.MoveNext()) {
490-
const intptr_t current_try_index = iter.TryIndex();
491-
if ((iter.PcOffset() == pc_offset) && (current_try_index != -1)) {
492-
try_index = current_try_index;
493-
break;
483+
intptr_t try_index = -1;
484+
if (handlers.num_entries() != 0) {
485+
if (is_interpreted()) {
486+
try_index = bytecode.GetTryIndexAtPc(pc());
487+
} else {
488+
uword pc_offset = pc() - code.PayloadStart();
489+
PcDescriptors::Iterator iter(descriptors,
490+
UntaggedPcDescriptors::kAnyKind);
491+
while (iter.MoveNext()) {
492+
const intptr_t current_try_index = iter.TryIndex();
493+
if ((iter.PcOffset() == pc_offset) && (current_try_index != -1)) {
494+
try_index = current_try_index;
495+
break;
496+
}
494497
}
495498
}
496499
}
497-
}
498-
if (try_index == -1) {
499-
if (handlers.has_async_handler()) {
500-
*handler_pc = StubCode::AsyncExceptionHandler().EntryPoint();
501-
*needs_stacktrace = true;
502-
*has_catch_all = true;
503-
return true;
500+
if (try_index == -1) {
501+
if (handlers.has_async_handler()) {
502+
*handler_pc = StubCode::AsyncExceptionHandler().EntryPoint();
503+
*needs_stacktrace = true;
504+
*has_catch_all = true;
505+
return true;
506+
}
507+
return false;
504508
}
505-
return false;
509+
ExceptionHandlerInfo handler_info;
510+
handlers.GetHandlerInfo(try_index, &handler_info);
511+
*handler_pc = start + handler_info.handler_pc_offset;
512+
*needs_stacktrace = (handler_info.needs_stacktrace != 0);
513+
*has_catch_all = (handler_info.has_catch_all != 0);
514+
cache->Insert(pc(), handler_info);
506515
}
507-
ExceptionHandlerInfo handler_info;
508-
handlers.GetHandlerInfo(try_index, &handler_info);
509-
*handler_pc = start + handler_info.handler_pc_offset;
510-
*needs_stacktrace = (handler_info.needs_stacktrace != 0);
511-
*has_catch_all = (handler_info.has_catch_all != 0);
512-
cache->Insert(pc(), handler_info);
513516
return true;
514517
}
515518

0 commit comments

Comments
 (0)