diff --git a/include/haproxy/connection-t.h b/include/haproxy/connection-t.h index 2f3296d3b..531405607 100644 --- a/include/haproxy/connection-t.h +++ b/include/haproxy/connection-t.h @@ -526,7 +526,9 @@ struct connection { /* second cache line */ struct wait_event *subs; /* Task to wake when awaited events are ready */ struct mt_list toremove_list; /* list for connection to clean up */ - struct list session_list; /* List of attached connections to a session */ + union { + struct list session_list; /* used by backend conns, list of attached connections to a session */ + }; union conn_handle handle; /* connection handle at the socket layer */ const struct netns_entry *proxy_netns; diff --git a/include/haproxy/connection.h b/include/haproxy/connection.h index ae5f636c6..296da89e5 100644 --- a/include/haproxy/connection.h +++ b/include/haproxy/connection.h @@ -343,6 +343,15 @@ static inline void cs_init(struct conn_stream *cs, struct connection *conn) cs->conn = conn; } +/* returns 0 if the connection is valid and is a frontend connection, otherwise + * returns 1 indicating it's a backend connection. And uninitialized connection + * also returns 1 to better handle the usage in the middle of initialization. + */ +static inline int conn_is_back(const struct connection *conn) +{ + return !objt_listener(conn->target); +} + /* Initializes all required fields for a new connection. Note that it does the * minimum acceptable initialization for a connection that already exists and * is about to be reused. It also leaves the addresses untouched, which makes @@ -362,7 +371,8 @@ static inline void conn_init(struct connection *conn, void *target) conn->destroy_cb = NULL; conn->proxy_netns = NULL; MT_LIST_INIT(&conn->toremove_list); - LIST_INIT(&conn->session_list); + if (conn_is_back(conn)) + LIST_INIT(&conn->session_list); conn->subs = NULL; conn->src = NULL; conn->dst = NULL; @@ -440,15 +450,6 @@ static inline void sockaddr_free(struct sockaddr_storage **sap) *sap = NULL; } -/* returns 0 if the connection is valid and is a frontend connection, otherwise - * returns 1 indicating it's a backend connection. And uninitialized connection - * also returns 1 to better handle the usage in the middle of initialization. - */ -static inline int conn_is_back(const struct connection *conn) -{ - return !objt_listener(conn->target); -} - /* Tries to allocate a new connection and initialized its main fields. The * connection is returned on success, NULL on failure. The connection must * be released using pool_free() or conn_free(). @@ -545,7 +546,7 @@ static inline void conn_free(struct connection *conn) { /* If the connection is owned by the session, remove it from its list */ - if (LIST_INLIST(&conn->session_list)) { + if (conn_is_back(conn) && LIST_INLIST(&conn->session_list)) { session_unown_conn(conn->owner, conn); } else if (!(conn->flags & CO_FL_PRIVATE)) { diff --git a/include/haproxy/session.h b/include/haproxy/session.h index 6b289e2b7..1842b7aa7 100644 --- a/include/haproxy/session.h +++ b/include/haproxy/session.h @@ -116,6 +116,8 @@ static inline void session_unown_conn(struct session *sess, struct connection *c { struct sess_srv_list *srv_list = NULL; + BUG_ON(objt_listener(conn->target)); + /* WT: this currently is a workaround for an inconsistency between * the link status of the connection in the session list and the * connection's owner. This should be removed as soon as all this @@ -151,6 +153,8 @@ static inline int session_add_conn(struct session *sess, struct connection *conn struct sess_srv_list *srv_list = NULL; int found = 0; + BUG_ON(objt_listener(conn->target)); + /* Already attach to the session or not the connection owner */ if (!LIST_ISEMPTY(&conn->session_list) || (conn->owner && conn->owner != sess)) return 1;