Skip to content

Commit dc5a5da

Browse files
committed
deps: backport v8 f19142e6
[top-level-await] Implement the new post-order requirement for async subgraphs Refs: v8/v8@f19142e PR-URL: #37864 Reviewed-By: Michaël Zasso <targos@protonmail.com> Reviewed-By: Colin Ihrig <cjihrig@gmail.com>
1 parent 45cdc13 commit dc5a5da

18 files changed

+336
-88
lines changed

common.gypi

+1-1
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@
3636

3737
# Reset this number to 0 on major V8 upgrades.
3838
# Increment by one for each non-official patch applied to deps/v8.
39-
'v8_embedder_string': '-node.7',
39+
'v8_embedder_string': '-node.8',
4040

4141
##### V8 defaults for Node.js #####
4242

deps/v8/src/common/globals.h

+3
Original file line numberDiff line numberDiff line change
@@ -356,6 +356,9 @@ constexpr int kUC16Size = sizeof(uc16); // NOLINT
356356
// 128 bit SIMD value size.
357357
constexpr int kSimd128Size = 16;
358358

359+
// Maximum ordinal used for tracking asynchronous module evaluation order.
360+
constexpr unsigned kMaxModuleAsyncEvaluatingOrdinal = (1 << 30) - 1;
361+
359362
// FUNCTION_ADDR(f) gets the address of a C function f.
360363
#define FUNCTION_ADDR(f) (reinterpret_cast<v8::internal::Address>(f))
361364

deps/v8/src/diagnostics/objects-debug.cc

+1-1
Original file line numberDiff line numberDiff line change
@@ -1523,7 +1523,7 @@ void SourceTextModule::SourceTextModuleVerify(Isolate* isolate) {
15231523
}
15241524
CHECK(!AsyncParentModuleCount());
15251525
CHECK(!pending_async_dependencies());
1526-
CHECK(!async_evaluating());
1526+
CHECK(!IsAsyncEvaluating());
15271527
}
15281528

15291529
CHECK_EQ(requested_modules().length(), info().module_requests().length());

deps/v8/src/diagnostics/objects-printer.cc

+1
Original file line numberDiff line numberDiff line change
@@ -1731,6 +1731,7 @@ void SourceTextModule::SourceTextModulePrint(std::ostream& os) { // NOLINT
17311731
os << "\n - requested_modules: " << Brief(requested_modules());
17321732
os << "\n - import_meta: " << Brief(import_meta());
17331733
os << "\n - cycle_root: " << Brief(cycle_root());
1734+
os << "\n - async_evaluating_ordinal: " << async_evaluating_ordinal();
17341735
os << "\n";
17351736
}
17361737

deps/v8/src/execution/isolate-inl.h

+31
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#include "src/objects/property-cell.h"
1414
#include "src/objects/regexp-match-info.h"
1515
#include "src/objects/shared-function-info.h"
16+
#include "src/objects/source-text-module-inl.h"
1617

1718
namespace v8 {
1819
namespace internal {
@@ -119,6 +120,36 @@ bool Isolate::IsAnyInitialArrayPrototype(JSArray array) {
119120
return IsInAnyContext(array, Context::INITIAL_ARRAY_PROTOTYPE_INDEX);
120121
}
121122

123+
void Isolate::DidFinishModuleAsyncEvaluation(unsigned ordinal) {
124+
// To address overflow, the ordinal is reset when the async module with the
125+
// largest vended ordinal finishes evaluating. Modules are evaluated in
126+
// ascending order of their async_evaluating_ordinal.
127+
//
128+
// While the specification imposes a global total ordering, the intention is
129+
// that for each async module, all its parents are totally ordered by when
130+
// they first had their [[AsyncEvaluating]] bit set.
131+
//
132+
// The module with largest vended ordinal finishes evaluating implies that the
133+
// async dependency as well as all other modules in that module's graph
134+
// depending on async dependencies are finished evaluating.
135+
//
136+
// If the async dependency participates in other module graphs (e.g. via
137+
// dynamic import, or other <script type=module> tags), those module graphs
138+
// must have been evaluated either before or after the async dependency is
139+
// settled, as the concrete Evaluate() method on cyclic module records is
140+
// neither reentrant nor performs microtask checkpoints during its
141+
// evaluation. If before, then all modules that depend on the async
142+
// dependencies were given an ordinal that ensure they are relatively ordered,
143+
// before the global ordinal was reset. If after, then the async evaluating
144+
// ordering does not apply, as the dependency is no longer asynchronous.
145+
//
146+
// https://tc39.es/ecma262/#sec-moduleevaluation
147+
if (ordinal + 1 == next_module_async_evaluating_ordinal_) {
148+
next_module_async_evaluating_ordinal_ =
149+
SourceTextModule::kFirstAsyncEvaluatingOrdinal;
150+
}
151+
}
152+
122153
#define NATIVE_CONTEXT_FIELD_ACCESSOR(index, type, name) \
123154
Handle<type> Isolate::name() { \
124155
return Handle<type>(raw_native_context().name(), this); \

deps/v8/src/execution/isolate.cc

+3
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@
7373
#include "src/objects/prototype.h"
7474
#include "src/objects/slots.h"
7575
#include "src/objects/smi.h"
76+
#include "src/objects/source-text-module-inl.h"
7677
#include "src/objects/stack-frame-info-inl.h"
7778
#include "src/objects/visitors.h"
7879
#include "src/profiler/heap-profiler.h"
@@ -2897,6 +2898,8 @@ Isolate::Isolate(std::unique_ptr<i::IsolateAllocator> isolate_allocator)
28972898
#if V8_SFI_HAS_UNIQUE_ID
28982899
next_unique_sfi_id_(0),
28992900
#endif
2901+
next_module_async_evaluating_ordinal_(
2902+
SourceTextModule::kFirstAsyncEvaluatingOrdinal),
29002903
cancelable_task_manager_(new CancelableTaskManager()) {
29012904
TRACE_ISOLATE(constructor);
29022905
CheckIsolateLayout();

deps/v8/src/execution/isolate.h

+18
Original file line numberDiff line numberDiff line change
@@ -1369,6 +1369,22 @@ class V8_EXPORT_PRIVATE Isolate final : private HiddenFactory {
13691369
return id;
13701370
}
13711371

1372+
// https://github.com/tc39/proposal-top-level-await/pull/159
1373+
// TODO(syg): Update to actual spec link once merged.
1374+
//
1375+
// According to the spec, modules that depend on async modules (i.e. modules
1376+
// with top-level await) must be evaluated in order in which their
1377+
// [[AsyncEvaluating]] flags were set to true. V8 tracks this global total
1378+
// order with next_module_async_evaluating_ordinal_. Each module that sets its
1379+
// [[AsyncEvaluating]] to true grabs the next ordinal.
1380+
unsigned NextModuleAsyncEvaluatingOrdinal() {
1381+
unsigned ordinal = next_module_async_evaluating_ordinal_++;
1382+
CHECK_LT(ordinal, kMaxModuleAsyncEvaluatingOrdinal);
1383+
return ordinal;
1384+
}
1385+
1386+
inline void DidFinishModuleAsyncEvaluation(unsigned ordinal);
1387+
13721388
void AddNearHeapLimitCallback(v8::NearHeapLimitCallback, void* data);
13731389
void RemoveNearHeapLimitCallback(v8::NearHeapLimitCallback callback,
13741390
size_t heap_limit);
@@ -1970,6 +1986,8 @@ class V8_EXPORT_PRIVATE Isolate final : private HiddenFactory {
19701986
std::atomic<int> next_unique_sfi_id_;
19711987
#endif
19721988

1989+
unsigned next_module_async_evaluating_ordinal_;
1990+
19731991
// Vector of callbacks before a Call starts execution.
19741992
std::vector<BeforeCallEnteredCallback> before_call_entered_callbacks_;
19751993

deps/v8/src/heap/factory.cc

+1-1
Original file line numberDiff line numberDiff line change
@@ -2365,7 +2365,7 @@ Handle<SourceTextModule> Factory::NewSourceTextModule(
23652365
module->set_dfs_ancestor_index(-1);
23662366
module->set_flags(0);
23672367
module->set_async(IsAsyncModule(sfi->kind()));
2368-
module->set_async_evaluating(false);
2368+
module->set_async_evaluating_ordinal(SourceTextModule::kNotAsyncEvaluated);
23692369
module->set_cycle_root(roots.the_hole_value());
23702370
module->set_async_parent_modules(*async_parent_modules);
23712371
module->set_pending_async_dependencies(0);

deps/v8/src/objects/module-inl.h

+6-2
Original file line numberDiff line numberDiff line change
@@ -38,8 +38,8 @@ SMI_ACCESSORS(Module, status, kStatusOffset)
3838
SMI_ACCESSORS(Module, hash, kHashOffset)
3939

4040
BOOL_ACCESSORS(SourceTextModule, flags, async, AsyncBit::kShift)
41-
BOOL_ACCESSORS(SourceTextModule, flags, async_evaluating,
42-
AsyncEvaluatingBit::kShift)
41+
BIT_FIELD_ACCESSORS(SourceTextModule, flags, async_evaluating_ordinal,
42+
SourceTextModule::AsyncEvaluatingOrdinalBits)
4343
ACCESSORS(SourceTextModule, async_parent_modules, ArrayList,
4444
kAsyncParentModulesOffset)
4545

@@ -139,6 +139,10 @@ int SourceTextModule::AsyncParentModuleCount() {
139139
return async_parent_modules().Length();
140140
}
141141

142+
bool SourceTextModule::IsAsyncEvaluating() const {
143+
return async_evaluating_ordinal() >= kFirstAsyncEvaluatingOrdinal;
144+
}
145+
142146
bool SourceTextModule::HasPendingAsyncDependencies() {
143147
DCHECK_GE(pending_async_dependencies(), 0);
144148
return pending_async_dependencies() > 0;

0 commit comments

Comments
 (0)