diff --git a/include/proto/connection.h b/include/proto/connection.h index 0b4a0d845..ade699401 100644 --- a/include/proto/connection.h +++ b/include/proto/connection.h @@ -558,6 +558,7 @@ static inline void conn_init(struct connection *conn) conn->destroy_cb = NULL; conn->proxy_netns = NULL; LIST_INIT(&conn->list); + LIST_INIT(&conn->session_list); conn->send_wait = NULL; conn->recv_wait = NULL; } @@ -664,6 +665,13 @@ static inline void conn_force_unsubscribe(struct connection *conn) /* Releases a connection previously allocated by conn_new() */ static inline void conn_free(struct connection *conn) { + struct session *sess, *sess_back; + + list_for_each_entry_safe(sess, sess_back, &conn->session_list, conn_list) { + sess->srv_conn = NULL; + LIST_DEL(&sess->conn_list); + LIST_INIT(&sess->conn_list); + } conn_force_unsubscribe(conn); pool_free(pool_head_connection, conn); } diff --git a/include/types/connection.h b/include/types/connection.h index 2ed39f69c..a85343bdd 100644 --- a/include/types/connection.h +++ b/include/types/connection.h @@ -408,6 +408,7 @@ struct connection { struct wait_event *send_wait; /* Task to wake when we're ready to send */ struct wait_event *recv_wait; /* Task to wake when we're ready to recv */ struct list list; /* attach point to various connection lists (idle, ...) */ + struct list session_list; /* List of all sessions attached to this connection */ int xprt_st; /* transport layer state, initialized to zero */ int tmp_early_data; /* 1st byte of early data, if any */ int sent_early_data; /* Amount of early data we sent so far */ diff --git a/include/types/session.h b/include/types/session.h index c3bace85c..e0e145564 100644 --- a/include/types/session.h +++ b/include/types/session.h @@ -47,6 +47,8 @@ struct session { struct vars vars; /* list of variables for the session scope. */ struct task *task; /* handshake timeout processing */ long t_handshake; /* handshake duration, -1 = not completed */ + struct connection *srv_conn; /* Server connection we last used */ + struct list conn_list; /* List element for the session list in each connection */ }; #endif /* _TYPES_SESSION_H */ diff --git a/src/session.c b/src/session.c index afab68add..d8c8d36cf 100644 --- a/src/session.c +++ b/src/session.c @@ -53,6 +53,8 @@ struct session *session_new(struct proxy *fe, struct listener *li, enum obj_type vars_init(&sess->vars, SCOPE_SESS); sess->task = NULL; sess->t_handshake = -1; /* handshake not done yet */ + LIST_INIT(&sess->conn_list); + sess->srv_conn = NULL; HA_ATOMIC_UPDATE_MAX(&fe->fe_counters.conn_max, HA_ATOMIC_ADD(&fe->feconn, 1)); if (li)