Close a dropped TCP session without blocking on its task - #86
Open
IntellyCode wants to merge 1 commit into
Open
Conversation
`IpStackTcpStream::drop` waited for the session's task to finish, through `block_in_place` and `block_on`. `block_in_place` works by handing the worker's core to the blocking pool, and the pool stops accepting work once the runtime begins shutting down. A session dropped from that point on blocks its worker forever: the core is never handed off, the task it waits for has no thread left to run on, and the runtime's own shutdown waits for that worker in turn. The farewell packet reaches the device through an unbounded channel, so it is sent from the drop itself. The task is told to exit through the channel it already watches, and aborted rather than awaited. Aborting drops the task's `destroy_messenger`, and the watcher that removes the session treats a dropped sender the same as a sent one, so the session still leaves the stack.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
IpStackTcpStream::dropwaits for the session's task throughblock_in_placeandblock_on.block_in_placeworks by handing the worker's core to the blocking pool, but the pool stops accepting work as soon as the runtime starts shutting down. A session dropped from that point on blocks its worker forever — the core is never handed off, so the task being waited for has no thread left to run on, and the runtime's shutdown is itself waiting for that worker. For a TUN proxy this happens on every exit with open connections: a handful of sessions usually gets away with it, a few hundred hangs the process for good. On a current-thread runtime the same line panics instead, which aborts the process from insideDrop.This keeps what the waiting was for and drops the waiting.
send_fin_n_change_state_to_fin_wait1is synchronous and writes to an unbounded channel, so the farewell packet is sent from the drop itself, under the same state guard. The exit signal becomestry_send, and the task is aborted rather than awaited — which drops itsdestroy_messenger, and since the watcher doesrx.await.ok(), the session still leaves the stack.