[async_wrap] call destroy hooks on uv_timer_t#13369
[async_wrap] call destroy hooks on uv_timer_t#13369trevnorris merged 2 commits intonodejs:masterfrom
Conversation
93436c1 to
87ae33b
Compare
There was a problem hiding this comment.
Just fyi, the test from #13353 might be better because it uses AsyncResource to trigger the destroy call, so it doesn’t rely on .close() specifics.
There was a problem hiding this comment.
Ah thanks. And I can remove the setTimeout() at the bottom of the test.
src/async-wrap.cc
Outdated
There was a problem hiding this comment.
will this not call the destroy hook synchronously if emitDestroy was called from within the destroy hook? We don't want that because destroy hooks should never be called synchronously.
There was a problem hiding this comment.
@AndreasMadsen It would act like a nextTick(). The current execution scope would complete before the destroy hook was called.
There was a problem hiding this comment.
Yeah, that came to me a few hours after I wrote that. Thanks!
87ae33b to
fe1e23e
Compare
|
@addaleax Thanks for pointing to the other test. Also forgot to include your test for |
AndreasMadsen
left a comment
There was a problem hiding this comment.
LGTM, thanks for taking care of this.
fe1e23e to
a127045
Compare
a127045 to
5e4aaee
Compare
Calling the destroy callbacks in a uv_idle_t causes a timing issue where
if a handle or request is closed then the class isn't deleted until
uv_close() callbacks are called (which happens after the poll phase).
This results in some destroy callbacks not being called just before the
application exits. So instead switch the destroy callbacks to be called
in a uv_timer_t with the timeout set to zero.
When uv_run() is called with UV_RUN_ONCE the final operation of the
event loop is to process all remaining timers. By setting the timeout to
zero it results in the destroy callbacks being processed after
uv_close() but before uv_run() returned. Processing the destroyed ids
that were previously missed.
Also, process the destroy_ids_list() in a do {} while() loop that makes
sure the vector is empty before returning. Which also makes running
clear() unnecessary.
Fixes: nodejs#13262
PR-URL: nodejs#13369
Reviewed-By: Anna Henningsen <[email protected]>
Reviewed-By: Andreas Madsen <[email protected]>
Verify that the destroy callback for a TCP server is called before exit if it is closed in another destroy callback. Fixes: nodejs#13262 PR-URL: nodejs#13369 Reviewed-By: Trevor Norris <[email protected]> Reviewed-By: Andreas Madsen <[email protected]>
5e4aaee to
78b1358
Compare
Calling the destroy callbacks in a uv_idle_t causes a timing issue where
if a handle or request is closed then the class isn't deleted until
uv_close() callbacks are called (which happens after the poll phase).
This results in some destroy callbacks not being called just before the
application exits. So instead switch the destroy callbacks to be called
in a uv_timer_t with the timeout set to zero.
When uv_run() is called with UV_RUN_ONCE the final operation of the
event loop is to process all remaining timers. By setting the timeout to
zero it results in the destroy callbacks being processed after
uv_close() but before uv_run() returned. Processing the destroyed ids
that were previously missed.
Also, process the destroy_ids_list() in a do {} while() loop that makes
sure the vector is empty before returning. Which also makes running
clear() unnecessary.
Fixes: #13262
PR-URL: #13369
Reviewed-By: Anna Henningsen <[email protected]>
Reviewed-By: Andreas Madsen <[email protected]>
Verify that the destroy callback for a TCP server is called before exit if it is closed in another destroy callback. Fixes: #13262 PR-URL: #13369 Reviewed-By: Trevor Norris <[email protected]> Reviewed-By: Andreas Madsen <[email protected]>
Checklist
make -j4 test(UNIX), orvcbuild test(Windows) passesAffected core subsystem(s)
async_wrap
Summary
Calling the destroy callbacks in a
uv_idle_tcauses a timing issue whereif a handle or request is closed then the class isn't deleted until
uv_close()callbacks are called (which happens after the poll phase).This results in some destroy callbacks not being called just before the
application exits. So instead switch the destroy callbacks to be called
in a
uv_timer_twith the timeout set to zero.When
uv_run()is called withUV_RUN_ONCEthe final operation of theevent loop is to process all remaining timers. By setting the timeout to
zero it results in the destroy callbacks being processed after
uv_close()but beforeuv_run()returned. Processing the destroyed idsthat were previously missed.
Also, process the
destroy_ids_list()in ado {} while()loop that makessure the vector is empty before returning. Which also makes running
clear()unnecessary.Fixes: #13262
@addaleax Hope you don't mind that I added the relevant test you included in #13286 (left you as the committer, but altered the commit message)
CI: https://ci.nodejs.org/job/node-test-commit/10272/