Skip to content

long headers from the server hang tonic #1834

Closed
@ajwerner

Description

@ajwerner

Bug Report

Version

0.12.1

Platform

Linux pc 6.5.0-42-generic #42-Ubuntu SMP PREEMPT_DYNAMIC Mon Jun 10 09:28:55 UTC 2024 x86_64 x86_64 x86_64 GNU/Linux

Description

Long error messages corrupt h2 streams in some way. I noticed this primarily because the upgrade in 9c1f2f9 / #1670 changed the default maximum header size from 16MiB to 16KiB. For bidirectional streaming, I first get the error message, "h2 protocol error: http2 error", but later streams on that connection seem somewhat busted. For unary RPCs, it seems that even the first request just hangs as opposed to the client getting an error. When I've debugged this, I've found that the client resets the stream, but then things just hang.

I've written a simple test that just hangs to demonstrate the issue:

tests/integration_tests/tests/status.rs

#[tokio::test]
async fn long_error_message() {
    struct Svc;

    const N: usize = 100_000;

    #[tonic::async_trait]
    impl test_server::Test for Svc {
        async fn unary_call(&self, _: Request<Input>) -> Result<Response<Output>, Status> {
            Err(Status::internal("a".repeat(N)))
        }
    }

    let svc = test_server::TestServer::new(Svc);

    let (tx, rx) = oneshot::channel::<()>();

    let jh = tokio::spawn(async move {
        Server::builder()
            .add_service(svc)
            .serve_with_shutdown("127.0.0.1:1340".parse().unwrap(), async { drop(rx.await) })
            .await
            .unwrap();
    });

    tokio::time::sleep(Duration::from_millis(100)).await;

    let mut channel = test_client::TestClient::connect("http://127.0.0.1:1340")
        .await
        .unwrap();

    // !!! This call never finishes!
    let err = channel
        .unary_call(Request::new(Input {}))
        .await
        .unwrap_err();

    assert_eq!(err.message(), "a".repeat(N));

    tx.send(()).unwrap();

    jh.await.unwrap();
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions