From: Christopher Faulet Date: Wed, 7 Oct 2026 09:53:15 +0000 (+0200) Subject: BUG/MEDIUM: mux-h1: only accept the H2 preface on the first request X-Git-Tag: v3.5-dev9~29 X-Git-Url: https://git.kaiwu.me/?a=commitdiff_plain;h=cec63e95f62a7412484f1134f5aa227e5b7e1466;p=haproxy.git BUG/MEDIUM: mux-h1: only accept the H2 preface on the first request The H1 to H2 upgrade via the H2 connection preface is only supported for the first request of a connection. It is checked by testing the absence of H1C_F_WAIT_NEXT_REQ, which is set on the H1 connection once a first transaction is finished. But this flag is moved to the H1 stream (H1S_F_NOT_FIRST) and removed from the connection as soon as a new H1 stream is created, which happens when the beginning of the next request is received. So when the preface of a second request is received in several parts (e.g. "PRI " then the rest), the first part creates an embryonic H1 stream and clears the flag, and the upgrade is then accepted when the complete preface is received. The connection is upgraded to H2 in the middle of its life, while the end of the previous response may still be pending in the output buffer (it is then lost). Now the H1 stream's H1S_F_NOT_FIRST flag is also checked. This was introduced by commit 39c7b6b09 ("MEDIUM: mux-h1: Add ST_READY state for the H1 connections") in 2.4. It may be backported to all stable versions. --- diff --git a/src/mux_h1.c b/src/mux_h1.c index 0538088dd..0b0911450 100644 --- a/src/mux_h1.c +++ b/src/mux_h1.c @@ -4228,7 +4228,8 @@ static int h1_process(struct h1c * h1c) */ if (h1c->state != H1_CS_DRAINING && b_isteq(&h1c->ibuf, 0, b_data(&h1c->ibuf), ist(H2_CONN_PREFACE)) > 0) { - if (!(h1c->flags & H1C_F_WAIT_NEXT_REQ) && /* First request */ + if (!(h1c->flags & H1C_F_WAIT_NEXT_REQ) && /* First request (the flag is */ + !(h1s && (h1s->flags & H1S_F_NOT_FIRST)) && /* moved to the h1s once created) */ !(h1c->px->options2 & PR_O2_NO_H2_UPGRADE) && /* H2 upgrade supported by the proxy */ !(conn->mux->flags & MX_FL_NO_UPG)) { /* the current mux supports upgrades */ h1c->flags |= H1C_F_UPG_H2C;