Force uv loop cleanup (#11465)
* ensure all uv handles are closed before ending worker's loop * add DCHECK to test that the Worker loop is finished * don't call deprecated uv_loop_new(), uv_loop_delete() * make cpplint happy * fix comment error * empty commit for CI * tweak DCHECK expression * extract-method: stop_and_close_uv_loop() * fix DCHECK oops
This commit is contained in:
parent
eb89e12c5b
commit
435c9c1486
2 changed files with 35 additions and 4 deletions
|
@ -64,6 +64,29 @@ REFERENCE_MODULE(atom_renderer_ipc);
|
||||||
REFERENCE_MODULE(atom_renderer_web_frame);
|
REFERENCE_MODULE(atom_renderer_web_frame);
|
||||||
#undef REFERENCE_MODULE
|
#undef REFERENCE_MODULE
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
void stop_and_close_uv_loop(uv_loop_t* loop) {
|
||||||
|
// Close any active handles
|
||||||
|
uv_stop(loop);
|
||||||
|
uv_walk(loop, [](uv_handle_t* handle, void*){
|
||||||
|
if (!uv_is_closing(handle)) {
|
||||||
|
uv_close(handle, nullptr);
|
||||||
|
}
|
||||||
|
}, nullptr);
|
||||||
|
|
||||||
|
// Run the loop to let it finish all the closing handles
|
||||||
|
// NB: after uv_stop(), uv_run(UV_RUN_DEFAULT) returns 0 when that's done
|
||||||
|
for (;;)
|
||||||
|
if (!uv_run(loop, UV_RUN_DEFAULT))
|
||||||
|
break;
|
||||||
|
|
||||||
|
DCHECK(!uv_loop_alive(loop));
|
||||||
|
uv_loop_close(loop);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace
|
||||||
|
|
||||||
namespace atom {
|
namespace atom {
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
@ -100,10 +123,15 @@ base::FilePath GetResourcesPath(bool is_browser) {
|
||||||
|
|
||||||
NodeBindings::NodeBindings(BrowserEnvironment browser_env)
|
NodeBindings::NodeBindings(BrowserEnvironment browser_env)
|
||||||
: browser_env_(browser_env),
|
: browser_env_(browser_env),
|
||||||
uv_loop_(browser_env == WORKER ? uv_loop_new() : uv_default_loop()),
|
|
||||||
embed_closed_(false),
|
embed_closed_(false),
|
||||||
uv_env_(nullptr),
|
uv_env_(nullptr),
|
||||||
weak_factory_(this) {
|
weak_factory_(this) {
|
||||||
|
if (browser_env == WORKER) {
|
||||||
|
uv_loop_init(&worker_loop_);
|
||||||
|
uv_loop_ = &worker_loop_;
|
||||||
|
} else {
|
||||||
|
uv_loop_ = uv_default_loop();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
NodeBindings::~NodeBindings() {
|
NodeBindings::~NodeBindings() {
|
||||||
|
@ -119,9 +147,9 @@ NodeBindings::~NodeBindings() {
|
||||||
uv_sem_destroy(&embed_sem_);
|
uv_sem_destroy(&embed_sem_);
|
||||||
uv_close(reinterpret_cast<uv_handle_t*>(&dummy_uv_handle_), nullptr);
|
uv_close(reinterpret_cast<uv_handle_t*>(&dummy_uv_handle_), nullptr);
|
||||||
|
|
||||||
// Destroy loop.
|
// Clean up worker loop
|
||||||
if (uv_loop_ != uv_default_loop())
|
if (uv_loop_ == &worker_loop_)
|
||||||
uv_loop_delete(uv_loop_);
|
stop_and_close_uv_loop(uv_loop_);
|
||||||
}
|
}
|
||||||
|
|
||||||
void NodeBindings::Initialize() {
|
void NodeBindings::Initialize() {
|
||||||
|
|
|
@ -85,6 +85,9 @@ class NodeBindings {
|
||||||
// Whether the libuv loop has ended.
|
// Whether the libuv loop has ended.
|
||||||
bool embed_closed_;
|
bool embed_closed_;
|
||||||
|
|
||||||
|
// Loop used when constructed in WORKER mode
|
||||||
|
uv_loop_t worker_loop_;
|
||||||
|
|
||||||
// Dummy handle to make uv's loop not quit.
|
// Dummy handle to make uv's loop not quit.
|
||||||
uv_async_t dummy_uv_handle_;
|
uv_async_t dummy_uv_handle_;
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue