MINOR: quic: split global CID tree between FE and BE sides

QUIC CIDs are stored in a global tree. Prior to this patch, CIDs used on
both frontend and backend sides were mixed together.

This patch implement CID storage separation between FE and BE sides. The
original tre quic_cid_trees is splitted as
quic_fe_cid_trees/quic_be_cid_trees.

This patch should reduce contention between frontend and backend usages.
Also, it should reduce the risk of random CID collision.
This commit is contained in:
Amaury Denoyelle
2025-11-21 17:21:26 +01:00
parent 4b596c1ea8
commit a5801e542d
7 changed files with 87 additions and 33 deletions

View File

@@ -24,6 +24,12 @@ struct quic_cid {
unsigned char len; /* size of QUIC CID */
};
/* Determines whether a CID is used for frontend or backend connections. */
enum quic_cid_side {
QUIC_CID_SIDE_FE,
QUIC_CID_SIDE_BE
};
/* QUIC connection id attached to a QUIC connection.
*
* This structure is used to match received packets DCIDs with the
@@ -34,11 +40,12 @@ struct quic_connection_id {
uint64_t retire_prior_to;
unsigned char stateless_reset_token[QUIC_STATELESS_RESET_TOKEN_LEN];
struct ebmb_node node; /* node for receiver tree, cid.data as key */
struct quic_cid cid; /* CID data */
struct ebmb_node node; /* node for receiver tree, cid.data as key */
struct quic_cid cid; /* CID data */
struct quic_conn *qc; /* QUIC connection using this CID */
uint tid; /* Attached Thread ID for the connection. */
struct quic_conn *qc; /* QUIC connection using this CID */
uint tid; /* Attached Thread ID for the connection. */
enum quic_cid_side side; /* side where this CID is used */
};
#endif /* _HAPROXY_QUIC_CID_T_H */

View File

@@ -15,9 +15,10 @@
#include <haproxy/quic_rx-t.h>
#include <haproxy/proto_quic.h>
extern struct quic_cid_tree *quic_cid_trees;
extern struct quic_cid_tree *quic_fe_cid_trees;
extern struct quic_cid_tree *quic_be_cid_trees;
struct quic_connection_id *quic_cid_alloc(void);
struct quic_connection_id *quic_cid_alloc(enum quic_cid_side side);
int quic_cid_generate_random(struct quic_connection_id *conn_id);
int quic_cid_generate_from_hash(struct quic_connection_id *conn_id, uint64_t hash64);
@@ -81,11 +82,18 @@ static inline uchar quic_cid_tree_idx(const struct quic_cid *cid)
return _quic_cid_tree_idx(cid->data);
}
/* Returns the tree instance responsible for <conn_id> storage. */
static inline struct quic_cid_tree *quic_cid_get_tree(const struct quic_connection_id *conn_id)
{
const int tree_idx = quic_cid_tree_idx(&conn_id->cid);
return conn_id->side == QUIC_CID_SIDE_FE ?
&quic_fe_cid_trees[tree_idx] : &quic_be_cid_trees[tree_idx];
}
/* Remove <conn_id> from global CID tree as a thread-safe operation. */
static inline void quic_cid_delete(struct quic_connection_id *conn_id)
{
const uchar idx = quic_cid_tree_idx(&conn_id->cid);
struct quic_cid_tree __maybe_unused *tree = &quic_cid_trees[idx];
struct quic_cid_tree __maybe_unused *tree = quic_cid_get_tree(conn_id);
HA_RWLOCK_WRLOCK(QC_CID_LOCK, &tree->lock);
ebmb_delete(&conn_id->node);

View File

@@ -91,6 +91,12 @@ static inline int qc_is_back(const struct quic_conn *qc)
return qc->flags & QUIC_FL_CONN_IS_BACK;
}
static inline enum quic_cid_side qc_cid_side(const struct quic_conn *qc)
{
return !(qc->flags & QUIC_FL_CONN_IS_BACK) ?
QUIC_CID_SIDE_FE : QUIC_CID_SIDE_BE;
}
/* Free the CIDs attached to <conn> QUIC connection. */
static inline void free_quic_conn_cids(struct quic_conn *conn)
{