From deb7c87f5525d5645dd7c94fb187603edbb8d27a Mon Sep 17 00:00:00 2001 From: Amaury Denoyelle Date: Wed, 19 Oct 2022 17:14:28 +0200 Subject: [PATCH] MINOR: quic: define first packet flag Received packets treatment has some difference regarding if this is the first one or not of the encapsulating datagram. Previously, this was set via a function argument. Simplify this by defining a new Rx packet flag named QUIC_FL_RX_PACKET_DGRAM_FIRST. This change does not have functional impact. It will simplify API when qc_lstnr_pkt_rcv() is broken into several functions : their number of arguments will be reduced thanks to this patch. This should be backported up to 2.6. --- include/haproxy/quic_conn-t.h | 2 ++ src/quic_conn.c | 23 ++++++++++++++--------- 2 files changed, 16 insertions(+), 9 deletions(-) diff --git a/include/haproxy/quic_conn-t.h b/include/haproxy/quic_conn-t.h index 15568631d..b493f85f9 100644 --- a/include/haproxy/quic_conn-t.h +++ b/include/haproxy/quic_conn-t.h @@ -391,6 +391,8 @@ struct quic_dgram { #define QUIC_MAX_RX_AEPKTS_SINCE_LAST_ACK 2 /* Flag a received packet as being an ack-eliciting packet. */ #define QUIC_FL_RX_PACKET_ACK_ELICITING (1UL << 0) +/* Packet is the first one in the containing datagram. */ +#define QUIC_FL_RX_PACKET_DGRAM_FIRST (1UL << 1) struct quic_rx_packet { struct list list; diff --git a/src/quic_conn.c b/src/quic_conn.c index 3f1e180bc..203a36747 100644 --- a/src/quic_conn.c +++ b/src/quic_conn.c @@ -5937,8 +5937,9 @@ static inline int quic_padding_check(const unsigned char *buf, * bytes in the datagram to entirely consume this latter. */ static void qc_lstnr_pkt_rcv(unsigned char *buf, const unsigned char *end, - struct quic_rx_packet *pkt, int first_pkt, - struct quic_dgram *dgram, struct list **tasklist_head) + struct quic_rx_packet *pkt, + struct quic_dgram *dgram, + struct list **tasklist_head) { unsigned char *beg; struct quic_conn *qc; @@ -5970,7 +5971,8 @@ static void qc_lstnr_pkt_rcv(unsigned char *buf, const unsigned char *end, /* Fixed bit */ if (!(*buf & QUIC_PACKET_FIXED_BIT)) { - if (!first_pkt && quic_padding_check(buf, end)) { + if (!(pkt->flags & QUIC_FL_RX_PACKET_DGRAM_FIRST) && + quic_padding_check(buf, end)) { /* Some browsers may pad the remaining datagram space with null bytes. * That is what we called add padding out of QUIC packets. Such * datagrams must be considered as valid. But we can only consume @@ -6015,7 +6017,7 @@ static void qc_lstnr_pkt_rcv(unsigned char *buf, const unsigned char *end, /* When multiple QUIC packets are coalesced on the same UDP datagram, * they must have the same DCID. */ - if (!first_pkt && + if (!(pkt->flags & QUIC_FL_RX_PACKET_DGRAM_FIRST) && (pkt->dcid.len != dgram->dcid_len || memcmp(dgram->dcid, pkt->dcid.data, pkt->dcid.len))) { TRACE_PROTO("Packet dropped", QUIC_EV_CONN_LPKT, qc); @@ -6196,7 +6198,7 @@ static void qc_lstnr_pkt_rcv(unsigned char *buf, const unsigned char *end, /* When multiple QUIC packets are coalesced on the same UDP datagram, * they must have the same DCID. */ - if (!first_pkt && + if (!(pkt->flags & QUIC_FL_RX_PACKET_DGRAM_FIRST) && (pkt->dcid.len != dgram->dcid_len || memcmp(dgram->dcid, pkt->dcid.data, pkt->dcid.len))) { TRACE_PROTO("Packet dropped", QUIC_EV_CONN_LPKT, qc); @@ -6240,7 +6242,8 @@ static void qc_lstnr_pkt_rcv(unsigned char *buf, const unsigned char *end, * This check must be done after the final update to pkt.len to * properly drop the packet on failure. */ - if (first_pkt && !quic_peer_validated_addr(qc) && + if (pkt->flags & QUIC_FL_RX_PACKET_DGRAM_FIRST && + !quic_peer_validated_addr(qc) && qc->flags & QUIC_FL_CONN_ANTI_AMPLIFICATION_REACHED) { TRACE_PROTO("PTO timer must be armed after anti-amplication was reached", QUIC_EV_CONN_LPKT, qc, NULL, NULL, qv); @@ -7167,7 +7170,6 @@ struct task *quic_lstnr_dghdlr(struct task *t, void *ctx, unsigned int state) const unsigned char *end; struct quic_dghdlr *dghdlr = ctx; struct quic_dgram *dgram; - int first_pkt = 1; struct list *tasklist_head = NULL; int max_dgrams = global.tune.maxpollevents; @@ -7190,11 +7192,14 @@ struct task *quic_lstnr_dghdlr(struct task *t, void *ctx, unsigned int state) pkt->version = NULL; pkt->pn_offset = 0; + /* Set flag if pkt is the first one in dgram. */ + if (pos == dgram->buf) + pkt->flags |= QUIC_FL_RX_PACKET_DGRAM_FIRST; + LIST_INIT(&pkt->qc_rx_pkt_list); pkt->time_received = now_ms; quic_rx_packet_refinc(pkt); - qc_lstnr_pkt_rcv(pos, end, pkt, first_pkt, dgram, &tasklist_head); - first_pkt = 0; + qc_lstnr_pkt_rcv(pos, end, pkt, dgram, &tasklist_head); pos += pkt->len; quic_rx_packet_refdec(pkt);