mirror of
http://git.haproxy.org/git/haproxy.git/
synced 2025-02-15 10:06:55 +00:00
MEDIUM: stream-int: queue idle connections at the server
Now we get a per-server list of all idle connections. That way we'll be able to reclaim them upon shortage later.
This commit is contained in:
parent
d75d40e9a8
commit
323a2d925c
@ -25,6 +25,7 @@
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <common/config.h>
|
||||
#include <types/server.h>
|
||||
#include <types/stream.h>
|
||||
#include <types/stream_interface.h>
|
||||
#include <proto/applet.h>
|
||||
@ -154,6 +155,7 @@ static inline void si_release_endpoint(struct stream_interface *si)
|
||||
return;
|
||||
|
||||
if ((conn = objt_conn(si->end))) {
|
||||
LIST_DEL(&conn->list);
|
||||
conn_force_close(conn);
|
||||
conn_free(conn);
|
||||
}
|
||||
@ -167,15 +169,19 @@ static inline void si_release_endpoint(struct stream_interface *si)
|
||||
|
||||
/* Turn a possibly existing connection endpoint of stream interface <si> to
|
||||
* idle mode, which means that the connection will be polled for incoming events
|
||||
* and might be killed by the underlying I/O handler.
|
||||
* and might be killed by the underlying I/O handler. If <pool> is not null, the
|
||||
* connection will also be added at the head of this list.
|
||||
*/
|
||||
static inline void si_idle_conn(struct stream_interface *si)
|
||||
static inline void si_idle_conn(struct stream_interface *si, struct list *pool)
|
||||
{
|
||||
struct connection *conn = objt_conn(si->end);
|
||||
|
||||
if (!conn)
|
||||
return;
|
||||
|
||||
if (pool)
|
||||
LIST_ADD(pool, &conn->list);
|
||||
|
||||
conn_attach(conn, si, &si_idle_conn_cb);
|
||||
conn_data_want_recv(conn);
|
||||
}
|
||||
|
@ -1052,6 +1052,11 @@ int connect_server(struct stream *s)
|
||||
|
||||
if (!reuse)
|
||||
srv_conn = si_alloc_conn(&s->si[1]);
|
||||
else {
|
||||
/* reusing our connection, take it out of the idle list */
|
||||
LIST_DEL(&srv_conn->list);
|
||||
LIST_INIT(&srv_conn->list);
|
||||
}
|
||||
|
||||
if (!srv_conn)
|
||||
return SF_ERR_RESOURCE;
|
||||
|
@ -5030,12 +5030,15 @@ void http_end_txn_clean_session(struct stream *s)
|
||||
{
|
||||
int prev_status = s->txn->status;
|
||||
struct proxy *fe = strm_fe(s);
|
||||
struct connection *srv_conn;
|
||||
struct server *srv;
|
||||
|
||||
/* FIXME: We need a more portable way of releasing a backend's and a
|
||||
* server's connections. We need a safer way to reinitialize buffer
|
||||
* flags. We also need a more accurate method for computing per-request
|
||||
* data.
|
||||
*/
|
||||
srv_conn = objt_conn(s->si[1].end);
|
||||
|
||||
/* unless we're doing keep-alive, we want to quickly close the connection
|
||||
* to the server.
|
||||
@ -5125,6 +5128,7 @@ void http_end_txn_clean_session(struct stream *s)
|
||||
if (((s->txn->flags & TX_CON_WANT_MSK) != TX_CON_WANT_KAL) ||
|
||||
!si_conn_ready(&s->si[1])) {
|
||||
si_release_endpoint(&s->si[1]);
|
||||
srv_conn = NULL;
|
||||
}
|
||||
|
||||
s->si[1].state = s->si[1].prev_state = SI_ST_INI;
|
||||
@ -5182,7 +5186,11 @@ void http_end_txn_clean_session(struct stream *s)
|
||||
channel_auto_close(&s->res);
|
||||
|
||||
/* we're in keep-alive with an idle connection, monitor it */
|
||||
si_idle_conn(&s->si[1]);
|
||||
srv = NULL;
|
||||
if (srv_conn)
|
||||
srv = objt_server(srv_conn->target);
|
||||
|
||||
si_idle_conn(&s->si[1], srv ? &srv->priv_conns : NULL);
|
||||
|
||||
s->req.analysers = strm_li(s)->analysers;
|
||||
s->res.analysers = 0;
|
||||
|
@ -515,6 +515,7 @@ static int si_idle_conn_wake_cb(struct connection *conn)
|
||||
|
||||
if (conn->flags & (CO_FL_ERROR | CO_FL_SOCK_RD_SH)) {
|
||||
/* warning, we can't do anything on <conn> after this call ! */
|
||||
LIST_DEL(&conn->list);
|
||||
conn_force_close(conn);
|
||||
conn_free(conn);
|
||||
si->end = NULL;
|
||||
|
Loading…
Reference in New Issue
Block a user