From 8f64b8164338c231662be8e5ea207f07dae5828f Mon Sep 17 00:00:00 2001 From: Momtchil Momtchev Date: Wed, 6 Jul 2022 00:35:27 +0200 Subject: [PATCH] keep open the context scope --- src/js_native_api_v8.cc | 33 ++++++++++++++++++++------------- test/embedding/napi_embedding.c | 6 ++++++ 2 files changed, 26 insertions(+), 13 deletions(-) diff --git a/src/js_native_api_v8.cc b/src/js_native_api_v8.cc index 179a76ad0ac380..ab989a76c40a05 100644 --- a/src/js_native_api_v8.cc +++ b/src/js_native_api_v8.cc @@ -128,13 +128,26 @@ class EnvironmentInstanceData { std::unique_ptr&& setup) : setup_(std::move(setup)), locker(setup_->isolate()), - isolate_scope(setup_->isolate()) {} + isolate_scope(setup_->isolate()), + handle_scope(setup_->isolate()), + context_scope(setup_->context()), + seal_scope(nullptr) {} node::CommonEnvironmentSetup* setup() { return setup_.get(); } + inline void seal() { + seal_scope = + std::make_unique(setup_->isolate()); + } private: std::unique_ptr setup_; v8::Locker locker; v8::Isolate::Scope isolate_scope; + v8::HandleScope handle_scope; + v8::Context::Scope context_scope; + // As this handle scope will remain open for the lifetime + // of the environment, we seal it to prevent it from + // becoming everyone's favorite trash bin + std::unique_ptr seal_scope; }; class HandleScopeWrapper { @@ -869,32 +882,26 @@ napi_status NAPI_CDECL napi_create_environment(napi_platform platform, auto wrapper = reinterpret_cast(platform); std::vector errors_vec; - auto instance_data = new v8impl::EnvironmentInstanceData( - node::CommonEnvironmentSetup::Create(wrapper->platform.get(), - &errors_vec, - wrapper->args, - wrapper->exec_args)); - - if (instance_data->setup() == nullptr) { + auto setup = node::CommonEnvironmentSetup::Create( + wrapper->platform.get(), &errors_vec, wrapper->args, wrapper->exec_args); + if (setup == nullptr) { HANDLE_ERRORS_VECTOR(errors, errors_vec); return napi_generic_failure; } - - v8::HandleScope handle_scope(instance_data->setup()->isolate()); - v8::Local context = instance_data->setup()->context(); - v8::Context::Scope context_scope(context); + auto instance_data = new v8impl::EnvironmentInstanceData(std::move(setup)); v8::MaybeLocal loadenv_ret = node::LoadEnvironment(instance_data->setup()->env(), main_script); std::string filename = wrapper->args.size() > 1 ? wrapper->args[1] : ""; - auto env__ = new node_napi_env__(context, filename); + auto env__ = new node_napi_env__(instance_data->setup()->context(), filename); env__->instance_data = reinterpret_cast(instance_data); env__->node_env()->AddCleanupHook( [](void* arg) { static_cast(arg)->Unref(); }, static_cast(env__)); *result = env__; + instance_data->seal(); if (loadenv_ret.IsEmpty()) return napi_pending_exception; return napi_ok; diff --git a/test/embedding/napi_embedding.c b/test/embedding/napi_embedding.c index d05bccb02e6d7b..84d4cf404fc9ab 100644 --- a/test/embedding/napi_embedding.c +++ b/test/embedding/napi_embedding.c @@ -85,6 +85,12 @@ int callMe(napi_env env) { return -1; } + napi_value object; + if (napi_create_object(env, &object) != napi_ok) { + fprintf(stderr, "Failed creating an object\n"); + return -1; + } + napi_close_handle_scope(env, scope); return 0; }