Commit a1241353 authored by Georg Neis's avatar Georg Neis Committed by Commit Bot

[modules] Anticipate stack overflow when traversing module graph.

Bug: chromium:836124
Change-Id: I82d29408476c9c5b2c62a6368f32575e33932ef3
Reviewed-on: https://chromium-review.googlesource.com/1025890Reviewed-by: 's avatarSathya Gunasekaran <gsathya@chromium.org>
Commit-Queue: Georg Neis <neis@chromium.org>
Cr-Commit-Position: refs/heads/master@{#52774}
parent 44a000fd
......@@ -461,8 +461,10 @@ bool Module::PrepareInstantiate(Handle<Module> module,
if (module->status() >= kPreInstantiating) return true;
module->SetStatus(kPreInstantiating);
// Obtain requested modules.
Isolate* isolate = module->GetIsolate();
STACK_CHECK(isolate, false);
// Obtain requested modules.
Handle<ModuleInfo> module_info(module->info(), isolate);
Handle<FixedArray> module_requests(module_info->module_requests(), isolate);
Handle<FixedArray> requested_modules(module->requested_modules(), isolate);
......@@ -515,21 +517,26 @@ bool Module::PrepareInstantiate(Handle<Module> module,
return true;
}
void Module::RunInitializationCode(Handle<Module> module) {
bool Module::RunInitializationCode(Handle<Module> module) {
DCHECK_EQ(module->status(), kInstantiating);
Isolate* isolate = module->GetIsolate();
Handle<JSFunction> function(JSFunction::cast(module->code()), isolate);
DCHECK_EQ(MODULE_SCOPE, function->shared()->scope_info()->scope_type());
Handle<Object> receiver = isolate->factory()->undefined_value();
Handle<Object> argv[] = {module};
Handle<Object> generator =
Execution::Call(isolate, function, receiver, arraysize(argv), argv)
.ToHandleChecked();
MaybeHandle<Object> maybe_generator =
Execution::Call(isolate, function, receiver, arraysize(argv), argv);
Handle<Object> generator;
if (!maybe_generator.ToHandle(&generator)) {
DCHECK(isolate->has_pending_exception());
return false;
}
DCHECK_EQ(*function, Handle<JSGeneratorObject>::cast(generator)->function());
module->set_code(*generator);
return true;
}
void Module::MaybeTransitionComponent(Handle<Module> module,
bool Module::MaybeTransitionComponent(Handle<Module> module,
ZoneForwardList<Handle<Module>>* stack,
Status new_status) {
DCHECK(new_status == kInstantiated || new_status == kEvaluated);
......@@ -546,10 +553,13 @@ void Module::MaybeTransitionComponent(Handle<Module> module,
stack->pop_front();
DCHECK_EQ(ancestor->status(),
new_status == kInstantiated ? kInstantiating : kEvaluating);
if (new_status == kInstantiated) RunInitializationCode(ancestor);
if (new_status == kInstantiated) {
if (!RunInitializationCode(ancestor)) return false;
}
ancestor->SetStatus(new_status);
} while (*ancestor != *module);
}
return true;
}
bool Module::FinishInstantiate(Handle<Module> module,
......@@ -559,9 +569,11 @@ bool Module::FinishInstantiate(Handle<Module> module,
if (module->status() >= kInstantiating) return true;
DCHECK_EQ(module->status(), kPreInstantiating);
Isolate* isolate = module->GetIsolate();
STACK_CHECK(isolate, false);
// Instantiate SharedFunctionInfo and mark module as instantiating for
// the recursion.
Isolate* isolate = module->GetIsolate();
Handle<SharedFunctionInfo> shared(SharedFunctionInfo::cast(module->code()),
isolate);
Handle<JSFunction> function =
......@@ -635,8 +647,7 @@ bool Module::FinishInstantiate(Handle<Module> module,
}
}
MaybeTransitionComponent(module, stack, kInstantiated);
return true;
return MaybeTransitionComponent(module, stack, kInstantiated);
}
MaybeHandle<Object> Module::Evaluate(Handle<Module> module) {
......@@ -688,6 +699,7 @@ MaybeHandle<Object> Module::Evaluate(Handle<Module> module,
return isolate->factory()->undefined_value();
}
DCHECK_EQ(module->status(), kInstantiated);
STACK_CHECK(isolate, MaybeHandle<Object>());
Handle<JSGeneratorObject> generator(JSGeneratorObject::cast(module->code()),
isolate);
......@@ -734,7 +746,7 @@ MaybeHandle<Object> Module::Evaluate(Handle<Module> module,
->done()
->BooleanValue());
MaybeTransitionComponent(module, stack, kEvaluated);
CHECK(MaybeTransitionComponent(module, stack, kEvaluated));
return handle(
static_cast<JSIteratorResult*>(JSObject::cast(*result))->value(),
isolate);
......
......@@ -172,15 +172,16 @@ class Module : public Struct {
static V8_WARN_UNUSED_RESULT bool FinishInstantiate(
Handle<Module> module, ZoneForwardList<Handle<Module>>* stack,
unsigned* dfs_index, Zone* zone);
static void RunInitializationCode(Handle<Module> module);
static V8_WARN_UNUSED_RESULT bool RunInitializationCode(
Handle<Module> module);
static V8_WARN_UNUSED_RESULT MaybeHandle<Object> Evaluate(
Handle<Module> module, ZoneForwardList<Handle<Module>>* stack,
unsigned* dfs_index);
static void MaybeTransitionComponent(Handle<Module> module,
ZoneForwardList<Handle<Module>>* stack,
Status new_status);
static V8_WARN_UNUSED_RESULT bool MaybeTransitionComponent(
Handle<Module> module, ZoneForwardList<Handle<Module>>* stack,
Status new_status);
// Set module's status back to kUninstantiated and reset other internal state.
// This is used when instantiation fails.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment