Commit 31ec70af authored by David Howells's avatar David Howells Committed by Jakub Kicinski
Browse files

rxrpc: Fix over large frame size warning



Under some circumstances, the compiler will emit the following warning for
rxrpc_send_response():

   net/rxrpc/output.c: In function 'rxrpc_send_response':
   net/rxrpc/output.c:974:1: warning: the frame size of 1160 bytes is larger than 1024 bytes

This occurs because the local variables include a 16-element scatterlist
array and a 16-element bio_vec array.  It's probably not actually a problem
as this function is only called by the rxrpc I/O thread function in a
kernel thread and there won't be much on the stack before it.

Fix this by overlaying the bio_vec array over the kvec array in the
rxrpc_local struct.  There is one of these per I/O thread and the kvec
array is intended for pointing at bits of a packet to be transmitted,
typically a DATA or an ACK packet.  As packets for a local endpoint are
only transmitted by its specific I/O thread, there can be no race, and so
overlaying this bit of memory should be no problem.

Fixes: 5800b1cf ("rxrpc: Allow CHALLENGEs to the passed to the app for a RESPONSE")
Reported-by: default avatarkernel test robot <lkp@intel.com>
Closes: https://lore.kernel.org/oe-kbuild-all/202506240423.E942yKJP-lkp@intel.com/


Signed-off-by: default avatarDavid Howells <dhowells@redhat.com>
cc: Marc Dionne <marc.dionne@auristor.com>
cc: Simon Horman <horms@kernel.org>
cc: linux-afs@lists.infradead.org
Link: https://patch.msgid.link/20250707102435.2381045-2-dhowells@redhat.com


Signed-off-by: default avatarJakub Kicinski <kuba@kernel.org>
parent 3ef07434
Loading
Loading
Loading
Loading
+9 −6
Original line number Diff line number Diff line
@@ -361,12 +361,15 @@ struct rxrpc_local {
	struct list_head	new_client_calls; /* Newly created client calls need connection */
	spinlock_t		client_call_lock; /* Lock for ->new_client_calls */
	struct sockaddr_rxrpc	srx;		/* local address */
	/* Provide a kvec table sufficiently large to manage either a DATA
	 * packet with a maximum set of jumbo subpackets or a PING ACK padded
	 * out to 64K with zeropages for PMTUD.
	union {
		/* Provide a kvec table sufficiently large to manage either a
		 * DATA packet with a maximum set of jumbo subpackets or a PING
		 * ACK padded out to 64K with zeropages for PMTUD.
		 */
		struct kvec		kvec[1 + RXRPC_MAX_NR_JUMBO > 3 + 16 ?
					     1 + RXRPC_MAX_NR_JUMBO : 3 + 16];
		struct bio_vec		bvec[3 + 16];
	};
};

/*
+4 −1
Original line number Diff line number Diff line
@@ -924,7 +924,7 @@ void rxrpc_send_response(struct rxrpc_connection *conn, struct sk_buff *response
{
	struct rxrpc_skb_priv *sp = rxrpc_skb(response);
	struct scatterlist sg[16];
	struct bio_vec bvec[16];
	struct bio_vec *bvec = conn->local->bvec;
	struct msghdr msg;
	size_t len = sp->resp.len;
	__be32 wserial;
@@ -938,6 +938,9 @@ void rxrpc_send_response(struct rxrpc_connection *conn, struct sk_buff *response
	if (ret < 0)
		goto fail;
	nr_sg = ret;
	ret = -EIO;
	if (WARN_ON_ONCE(nr_sg > ARRAY_SIZE(conn->local->bvec)))
		goto fail;

	for (int i = 0; i < nr_sg; i++)
		bvec_set_page(&bvec[i], sg_page(&sg[i]), sg[i].length, sg[i].offset);