hyperium / h2

HTTP 2.0 client & server implementation for Rust.
MIT License
1.34k stars 269 forks source link

Stream `poll_write()` sometimes returning `Poll::Ready(Ok(0))` on large transfers #595

Closed jvimal-eg closed 2 years ago

jvimal-eg commented 2 years ago

Encountering a weird issue where a h2 stream that's upgraded used to work with h2 0.3.7, but fails with 0.3.9. (Didn't try 0.3.8 as I hit the connection hanging issue #584.)

I have a h2 stream that received a CONNECT request to host:port and subsequently upgraded. I then use tokio's copy function to copy bytes back and forth between the stream and the host:port TCP connection. For large file (> 20MB or so) downloads, write() to the stream fails and hits this error: https://github.com/tokio-rs/tokio-io/blob/master/src/copy.rs#L75-L78.

poll_write() shouldn't return Poll::Ready(Ok(0)), but Poll::Pending... I suspect it's related to the recent send buffer size changes, but can't put my finger on the line that's causing the issue.

seanmonstar commented 2 years ago

Are you referring to hyper::upgrade::Upgraded? I'm not sure of any type exposed in the h2 crate that has a poll_write method.

jvimal-eg commented 2 years ago

Yes, it's a hyper::upgrade::Upgraded instance that's backed by a h2 stream. A hyper::upgrade::Upgrade instance over a http/1.1 connection works just fine.

nox commented 2 years ago

This happens when poll_capacity returns Ok(0).

https://github.com/hyperium/hyper/blob/6169db250c932dd012d391389826cd34833077b4/src/proto/h2/mod.rs#L352-L364

nox commented 2 years ago

So this is a duplicate of https://github.com/hyperium/h2/issues/270.