v8
V8 is Google’s open source high-performance JavaScript and WebAssembly engine, written in C++.
Loading...
Searching...
No Matches
maglev-compilation-info.cc
Go to the documentation of this file.
1// Copyright 2022 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
6
7#include <optional>
8
13#include "src/flags/flags.h"
15#ifdef V8_ENABLE_MAGLEV
18#endif
23
24namespace v8 {
25namespace internal {
26namespace maglev {
27
28namespace {
29
30constexpr char kMaglevZoneName[] = "maglev-compilation-job-zone";
31
32class V8_NODISCARD MaglevCompilationHandleScope final {
33 public:
34 MaglevCompilationHandleScope(Isolate* isolate,
35 maglev::MaglevCompilationInfo* info)
36 : info_(info),
37 persistent_(isolate)
38#ifdef V8_ENABLE_MAGLEV
39 ,
40 exported_info_(info)
41#endif
42 {
43 info->ReopenAndCanonicalizeHandlesInNewScope(isolate);
44 }
45
46 ~MaglevCompilationHandleScope() {
47 info_->set_persistent_handles(persistent_.Detach());
48 }
49
50 private:
51 maglev::MaglevCompilationInfo* const info_;
52 PersistentHandlesScope persistent_;
53#ifdef V8_ENABLE_MAGLEV
54 ExportedMaglevCompilationInfo exported_info_;
55#endif
56};
57
58static bool SpecializeToFunctionContext(
59 Isolate* isolate, BytecodeOffset osr_offset,
60 DirectHandle<JSFunction> function,
61 std::optional<bool> specialize_to_function_context_override) {
62 if (osr_offset != BytecodeOffset::None()) return false;
63 if (!v8_flags.maglev_function_context_specialization) return false;
64 if (specialize_to_function_context_override.has_value()) {
65 return specialize_to_function_context_override.value();
66 }
67 if (function->shared()->function_context_independent_compiled()) {
68 return false;
69 }
70 return function->raw_feedback_cell()->map() ==
71 ReadOnlyRoots(isolate).one_closure_cell_map();
72}
73
74} // namespace
75
77 Isolate* isolate, IndirectHandle<JSFunction> function,
78 BytecodeOffset osr_offset, std::optional<compiler::JSHeapBroker*> js_broker,
79 std::optional<bool> specialize_to_function_context,
80 bool for_turboshaft_frontend)
81 : zone_(isolate->allocator(), kMaglevZoneName),
82 broker_(js_broker.has_value()
83 ? js_broker.value()
84 : new compiler::JSHeapBroker(isolate, zone(),
85 v8_flags.trace_heap_broker,
86 CodeKind::MAGLEV)),
87 toplevel_function_(function),
88 osr_offset_(osr_offset),
89 owns_broker_(!js_broker.has_value()),
90 is_turbolev_(for_turboshaft_frontend)
91#define V(Name) , Name##_(v8_flags.Name)
93#undef V
94 ,
95 specialize_to_function_context_(SpecializeToFunctionContext(
96 isolate, osr_offset, function, specialize_to_function_context)) {
97 if (owns_broker_) {
98 canonical_handles_ = std::make_unique<CanonicalHandlesMap>(
99 isolate->heap(), ZoneAllocationPolicy(&zone_));
101
102 MaglevCompilationHandleScope compilation(isolate, this);
103
106 USE(deps); // The deps register themselves in the heap broker.
107
109
110 // Heap broker initialization may already use IsPendingAllocation.
111 isolate->heap()->PublishMainThreadPendingAllocations();
113 direct_handle(function->native_context(), isolate));
115
116 // Serialization may have allocated.
117 isolate->heap()->PublishMainThreadPendingAllocations();
118
120 MaglevCompilationUnit::New(zone(), this, function);
121 } else {
123 MaglevCompilationUnit::New(zone(), this, function);
124 }
125
126 collect_source_positions_ = isolate->NeedsDetailedOptimizedCodeLineInfo();
127}
128
134
139
140#ifdef V8_ENABLE_MAGLEV
141void MaglevCompilationInfo::set_code_generator(
142 std::unique_ptr<MaglevCodeGenerator> code_generator) {
143 code_generator_ = std::move(code_generator);
144}
145#endif
146
147namespace {
148template <typename T>
149IndirectHandle<T> CanonicalHandle(CanonicalHandlesMap* canonical_handles,
150 Tagged<T> object, Isolate* isolate) {
151 DCHECK_NOT_NULL(canonical_handles);
153 auto find_result = canonical_handles->FindOrInsert(object);
154 if (!find_result.already_exists) {
155 *find_result.entry = IndirectHandle<T>(object, isolate).location();
156 }
157 return IndirectHandle<T>(*find_result.entry);
158}
159} // namespace
160
166
168 std::unique_ptr<PersistentHandles>&& persistent_handles) {
170 ph_ = std::move(persistent_handles);
172}
173
174std::unique_ptr<PersistentHandles>
179
181 std::unique_ptr<CanonicalHandlesMap>&& canonical_handles) {
185}
186
188 return toplevel_function_->context()->IsDetached();
189}
190
191std::unique_ptr<CanonicalHandlesMap>
196
197} // namespace maglev
198} // namespace internal
199} // namespace v8
static constexpr BytecodeOffset None()
Definition utils.h:675
IdentityMapFindResult< V > FindOrInsert(DirectHandle< Object > key)
static V8_EXPORT_PRIVATE bool IsActive(Isolate *isolate)
T * New(Args &&... args)
Definition zone.h:114
void AttachCompilationInfo(CompilationInfoT *info)
void InitializeAndStartSerializing(DirectHandle< NativeContext > native_context)
void set_graph_labeller(MaglevGraphLabeller *graph_labeller)
std::unique_ptr< MaglevGraphLabeller > graph_labeller_
void set_persistent_handles(std::unique_ptr< PersistentHandles > &&persistent_handles)
void set_canonical_handles(std::unique_ptr< CanonicalHandlesMap > &&canonical_handles)
std::unique_ptr< CanonicalHandlesMap > canonical_handles_
std::unique_ptr< PersistentHandles > DetachPersistentHandles()
std::unique_ptr< CanonicalHandlesMap > DetachCanonicalHandles()
MaglevCompilationInfo(Isolate *isolate, IndirectHandle< JSFunction > function, BytecodeOffset osr_offset, std::optional< compiler::JSHeapBroker * > broker=std::nullopt, std::optional< bool > specialize_to_function_context=std::nullopt, bool for_turboshaft_frontend=false)
static MaglevCompilationUnit * New(Zone *zone, MaglevCompilationInfo *info, Handle< JSFunction > function)
Zone * zone_
JSHeapBroker *const broker_
#define _
PersistentHandlesScope persistent_
#define MAGLEV_COMPILATION_FLAG_LIST(V)
V8_INLINE DirectHandle< T > direct_handle(Tagged< T > object, Isolate *isolate)
Handle< T > IndirectHandle
Definition globals.h:1086
V8_EXPORT_PRIVATE FlagValues v8_flags
OptimizedCompilationInfo * info_
Definition pipeline.cc:305
#define DCHECK_NULL(val)
Definition logging.h:491
#define DCHECK_NOT_NULL(val)
Definition logging.h:492
#define DCHECK(condition)
Definition logging.h:482
#define USE(...)
Definition macros.h:293
#define V8_NODISCARD
Definition v8config.h:693