From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: passt.top; dmarc=none (p=none dis=none) header.from=gibson.dropbear.id.au Authentication-Results: passt.top; dkim=pass (2048-bit key; secure) header.d=gibson.dropbear.id.au header.i=@gibson.dropbear.id.au header.a=rsa-sha256 header.s=202602 header.b=BJuNP1rd; dkim-atps=neutral Received: from mail.ozlabs.org (gandalf.ozlabs.org [150.107.74.76]) by passt.top (Postfix) with ESMTPS id 7B7FD5A026D for ; Thu, 28 May 2026 07:02:18 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gibson.dropbear.id.au; s=202602; t=1779944534; bh=OcI43Dcg03jlBUBRYa4Bmv3rGfvD/TERaAlhwX1hG6E=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=BJuNP1rdYCJ4+RfISVZPR6+yJx1DcBtK1ku7fhHkjbjTy8KysPAxrwW0rm00ml9tJ gqtgxmFjFvLpVpVl4uMltmwe9qnM+zT1msT7ciUc3ciIWXCZyBK8xrtcvV9KJxTQDr TYFnlOOpZXbuhx2XnZXLq3BJvZVM4siM/frD2CniIJqm9RBGi9ZxsDJTZ6VRGQXS4c 8ROX6os7d5l7yCFrcwCEUENlxlzXVjoqAXExTURVG6CDDD4bNZKITJ6uPuqs2r/UaC e7WZTogLoJ8tVlDdC7KyPSpjB+WkmO4KtQXn0ce+o/grqnJIYNmJefcpky0U2GLFTU rin1nt59gWm3A== Received: by gandalf.ozlabs.org (Postfix, from userid 1007) id 4gQvVZ6ycPz4wLp; Thu, 28 May 2026 15:02:14 +1000 (AEST) From: David Gibson To: passt-dev@passt.top, Stefano Brivio Subject: [PATCH 2/8] tcp_splice: Simplify EPOLLRDHUP / eof / FIN handling Date: Thu, 28 May 2026 15:02:07 +1000 Message-ID: <20260528050213.679685-3-david@gibson.dropbear.id.au> X-Mailer: git-send-email 2.54.0 In-Reply-To: <20260528050213.679685-1-david@gibson.dropbear.id.au> References: <20260528050213.679685-1-david@gibson.dropbear.id.au> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Message-ID-Hash: QWENH3NSXIRXIPBUOWMZOFHMMRJVXBM2 X-Message-ID-Hash: QWENH3NSXIRXIPBUOWMZOFHMMRJVXBM2 X-MailFrom: dgibson@gandalf.ozlabs.org X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; emergency; loop; banned-address; member-moderation; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; digests; suspicious-header CC: David Gibson X-Mailman-Version: 3.3.8 Precedence: list List-Id: Development discussion and patches for passt Archived-At: Archived-At: List-Archive: List-Archive: List-Help: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: There are two ways we can tell one of our sockets has received a FIN. We can either see an EPOLLRDHUP epoll event, or we can get a zero-length read (EOF) on the socket. We currently use both, in a mildly confusing way: we only set the FIN_RCVD() flag based on the EPOLLRDHUP event, but then some other close out logic is based on seeing an EOF. Simplify this by setting the flag based on only the EOF. To make sure we don't miss an event if we get an EPOLLRDHUP with no data, we trigger the forwarding path for EPOLLRDHUP as well as EPOLLIN. Signed-off-by: David Gibson --- tcp_splice.c | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/tcp_splice.c b/tcp_splice.c index c066d689..25e5d097 100644 --- a/tcp_splice.c +++ b/tcp_splice.c @@ -477,7 +477,6 @@ static int tcp_splice_forward(struct ctx *c, uint8_t lowat_set_flag = RCVLOWAT_SET(fromsidei); uint8_t lowat_act_flag = RCVLOWAT_ACT(fromsidei); int never_read = 1; - int eof = 0; while (1) { ssize_t readlen, written; @@ -501,7 +500,7 @@ retry: flow_trace(conn, "%zi from read-side call", readlen); if (!readlen) { - eof = 1; + conn_event(conn, FIN_RCVD(fromsidei)); } else if (readlen > 0) { never_read = 0; @@ -551,11 +550,12 @@ retry: written < conn->pending[fromsidei]) goto retry; - if (eof) + if (conn->events & FIN_RCVD(fromsidei)) break; } - if (!conn->pending[fromsidei] && eof) { + if (!conn->pending[fromsidei] && + conn->events & FIN_RCVD(fromsidei)) { unsigned sidei; flow_foreach_sidei(sidei) { @@ -620,17 +620,13 @@ void tcp_splice_sock_handler(struct ctx *c, union epoll_ref ref, goto reset; } - if (events & EPOLLRDHUP) - /* For side 0 this is fake, but implied */ - conn_event(conn, FIN_RCVD(evsidei)); - if (events & EPOLLOUT) { if (tcp_splice_forward(c, conn, !evsidei, now)) goto reset; conn_event(conn, ~OUT_WAIT(evsidei)); } - if (events & EPOLLIN) { + if (events & (EPOLLIN | EPOLLRDHUP)) { if (tcp_splice_forward(c, conn, evsidei, now)) goto reset; } -- 2.54.0