Observed while implementing and testing WebTransport session close, but the issue appears broader than WebTransport.
Problem:
- When a peer receives
STOP_SENDING on a bidirectional stream, lsquic appears to tear down stream state aggressively enough that subsequently arriving application data on the opposite direction may no longer be delivered to user code.
- In our WT case, this means a peer can receive
STOP_SENDING for the CONNECT stream before the WT_CLOSE_SESSION capsule bytes are processed, so the close capsule is never surfaced to the application.
Why this matters beyond WT:
- The same pattern can happen in HTTP/3. Example: client uploads a large POST body; server decides it is too large, sends a response (e.g. 413 with response body), and also sends
STOP_SENDING to stop the upload. If the client discards incoming response data because STOP_SENDING was processed first, that is incorrect for a bidi request/response stream.
Spec context:
- QUIC
STOP_SENDING is directional: it asks the peer to stop transmitting on that stream and send RESET_STREAM.
- It should not by itself imply that already-received or subsequently-arriving data in the opposite direction becomes irrelevant for the application on a bidirectional stream.
Concrete WT manifestation:
- Client sends
WT_CLOSE_SESSION capsule on the CONNECT stream and then STOP_SENDING WT_SESSION_GONE.
- Server processes
STOP_SENDING first and resets/closes the CONNECT stream before the capsule bytes are delivered to WT capsule handling.
- Result: session closes with code 0 / empty reason instead of the application-provided close reason.
Suggested investigation:
- Audit how incoming
STOP_SENDING is handled for bidi streams.
- Verify whether stream teardown on received
STOP_SENDING is collapsing both directions too early.
- Add a regression test around a bidi stream where one side sends
STOP_SENDING while the other direction still carries meaningful response/application data.
This is likely a stream-layer behavioral issue rather than something specific to WebTransport.
Observed while implementing and testing WebTransport session close, but the issue appears broader than WebTransport.
Problem:
STOP_SENDINGon a bidirectional stream, lsquic appears to tear down stream state aggressively enough that subsequently arriving application data on the opposite direction may no longer be delivered to user code.STOP_SENDINGfor the CONNECT stream before theWT_CLOSE_SESSIONcapsule bytes are processed, so the close capsule is never surfaced to the application.Why this matters beyond WT:
STOP_SENDINGto stop the upload. If the client discards incoming response data becauseSTOP_SENDINGwas processed first, that is incorrect for a bidi request/response stream.Spec context:
STOP_SENDINGis directional: it asks the peer to stop transmitting on that stream and sendRESET_STREAM.Concrete WT manifestation:
WT_CLOSE_SESSIONcapsule on the CONNECT stream and thenSTOP_SENDING WT_SESSION_GONE.STOP_SENDINGfirst and resets/closes the CONNECT stream before the capsule bytes are delivered to WT capsule handling.Suggested investigation:
STOP_SENDINGis handled for bidi streams.STOP_SENDINGis collapsing both directions too early.STOP_SENDINGwhile the other direction still carries meaningful response/application data.This is likely a stream-layer behavioral issue rather than something specific to WebTransport.