From cd61ad02d4181e8fa34e2bcb8f8436fd9a64714b Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 28 May 2026 15:02:10 +1000 Subject: tcp_splice: Simplify shutdown(2) handling At the end of tcp_splice_forward(), we check for half-closed connections in either direction and propagate the FIN to the other side with a shutdown(2). However, it's unnecessary to check both directions: a FIN from side X will cause an EPOLLRDUP on side X's socket, which will trigger tcp_splice_forward() from side X to side !X. Likewise for the other side. So we only need to check for "forward" FIN propagation. Signed-off-by: David Gibson Signed-off-by: Stefano Brivio --- tcp_splice.c | 23 ++++++++--------------- 1 file changed, 8 insertions(+), 15 deletions(-) diff --git a/tcp_splice.c b/tcp_splice.c index 8c8e3bb..4290268 100644 --- a/tcp_splice.c +++ b/tcp_splice.c @@ -544,22 +544,15 @@ static int tcp_splice_forward(struct ctx *c, break; } - if (!conn->pending[fromsidei] && - conn->events & FIN_RCVD(fromsidei)) { - unsigned sidei; - - flow_foreach_sidei(sidei) { - if ((conn->events & FIN_RCVD(sidei)) && - !(conn->events & FIN_SENT(!sidei))) { - if (shutdown(conn->s[!sidei], SHUT_WR) < 0) { - flow_perror_ratelimit( - conn, now, "shutdown() on %s", - pif_name(conn->f.pif[!sidei])); - return -1; - } - conn_event(conn, FIN_SENT(!sidei)); - } + if ((conn->events & FIN_RCVD(fromsidei)) && + !(conn->events & FIN_SENT(!fromsidei)) && + !conn->pending[fromsidei]) { + if (shutdown(conn->s[!fromsidei], SHUT_WR) < 0) { + flow_perror_ratelimit(conn, now, "shutdown() on %s", + pif_name(conn->f.pif[!fromsidei])); + return -1; } + conn_event(conn, FIN_SENT(!fromsidei)); } return 0; -- cgit v1.2.3