From 8ddde4f05e1cc82209b6054fa8cfc4c4e0eb1788 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fr=C3=A9d=C3=A9ric=20L=C3=A9caille?= Date: Mon, 1 Aug 2022 14:07:50 +0200 Subject: [PATCH] BUG/MINOR: quic: Missing in flight ack eliciting packet counter decrement The decrement was missing in quic_pktns_tx_pkts_release() called each time a packet number space is discarded. This is not sure this bug could have an impact during handshakes. This counter is used to cancel the timer used both for packet detection and PTO, setting its value to null. So there could be retransmissions or probing which could be triggered for nothing. Must be backported to 2.6. --- include/haproxy/xprt_quic.h | 6 ++++-- src/xprt_quic.c | 2 +- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/include/haproxy/xprt_quic.h b/include/haproxy/xprt_quic.h index 9f42bd1153..ee08a7d8a6 100644 --- a/include/haproxy/xprt_quic.h +++ b/include/haproxy/xprt_quic.h @@ -542,7 +542,7 @@ static inline void quic_tx_packet_refdec(struct quic_tx_packet *pkt) } } -static inline void quic_pktns_tx_pkts_release(struct quic_pktns *pktns) +static inline void quic_pktns_tx_pkts_release(struct quic_pktns *pktns, struct quic_conn *qc) { struct eb64_node *node; @@ -553,6 +553,8 @@ static inline void quic_pktns_tx_pkts_release(struct quic_pktns *pktns) pkt = eb64_entry(node, struct quic_tx_packet, pn_node); node = eb64_next(node); + if (pkt->flags & QUIC_FL_TX_PACKET_ACK_ELICITING) + qc->path->ifae_pkts--; list_for_each_entry_safe(frm, frmbak, &pkt->frms, list) { LIST_DELETE(&frm->list); quic_tx_packet_refdec(frm->pkt); @@ -581,7 +583,7 @@ static inline void quic_pktns_discard(struct quic_pktns *pktns, pktns->tx.loss_time = TICK_ETERNITY; pktns->tx.pto_probe = 0; pktns->tx.in_flight = 0; - quic_pktns_tx_pkts_release(pktns); + quic_pktns_tx_pkts_release(pktns, qc); } /* Initialize

QUIC network path depending on boolean diff --git a/src/xprt_quic.c b/src/xprt_quic.c index 67ab817df5..a6e257d7af 100644 --- a/src/xprt_quic.c +++ b/src/xprt_quic.c @@ -4137,7 +4137,7 @@ static void quic_conn_release(struct quic_conn *qc) pool_free(pool_head_quic_tls_secret, app_tls_ctx->tx.secret); for (i = 0; i < QUIC_TLS_PKTNS_MAX; i++) { - quic_pktns_tx_pkts_release(&qc->pktns[i]); + quic_pktns_tx_pkts_release(&qc->pktns[i], qc); quic_free_arngs(&qc->pktns[i].rx.arngs); }