tcp: Unify tcp_defer_handler and tcp_splice_defer_handler()
These two functions each step through non-spliced and spliced connections respectively and clean up entries for closed connections. To avoid scanning the connection table twice, we merge these into a single function which scans the unified table and performs the appropriate sort of cleanup action on each one. Signed-off-by: David Gibson <david@gibson.dropbear.id.au> Signed-off-by: Stefano Brivio <sbrivio@redhat.com>
This commit is contained in:
parent
ee8f8e9564
commit
0eef48c4be
4 changed files with 13 additions and 33 deletions
20
tcp.c
20
tcp.c
|
@ -1527,21 +1527,23 @@ void tcp_defer_handler(struct ctx *c)
|
||||||
{
|
{
|
||||||
int max_conns = c->tcp.conn_count / 100 * TCP_CONN_PRESSURE;
|
int max_conns = c->tcp.conn_count / 100 * TCP_CONN_PRESSURE;
|
||||||
int max_files = c->nofile / 100 * TCP_FILE_PRESSURE;
|
int max_files = c->nofile / 100 * TCP_FILE_PRESSURE;
|
||||||
struct tcp_tap_conn *conn;
|
union tcp_conn *conn;
|
||||||
|
|
||||||
tcp_l2_flags_buf_flush(c);
|
tcp_l2_flags_buf_flush(c);
|
||||||
tcp_l2_data_buf_flush(c);
|
tcp_l2_data_buf_flush(c);
|
||||||
|
|
||||||
tcp_splice_defer_handler(c);
|
if ((c->tcp.conn_count < MIN(max_files, max_conns)) &&
|
||||||
|
(c->tcp.splice_conn_count < MIN(max_files / 6, max_conns)))
|
||||||
if (c->tcp.conn_count < MIN(max_files, max_conns))
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
for (conn = CONN(c->tcp.conn_count - 1); conn >= CONN(0); conn--) {
|
for (conn = tc + c->tcp.conn_count - 1; conn >= tc; conn--) {
|
||||||
if (conn->c.spliced)
|
if (conn->c.spliced) {
|
||||||
continue;
|
if (conn->splice.flags & CLOSING)
|
||||||
if (conn->events == CLOSED)
|
tcp_splice_destroy(c, &conn->splice);
|
||||||
tcp_conn_destroy(c, conn);
|
} else {
|
||||||
|
if (conn->tap.events == CLOSED)
|
||||||
|
tcp_conn_destroy(c, &conn->tap);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -200,5 +200,6 @@ extern union tcp_conn tc[];
|
||||||
|
|
||||||
void tcp_splice_conn_update(struct ctx *c, struct tcp_splice_conn *new);
|
void tcp_splice_conn_update(struct ctx *c, struct tcp_splice_conn *new);
|
||||||
void tcp_table_compact(struct ctx *c, union tcp_conn *hole);
|
void tcp_table_compact(struct ctx *c, union tcp_conn *hole);
|
||||||
|
void tcp_splice_destroy(struct ctx *c, struct tcp_splice_conn *conn);
|
||||||
|
|
||||||
#endif /* TCP_CONN_H */
|
#endif /* TCP_CONN_H */
|
||||||
|
|
24
tcp_splice.c
24
tcp_splice.c
|
@ -111,7 +111,6 @@ static void tcp_splice_conn_epoll_events(uint16_t events,
|
||||||
*b |= (events & B_OUT_WAIT) ? EPOLLOUT : 0;
|
*b |= (events & B_OUT_WAIT) ? EPOLLOUT : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void tcp_splice_destroy(struct ctx *c, struct tcp_splice_conn *conn);
|
|
||||||
static int tcp_splice_epoll_ctl(const struct ctx *c,
|
static int tcp_splice_epoll_ctl(const struct ctx *c,
|
||||||
struct tcp_splice_conn *conn);
|
struct tcp_splice_conn *conn);
|
||||||
|
|
||||||
|
@ -257,7 +256,7 @@ void tcp_splice_conn_update(struct ctx *c, struct tcp_splice_conn *new)
|
||||||
* @c: Execution context
|
* @c: Execution context
|
||||||
* @conn: Connection pointer
|
* @conn: Connection pointer
|
||||||
*/
|
*/
|
||||||
static void tcp_splice_destroy(struct ctx *c, struct tcp_splice_conn *conn)
|
void tcp_splice_destroy(struct ctx *c, struct tcp_splice_conn *conn)
|
||||||
{
|
{
|
||||||
if (conn->events & SPLICE_ESTABLISHED) {
|
if (conn->events & SPLICE_ESTABLISHED) {
|
||||||
/* Flushing might need to block: don't recycle them. */
|
/* Flushing might need to block: don't recycle them. */
|
||||||
|
@ -849,24 +848,3 @@ void tcp_splice_timer(struct ctx *c)
|
||||||
|
|
||||||
tcp_splice_pipe_refill(c);
|
tcp_splice_pipe_refill(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* tcp_splice_defer_handler() - Close connections without timer on file pressure
|
|
||||||
* @c: Execution context
|
|
||||||
*/
|
|
||||||
void tcp_splice_defer_handler(struct ctx *c)
|
|
||||||
{
|
|
||||||
int max_conns = c->tcp.conn_count / 100 * TCP_SPLICE_CONN_PRESSURE;
|
|
||||||
int max_files = c->nofile / 100 * TCP_SPLICE_FILE_PRESSURE;
|
|
||||||
struct tcp_splice_conn *conn;
|
|
||||||
|
|
||||||
if (c->tcp.conn_count < MIN(max_files / 6, max_conns))
|
|
||||||
return;
|
|
||||||
|
|
||||||
for (conn = CONN(c->tcp.conn_count - 1); conn >= CONN(0); conn--) {
|
|
||||||
if (!conn->c.spliced)
|
|
||||||
continue;
|
|
||||||
if (conn->flags & CLOSING)
|
|
||||||
tcp_splice_destroy(c, conn);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
|
@ -10,6 +10,5 @@ void tcp_sock_handler_splice(struct ctx *c, union epoll_ref ref,
|
||||||
uint32_t events);
|
uint32_t events);
|
||||||
void tcp_splice_init(struct ctx *c);
|
void tcp_splice_init(struct ctx *c);
|
||||||
void tcp_splice_timer(struct ctx *c);
|
void tcp_splice_timer(struct ctx *c);
|
||||||
void tcp_splice_defer_handler(struct ctx *c);
|
|
||||||
|
|
||||||
#endif /* TCP_SPLICE_H */
|
#endif /* TCP_SPLICE_H */
|
||||||
|
|
Loading…
Reference in a new issue