netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH net] rxrpc: Fix DATA Tx to disable nofrag for UDP on AF_INET6 socket
@ 2020-04-13 12:57 David Howells
  2020-04-14 23:27 ` David Miller
  0 siblings, 1 reply; 2+ messages in thread
From: David Howells @ 2020-04-13 12:57 UTC (permalink / raw)
  To: netdev; +Cc: dhowells, linux-afs, linux-kernel

Fix the DATA packet transmission to disable nofrag for UDPv4 on an AF_INET6
socket as well as UDPv6 when trying to transmit fragmentably.

Without this, packets filled to the normal size used by the kernel AFS
client of 1412 bytes be rejected by udp_sendmsg() with EMSGSIZE
immediately.  The ->sk_error_report() notification hook is called, but
rxrpc doesn't generate a trace for it.

This is a temporary fix; a more permanent solution needs to involve
changing the size of the packets being filled in accordance with the MTU,
which isn't currently done in AF_RXRPC.  The reason for not doing so was
that, barring the last packet in an rx jumbo packet, jumbos can only be
assembled out of 1412-byte packets - and the plan was to construct jumbos
on the fly at transmission time.

Also, there's no point turning on IPV6_MTU_DISCOVER, since IPv6 has to
engage in this anyway since fragmentation is only done by the sender.  We
can then condense the switch-statement in rxrpc_send_data_packet().

Fixes: 75b54cb57ca3 ("rxrpc: Add IPv6 support")
Signed-off-by: David Howells <dhowells@redhat.com>
---

 net/rxrpc/local_object.c |    9 ---------
 net/rxrpc/output.c       |   44 ++++++++++++--------------------------------
 2 files changed, 12 insertions(+), 41 deletions(-)

diff --git a/net/rxrpc/local_object.c b/net/rxrpc/local_object.c
index a6c1349e965d..01135e54d95d 100644
--- a/net/rxrpc/local_object.c
+++ b/net/rxrpc/local_object.c
@@ -165,15 +165,6 @@ static int rxrpc_open_socket(struct rxrpc_local *local, struct net *net)
 			goto error;
 		}
 
-		/* we want to set the don't fragment bit */
-		opt = IPV6_PMTUDISC_DO;
-		ret = kernel_setsockopt(local->socket, SOL_IPV6, IPV6_MTU_DISCOVER,
-					(char *) &opt, sizeof(opt));
-		if (ret < 0) {
-			_debug("setsockopt failed");
-			goto error;
-		}
-
 		/* Fall through and set IPv4 options too otherwise we don't get
 		 * errors from IPv4 packets sent through the IPv6 socket.
 		 */
diff --git a/net/rxrpc/output.c b/net/rxrpc/output.c
index bad3d2420344..90e263c6aa69 100644
--- a/net/rxrpc/output.c
+++ b/net/rxrpc/output.c
@@ -474,41 +474,21 @@ int rxrpc_send_data_packet(struct rxrpc_call *call, struct sk_buff *skb,
 	skb->tstamp = ktime_get_real();
 
 	switch (conn->params.local->srx.transport.family) {
+	case AF_INET6:
 	case AF_INET:
 		opt = IP_PMTUDISC_DONT;
-		ret = kernel_setsockopt(conn->params.local->socket,
-					SOL_IP, IP_MTU_DISCOVER,
-					(char *)&opt, sizeof(opt));
-		if (ret == 0) {
-			ret = kernel_sendmsg(conn->params.local->socket, &msg,
-					     iov, 2, len);
-			conn->params.peer->last_tx_at = ktime_get_seconds();
-
-			opt = IP_PMTUDISC_DO;
-			kernel_setsockopt(conn->params.local->socket, SOL_IP,
-					  IP_MTU_DISCOVER,
-					  (char *)&opt, sizeof(opt));
-		}
-		break;
-
-#ifdef CONFIG_AF_RXRPC_IPV6
-	case AF_INET6:
-		opt = IPV6_PMTUDISC_DONT;
-		ret = kernel_setsockopt(conn->params.local->socket,
-					SOL_IPV6, IPV6_MTU_DISCOVER,
-					(char *)&opt, sizeof(opt));
-		if (ret == 0) {
-			ret = kernel_sendmsg(conn->params.local->socket, &msg,
-					     iov, 2, len);
-			conn->params.peer->last_tx_at = ktime_get_seconds();
-
-			opt = IPV6_PMTUDISC_DO;
-			kernel_setsockopt(conn->params.local->socket,
-					  SOL_IPV6, IPV6_MTU_DISCOVER,
-					  (char *)&opt, sizeof(opt));
-		}
+		kernel_setsockopt(conn->params.local->socket,
+				  SOL_IP, IP_MTU_DISCOVER,
+				  (char *)&opt, sizeof(opt));
+		ret = kernel_sendmsg(conn->params.local->socket, &msg,
+				     iov, 2, len);
+		conn->params.peer->last_tx_at = ktime_get_seconds();
+
+		opt = IP_PMTUDISC_DO;
+		kernel_setsockopt(conn->params.local->socket,
+				  SOL_IP, IP_MTU_DISCOVER,
+				  (char *)&opt, sizeof(opt));
 		break;
-#endif
 
 	default:
 		BUG();



^ permalink raw reply related	[flat|nested] 2+ messages in thread

* Re: [PATCH net] rxrpc: Fix DATA Tx to disable nofrag for UDP on AF_INET6 socket
  2020-04-13 12:57 [PATCH net] rxrpc: Fix DATA Tx to disable nofrag for UDP on AF_INET6 socket David Howells
@ 2020-04-14 23:27 ` David Miller
  0 siblings, 0 replies; 2+ messages in thread
From: David Miller @ 2020-04-14 23:27 UTC (permalink / raw)
  To: dhowells; +Cc: netdev, linux-afs, linux-kernel

From: David Howells <dhowells@redhat.com>
Date: Mon, 13 Apr 2020 13:57:14 +0100

> Fix the DATA packet transmission to disable nofrag for UDPv4 on an AF_INET6
> socket as well as UDPv6 when trying to transmit fragmentably.
> 
> Without this, packets filled to the normal size used by the kernel AFS
> client of 1412 bytes be rejected by udp_sendmsg() with EMSGSIZE
> immediately.  The ->sk_error_report() notification hook is called, but
> rxrpc doesn't generate a trace for it.
> 
> This is a temporary fix; a more permanent solution needs to involve
> changing the size of the packets being filled in accordance with the MTU,
> which isn't currently done in AF_RXRPC.  The reason for not doing so was
> that, barring the last packet in an rx jumbo packet, jumbos can only be
> assembled out of 1412-byte packets - and the plan was to construct jumbos
> on the fly at transmission time.
> 
> Also, there's no point turning on IPV6_MTU_DISCOVER, since IPv6 has to
> engage in this anyway since fragmentation is only done by the sender.  We
> can then condense the switch-statement in rxrpc_send_data_packet().
> 
> Fixes: 75b54cb57ca3 ("rxrpc: Add IPv6 support")
> Signed-off-by: David Howells <dhowells@redhat.com>

Applied, thanks David.

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2020-04-14 23:29 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-04-13 12:57 [PATCH net] rxrpc: Fix DATA Tx to disable nofrag for UDP on AF_INET6 socket David Howells
2020-04-14 23:27 ` David Miller

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).