Flutter Engine
The Flutter Engine
weak_code.cc
Go to the documentation of this file.
1// Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file
2// for details. All rights reserved. Use of this source code is governed by a
3// BSD-style license that can be found in the LICENSE file.
4
5#include "vm/heap/weak_code.h"
6
7#include "platform/assert.h"
8
9#include "vm/code_patcher.h"
10#include "vm/hash_table.h"
11#include "vm/object.h"
12#include "vm/runtime_entry.h"
13#include "vm/stack_frame.h"
14
15namespace dart {
16
18 public:
19 static const char* Name() { return "CodeTraits"; }
20 static bool ReportStats() { return false; }
21 static bool IsMatch(const Object& a, const Object& b) {
22 return a.ptr() == b.ptr();
23 }
24 static uword Hash(const Object& key) { return Code::Cast(key).Hash(); }
25};
26
28
30 return !array_.IsNull() && (array_.Length() > 0);
31}
32
34 WeakCodeSet set(array_.IsNull() ? HashTables::New<WeakCodeSet>(4, Heap::kOld)
35 : array_.ptr());
36 set.Insert(value);
38}
39
40void WeakCodeReferences::DisableCode(bool are_mutators_stopped) {
41#if defined(DART_PRECOMPILED_RUNTIME)
42 ASSERT(array_.IsNull());
43 return;
44#else
45 // Ensure mutators see empty code_objects only after code was deoptimized.
47 IsolateGroup::Current()->program_lock()->IsCurrentThreadWriter());
48
49 if (array_.IsNull()) {
50 return;
51 }
52
53 WeakCodeSet set(array_.ptr());
54
55 auto isolate_group = IsolateGroup::Current();
56 auto disable_code_fun = [&]() {
58 isolate_group->ForEachIsolate(
59 [&](Isolate* isolate) {
60 auto mutator_thread = isolate->mutator_thread();
61 if (mutator_thread == nullptr) {
62 return;
63 }
64 DartFrameIterator iterator(
66 StackFrame* frame = iterator.NextFrame();
67 while (frame != nullptr) {
68 code = frame->LookupDartCode();
69
70 if (set.ContainsKey(code)) {
72 DeoptimizeAt(mutator_thread, code, frame);
73 }
74 frame = iterator.NextFrame();
75 }
76 },
77 /*at_safepoint=*/true);
78
79 // Switch functions that use dependent code to unoptimized code.
80 Object& owner = Object::Handle();
82 WeakCodeSet::Iterator it(&set);
83 while (it.MoveNext()) {
84 code ^= set.GetKey(it.Current());
85 if (code.IsNull()) {
86 // Code was garbage collected already.
87 continue;
88 }
89 owner = code.owner();
90 if (owner.IsFunction()) {
91 function ^= owner.ptr();
92 } else if (owner.IsClass()) {
93 Class& cls = Class::Handle();
94 cls ^= owner.ptr();
96 continue;
97 } else if (owner.IsNull()) {
98 code.Print();
99 continue;
100 }
101
102 // Only optimized code can make dependencies (assumptions) about CHA /
103 // field guards and might need to be deoptimized if those assumptions no
104 // longer hold.
105 // See similar assertions when code gets registered in
106 // `Field::RegisterDependentCode` and `Class::RegisterCHACode`.
107 ASSERT(code.is_optimized());
108 ASSERT(function.unoptimized_code() != code.ptr());
109
110 // If function uses dependent code switch it to unoptimized.
111 if (function.CurrentCode() == code.ptr()) {
113 function.SwitchToUnoptimizedCode();
114 } else {
115 // Make non-OSR code non-entrant.
116 if (!code.IsDisabled()) {
118 code.DisableDartCode();
119 }
120 }
121 }
122
124 };
125
126 // Deoptimize stacks and disable code (with mutators stopped if they are not
127 // stopped yet).
128 if (are_mutators_stopped) {
129 disable_code_fun();
130 } else {
131 isolate_group->RunWithStoppedMutators(disable_code_fun);
132 }
133
134 set.Release();
135
136#endif // defined(DART_PRECOMPILED_RUNTIME)
137}
138
139} // namespace dart
#define DEBUG_ASSERT(cond)
Definition: assert.h:321
void DisableAllocationStub() const
Definition: object.cc:5879
static const char * Name()
Definition: weak_code.cc:19
static uword Hash(const Object &key)
Definition: weak_code.cc:24
static bool ReportStats()
Definition: weak_code.cc:20
static bool IsMatch(const Object &a, const Object &b)
Definition: weak_code.cc:21
StackFrame * NextFrame()
Definition: stack_frame.h:352
@ kOld
Definition: heap.h:39
static IsolateGroup * Current()
Definition: isolate.h:539
Thread * mutator_thread() const
Definition: isolate.cc:1920
ObjectPtr ptr() const
Definition: object.h:332
bool IsNull() const
Definition: object.h:363
static Object & Handle()
Definition: object.h:407
intptr_t Length() const
Definition: object.h:6697
void DisableCode(bool are_mutators_stopped)
Definition: weak_code.cc:40
virtual void ReportDeoptimization(const Code &code)=0
virtual void UpdateArrayTo(const WeakArray &array)=0
virtual void ReportSwitchingCode(const Code &code)=0
void Register(const Code &value)
Definition: weak_code.cc:33
bool HasCodes() const
Definition: weak_code.cc:29
#define ASSERT(E)
double frame
Definition: examples.cpp:31
static bool b
struct MyStruct a[10]
uint8_t value
Dart_NativeFunction function
Definition: fuchsia.cc:51
Definition: dart_vm.cc:33
uintptr_t uword
Definition: globals.h:501
void DeoptimizeAt(Thread *mutator_thread, const Code &optimized_code, StackFrame *frame)
UnorderedHashSet< CodeTraits, WeakArrayStorageTraits > WeakCodeSet
Definition: weak_code.cc:27
DEF_SWITCHES_START aot vmservice shared library Name of the *so containing AOT compiled Dart assets for launching the service isolate vm snapshot The VM snapshot data that will be memory mapped as read only SnapshotAssetPath must be present isolate snapshot The isolate snapshot data that will be memory mapped as read only SnapshotAssetPath must be present cache dir Path to the cache directory This is different from the persistent_cache_path in embedder which is used for Skia shader cache icu native lib Path to the library file that exports the ICU data vm service The hostname IP address on which the Dart VM Service should be served If not set
Definition: switches.h:76