Linux NFS development
 help / color / mirror / Atom feed
* [PATCH] sunrpc: reject socket already in use in svc_addsock()
@ 2026-09-03 13:28 syzbot
  2026-09-03 13:48 ` Chuck Lever
  0 siblings, 1 reply; 3+ messages in thread
From: syzbot @ 2026-09-03 13:28 UTC (permalink / raw)
  To: syzkaller-bugs, Slawomir Stepien, Anna Schumaker, Chuck Lever,
	David S. Miller, Eric Dumazet, Jeff Layton, Jakub Kicinski,
	linux-nfs, netdev, Paolo Abeni, Trond Myklebust, Trond Myklebust
  Cc: Dai.Ngo, horms, linux-kernel, neil, okorniev, syzbot, tom

From: Slawomir Stepien <sst@poczta.fm>

When a socket is added to an RPC service via svc_addsock() (for example, by
writing its file descriptor to /proc/fs/nfsd/portlist), svc_setup_socket()
saves the original socket callbacks (such as sk_state_change) into struct
svc_sock and replaces them with RPC-specific callbacks (such as
svc_tcp_state_change). It also attaches the new svc_sock to
sk->sk_user_data.

If the same socket file descriptor is added to an RPC service again,
svc_addsock() invokes svc_setup_socket() a second time on the same socket.
During the second setup, svsk->sk_ostate is assigned the socket's current
sk_state_change callback, which was already replaced with
svc_tcp_state_change. When a state change event subsequently occurs on the
socket (for example, when connect() is called), svc_tcp_state_change()
invokes svsk->sk_ostate, calling itself in an infinite recursion until the
kernel stack overflows and triggers a stack guard page fault:

BUG: TASK stack guard page was hit at ffffc900030b7ff8 (stack is
ffffc900030b8000..ffffc900030c0000)
Oops: stack guard page: 0000 [#1] SMP KASAN NOPTI
...
Call Trace:
 <TASK>
 svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
 svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
 svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
 ...
 tcp_done_with_error net/ipv4/tcp_input.c:4877 [inline]
 tcp_reset+0x176/0x380 net/ipv4/tcp_input.c:4909
 tcp_rcv_synsent_state_process net/ipv4/tcp_input.c:6903 [inline]
 tcp_rcv_state_process+0x13bc/0x48a0 net/ipv4/tcp_input.c:7197
 tcp_v4_do_rcv+0xafc/0x1530 net/ipv4/tcp_ipv4.c:1876
 sk_backlog_rcv include/net/sock.h:1192 [inline]
 __release_sock+0x25b/0x390 net/core/sock.c:3260
 release_sock+0x190/0x260 net/core/sock.c:3859
 inet_wait_for_connect net/ipv4/af_inet.c:616 [inline]
 __inet_stream_connect+0x863/0xe00 net/ipv4/af_inet.c:710
 inet_stream_connect+0x66/0xa0 net/ipv4/af_inet.c:755
 connect_socket net/socket.c:2141 [inline]
 __sys_connect_file net/socket.c:2166 [inline]
 __sys_connect+0x316/0x450 net/socket.c:2183
 ...
 </TASK>

Fix this by checking if so->sk->sk_user_data is already set in
svc_addsock() before proceeding with svc_setup_socket(). If it is already
non-NULL, return -EBUSY to prevent re-initializing an active socket.

Fixes: fa9251afc33c ("SUNRPC: Call the default socket callbacks instead of open coding")
Assisted-by: Gemini:gemini-3.7-flash Gemini:gemini-3.1-pro-preview syzbot
Reported-by: syzbot+c9834a0c0215e6d8697a@syzkaller.appspotmail.com
Closes: https://syzkaller.appspot.com/bug?extid=c9834a0c0215e6d8697a
Link: https://syzkaller.appspot.com/ai_job?id=30de91d1-1d14-4676-8c38-a3564f7acf48
Signed-off-by: Slawomir Stepien <sst@poczta.fm>

---
diff --git a/net/sunrpc/svcsock.c b/net/sunrpc/svcsock.c
index 50e5e7f5b..e8cc4329f 100644
--- a/net/sunrpc/svcsock.c
+++ b/net/sunrpc/svcsock.c
@@ -1541,6 +1541,9 @@ int svc_addsock(struct svc_serv *serv, struct net *net, const int fd,
 	err = -EISCONN;
 	if (so->state > SS_UNCONNECTED)
 		goto out;
+	err = -EBUSY;
+	if (so->sk->sk_user_data)
+		goto out;
 	err = -ENOENT;
 	if (!try_module_get(THIS_MODULE))
 		goto out;


base-commit: cee9395acd8043be0644b25c34bfa86623f2b935
-- 
See https://goo.gle/syzbot-ai-patches for information about AI-generated patches.
The person who has signed off on the patch is responsible for
addressing comments.
syzbot engineers can be reached at syzkaller@googlegroups.com.

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

* Re: [PATCH] sunrpc: reject socket already in use in svc_addsock()
  2026-09-03 13:28 [PATCH] sunrpc: reject socket already in use in svc_addsock() syzbot
@ 2026-09-03 13:48 ` Chuck Lever
  2026-09-03 14:05   ` Slawomir Stepien
  0 siblings, 1 reply; 3+ messages in thread
From: Chuck Lever @ 2026-09-03 13:48 UTC (permalink / raw)
  To: syzbot, syzkaller-bugs, Slawomir Stepien, Anna Schumaker,
	David S. Miller, Eric Dumazet, Jeff Layton, Jakub Kicinski,
	linux-nfs, netdev, Paolo Abeni, Trond Myklebust, Trond Myklebust
  Cc: Dai Ngo, Simon Horman, linux-kernel, NeilBrown, Olga Kornievskaia,
	syzbot, Tom Talpey



On Thu, Sep 3, 2026, at 9:28 AM, syzbot wrote:
> From: Slawomir Stepien <sst@poczta.fm>
>
> When a socket is added to an RPC service via svc_addsock() (for example, by
> writing its file descriptor to /proc/fs/nfsd/portlist), svc_setup_socket()
> saves the original socket callbacks (such as sk_state_change) into struct
> svc_sock and replaces them with RPC-specific callbacks (such as
> svc_tcp_state_change). It also attaches the new svc_sock to
> sk->sk_user_data.
>
> If the same socket file descriptor is added to an RPC service again,
> svc_addsock() invokes svc_setup_socket() a second time on the same socket.
> During the second setup, svsk->sk_ostate is assigned the socket's current
> sk_state_change callback, which was already replaced with
> svc_tcp_state_change. When a state change event subsequently occurs on the
> socket (for example, when connect() is called), svc_tcp_state_change()
> invokes svsk->sk_ostate, calling itself in an infinite recursion until the
> kernel stack overflows and triggers a stack guard page fault:
>
> BUG: TASK stack guard page was hit at ffffc900030b7ff8 (stack is
> ffffc900030b8000..ffffc900030c0000)
> Oops: stack guard page: 0000 [#1] SMP KASAN NOPTI
> ...
> Call Trace:
>  <TASK>
>  svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
>  svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
>  svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
>  ...
>  tcp_done_with_error net/ipv4/tcp_input.c:4877 [inline]
>  tcp_reset+0x176/0x380 net/ipv4/tcp_input.c:4909
>  tcp_rcv_synsent_state_process net/ipv4/tcp_input.c:6903 [inline]
>  tcp_rcv_state_process+0x13bc/0x48a0 net/ipv4/tcp_input.c:7197
>  tcp_v4_do_rcv+0xafc/0x1530 net/ipv4/tcp_ipv4.c:1876
>  sk_backlog_rcv include/net/sock.h:1192 [inline]
>  __release_sock+0x25b/0x390 net/core/sock.c:3260
>  release_sock+0x190/0x260 net/core/sock.c:3859
>  inet_wait_for_connect net/ipv4/af_inet.c:616 [inline]
>  __inet_stream_connect+0x863/0xe00 net/ipv4/af_inet.c:710
>  inet_stream_connect+0x66/0xa0 net/ipv4/af_inet.c:755
>  connect_socket net/socket.c:2141 [inline]
>  __sys_connect_file net/socket.c:2166 [inline]
>  __sys_connect+0x316/0x450 net/socket.c:2183
>  ...
>  </TASK>
>
> Fix this by checking if so->sk->sk_user_data is already set in
> svc_addsock() before proceeding with svc_setup_socket(). If it is already
> non-NULL, return -EBUSY to prevent re-initializing an active socket.
>
> Fixes: fa9251afc33c ("SUNRPC: Call the default socket callbacks instead 
> of open coding")
> Assisted-by: Gemini:gemini-3.7-flash Gemini:gemini-3.1-pro-preview 
> syzbot
> Reported-by: syzbot+c9834a0c0215e6d8697a@syzkaller.appspotmail.com
> Closes: https://syzkaller.appspot.com/bug?extid=c9834a0c0215e6d8697a
> Link: 
> https://syzkaller.appspot.com/ai_job?id=30de91d1-1d14-4676-8c38-a3564f7acf48
> Signed-off-by: Slawomir Stepien <sst@poczta.fm>
>
> ---
> diff --git a/net/sunrpc/svcsock.c b/net/sunrpc/svcsock.c
> index 50e5e7f5b..e8cc4329f 100644
> --- a/net/sunrpc/svcsock.c
> +++ b/net/sunrpc/svcsock.c
> @@ -1541,6 +1541,9 @@ int svc_addsock(struct svc_serv *serv, struct net 
> *net, const int fd,
>  	err = -EISCONN;
>  	if (so->state > SS_UNCONNECTED)
>  		goto out;
> +	err = -EBUSY;
> +	if (so->sk->sk_user_data)
> +		goto out;
>  	err = -ENOENT;
>  	if (!try_module_get(THIS_MODULE))
>  		goto out;
>
>
> base-commit: cee9395acd8043be0644b25c34bfa86623f2b935

A similar fix is already in nfsd-testing:

https://git.kernel.org/pub/scm/linux/kernel/git/cel/linux.git/commit/net/sunrpc/svcsock.c?h=nfsd-testing&id=7e8d1b4845aac4ad3c7bcd39032754917f5b966d


-- 
Chuck Lever (Come to NFS bake-a-thon! https://nfsv4bat.org)

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

* Re: [PATCH] sunrpc: reject socket already in use in svc_addsock()
  2026-09-03 13:48 ` Chuck Lever
@ 2026-09-03 14:05   ` Slawomir Stepien
  0 siblings, 0 replies; 3+ messages in thread
From: Slawomir Stepien @ 2026-09-03 14:05 UTC (permalink / raw)
  To: Chuck Lever
  Cc: syzbot, syzkaller-bugs, Anna Schumaker, David S. Miller,
	Eric Dumazet, Jeff Layton, Jakub Kicinski, linux-nfs, netdev,
	Paolo Abeni, Trond Myklebust, Trond Myklebust, Dai Ngo,
	Simon Horman, linux-kernel, NeilBrown, Olga Kornievskaia, syzbot,
	Tom Talpey

On wrz 03, 2026 09:48, Chuck Lever wrote:
> On Thu, Sep 3, 2026, at 9:28 AM, syzbot wrote:
> > From: Slawomir Stepien <sst@poczta.fm>
> >
> > When a socket is added to an RPC service via svc_addsock() (for example, by
> > writing its file descriptor to /proc/fs/nfsd/portlist), svc_setup_socket()
> > saves the original socket callbacks (such as sk_state_change) into struct
> > svc_sock and replaces them with RPC-specific callbacks (such as
> > svc_tcp_state_change). It also attaches the new svc_sock to
> > sk->sk_user_data.
> >
> > If the same socket file descriptor is added to an RPC service again,
> > svc_addsock() invokes svc_setup_socket() a second time on the same socket.
> > During the second setup, svsk->sk_ostate is assigned the socket's current
> > sk_state_change callback, which was already replaced with
> > svc_tcp_state_change. When a state change event subsequently occurs on the
> > socket (for example, when connect() is called), svc_tcp_state_change()
> > invokes svsk->sk_ostate, calling itself in an infinite recursion until the
> > kernel stack overflows and triggers a stack guard page fault:
> >
> > BUG: TASK stack guard page was hit at ffffc900030b7ff8 (stack is
> > ffffc900030b8000..ffffc900030c0000)
> > Oops: stack guard page: 0000 [#1] SMP KASAN NOPTI
> > ...
> > Call Trace:
> >  <TASK>
> >  svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
> >  svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
> >  svc_tcp_state_change+0x76/0x2e0 net/sunrpc/svcsock.c:917
> >  ...
> >  tcp_done_with_error net/ipv4/tcp_input.c:4877 [inline]
> >  tcp_reset+0x176/0x380 net/ipv4/tcp_input.c:4909
> >  tcp_rcv_synsent_state_process net/ipv4/tcp_input.c:6903 [inline]
> >  tcp_rcv_state_process+0x13bc/0x48a0 net/ipv4/tcp_input.c:7197
> >  tcp_v4_do_rcv+0xafc/0x1530 net/ipv4/tcp_ipv4.c:1876
> >  sk_backlog_rcv include/net/sock.h:1192 [inline]
> >  __release_sock+0x25b/0x390 net/core/sock.c:3260
> >  release_sock+0x190/0x260 net/core/sock.c:3859
> >  inet_wait_for_connect net/ipv4/af_inet.c:616 [inline]
> >  __inet_stream_connect+0x863/0xe00 net/ipv4/af_inet.c:710
> >  inet_stream_connect+0x66/0xa0 net/ipv4/af_inet.c:755
> >  connect_socket net/socket.c:2141 [inline]
> >  __sys_connect_file net/socket.c:2166 [inline]
> >  __sys_connect+0x316/0x450 net/socket.c:2183
> >  ...
> >  </TASK>
> >
> > Fix this by checking if so->sk->sk_user_data is already set in
> > svc_addsock() before proceeding with svc_setup_socket(). If it is already
> > non-NULL, return -EBUSY to prevent re-initializing an active socket.
> >
> > Fixes: fa9251afc33c ("SUNRPC: Call the default socket callbacks instead 
> > of open coding")
> > Assisted-by: Gemini:gemini-3.7-flash Gemini:gemini-3.1-pro-preview 
> > syzbot
> > Reported-by: syzbot+c9834a0c0215e6d8697a@syzkaller.appspotmail.com
> > Closes: https://syzkaller.appspot.com/bug?extid=c9834a0c0215e6d8697a
> > Link: 
> > https://syzkaller.appspot.com/ai_job?id=30de91d1-1d14-4676-8c38-a3564f7acf48
> > Signed-off-by: Slawomir Stepien <sst@poczta.fm>
> >
> > ---
> > diff --git a/net/sunrpc/svcsock.c b/net/sunrpc/svcsock.c
> > index 50e5e7f5b..e8cc4329f 100644
> > --- a/net/sunrpc/svcsock.c
> > +++ b/net/sunrpc/svcsock.c
> > @@ -1541,6 +1541,9 @@ int svc_addsock(struct svc_serv *serv, struct net 
> > *net, const int fd,
> >  	err = -EISCONN;
> >  	if (so->state > SS_UNCONNECTED)
> >  		goto out;
> > +	err = -EBUSY;
> > +	if (so->sk->sk_user_data)
> > +		goto out;
> >  	err = -ENOENT;
> >  	if (!try_module_get(THIS_MODULE))
> >  		goto out;
> >
> >
> > base-commit: cee9395acd8043be0644b25c34bfa86623f2b935
> 
> A similar fix is already in nfsd-testing:
> 
> https://git.kernel.org/pub/scm/linux/kernel/git/cel/linux.git/commit/net/sunrpc/svcsock.c?h=nfsd-testing&id=7e8d1b4845aac4ad3c7bcd39032754917f5b966d

Ah ok, a different extid of syzbug that's why I've missed it. Thanks!

-- 
Slawomir Stepien

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

end of thread, other threads:[~2026-09-03 14:06 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-09-03 13:28 [PATCH] sunrpc: reject socket already in use in svc_addsock() syzbot
2026-09-03 13:48 ` Chuck Lever
2026-09-03 14:05   ` Slawomir Stepien

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox