diff mbox series

[1/2] SUNRPC: Don't allow waiting for exiting tasks

Message ID f301a88d04e1929a313c458bd8ce1218903b648a.1743183579.git.trond.myklebust@hammerspace.com (mailing list archive)
State New
Headers show
Series [1/2] SUNRPC: Don't allow waiting for exiting tasks | expand

Commit Message

Trond Myklebust March 28, 2025, 5:40 p.m. UTC
From: Trond Myklebust <trond.myklebust@hammerspace.com>

Once a task calls exit_signals() it can no longer be signalled. So do
not allow it to do killable waits.

Signed-off-by: Trond Myklebust <trond.myklebust@hammerspace.com>
---
 net/sunrpc/sched.c | 2 ++
 1 file changed, 2 insertions(+)

Comments

Jeff Layton March 28, 2025, 5:53 p.m. UTC | #1
On Fri, 2025-03-28 at 13:40 -0400, trondmy@kernel.org wrote:
> From: Trond Myklebust <trond.myklebust@hammerspace.com>
> 
> Once a task calls exit_signals() it can no longer be signalled. So do
> not allow it to do killable waits.
> 
> Signed-off-by: Trond Myklebust <trond.myklebust@hammerspace.com>
> ---
>  net/sunrpc/sched.c | 2 ++
>  1 file changed, 2 insertions(+)
> 
> diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
> index 9b45fbdc90ca..73bc39281ef5 100644
> --- a/net/sunrpc/sched.c
> +++ b/net/sunrpc/sched.c
> @@ -276,6 +276,8 @@ EXPORT_SYMBOL_GPL(rpc_destroy_wait_queue);
>  
>  static int rpc_wait_bit_killable(struct wait_bit_key *key, int mode)
>  {
> +	if (unlikely(current->flags & PF_EXITING))
> +		return -EINTR;
>  	schedule();
>  	if (signal_pending_state(mode, current))
>  		return -ERESTARTSYS;

Won't this mean that if a task is signalled and does a final fput, that
a CLOSE sent in task_work will never get sent?
Trond Myklebust March 28, 2025, 6 p.m. UTC | #2
On Fri, 2025-03-28 at 13:53 -0400, Jeff Layton wrote:
> On Fri, 2025-03-28 at 13:40 -0400, trondmy@kernel.org wrote:
> > From: Trond Myklebust <trond.myklebust@hammerspace.com>
> > 
> > Once a task calls exit_signals() it can no longer be signalled. So
> > do
> > not allow it to do killable waits.
> > 
> > Signed-off-by: Trond Myklebust <trond.myklebust@hammerspace.com>
> > ---
> >  net/sunrpc/sched.c | 2 ++
> >  1 file changed, 2 insertions(+)
> > 
> > diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
> > index 9b45fbdc90ca..73bc39281ef5 100644
> > --- a/net/sunrpc/sched.c
> > +++ b/net/sunrpc/sched.c
> > @@ -276,6 +276,8 @@ EXPORT_SYMBOL_GPL(rpc_destroy_wait_queue);
> >  
> >  static int rpc_wait_bit_killable(struct wait_bit_key *key, int
> > mode)
> >  {
> > +	if (unlikely(current->flags & PF_EXITING))
> > +		return -EINTR;
> >  	schedule();
> >  	if (signal_pending_state(mode, current))
> >  		return -ERESTARTSYS;
> 
> Won't this mean that if a task is signalled and does a final fput,
> that
> a CLOSE sent in task_work will never get sent?

It should mean that the close gets sent, but the task won't wait for
completion.
Jeff Layton March 28, 2025, 6:09 p.m. UTC | #3
On Fri, 2025-03-28 at 18:00 +0000, Trond Myklebust wrote:
> On Fri, 2025-03-28 at 13:53 -0400, Jeff Layton wrote:
> > On Fri, 2025-03-28 at 13:40 -0400, trondmy@kernel.org wrote:
> > > From: Trond Myklebust <trond.myklebust@hammerspace.com>
> > > 
> > > Once a task calls exit_signals() it can no longer be signalled. So
> > > do
> > > not allow it to do killable waits.
> > > 
> > > Signed-off-by: Trond Myklebust <trond.myklebust@hammerspace.com>
> > > ---
> > >  net/sunrpc/sched.c | 2 ++
> > >  1 file changed, 2 insertions(+)
> > > 
> > > diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
> > > index 9b45fbdc90ca..73bc39281ef5 100644
> > > --- a/net/sunrpc/sched.c
> > > +++ b/net/sunrpc/sched.c
> > > @@ -276,6 +276,8 @@ EXPORT_SYMBOL_GPL(rpc_destroy_wait_queue);
> > >  
> > >  static int rpc_wait_bit_killable(struct wait_bit_key *key, int
> > > mode)
> > >  {
> > > +	if (unlikely(current->flags & PF_EXITING))
> > > +		return -EINTR;
> > >  	schedule();
> > >  	if (signal_pending_state(mode, current))
> > >  		return -ERESTARTSYS;
> > 
> > Won't this mean that if a task is signalled and does a final fput,
> > that
> > a CLOSE sent in task_work will never get sent?
> 
> It should mean that the close gets sent, but the task won't wait for
> completion.
> 

Good enough, I guess.

Reviewed-by: Jeff Layton <jlayton@kernel.org>
Trond Myklebust March 28, 2025, 7:36 p.m. UTC | #4
On Fri, 2025-03-28 at 14:09 -0400, Jeff Layton wrote:
> On Fri, 2025-03-28 at 18:00 +0000, Trond Myklebust wrote:
> > On Fri, 2025-03-28 at 13:53 -0400, Jeff Layton wrote:
> > > On Fri, 2025-03-28 at 13:40 -0400, trondmy@kernel.org wrote:
> > > > From: Trond Myklebust <trond.myklebust@hammerspace.com>
> > > > 
> > > > Once a task calls exit_signals() it can no longer be signalled.
> > > > So
> > > > do
> > > > not allow it to do killable waits.
> > > > 
> > > > Signed-off-by: Trond Myklebust
> > > > <trond.myklebust@hammerspace.com>
> > > > ---
> > > >  net/sunrpc/sched.c | 2 ++
> > > >  1 file changed, 2 insertions(+)
> > > > 
> > > > diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
> > > > index 9b45fbdc90ca..73bc39281ef5 100644
> > > > --- a/net/sunrpc/sched.c
> > > > +++ b/net/sunrpc/sched.c
> > > > @@ -276,6 +276,8 @@ EXPORT_SYMBOL_GPL(rpc_destroy_wait_queue);
> > > >  
> > > >  static int rpc_wait_bit_killable(struct wait_bit_key *key, int
> > > > mode)
> > > >  {
> > > > +	if (unlikely(current->flags & PF_EXITING))
> > > > +		return -EINTR;
> > > >  	schedule();
> > > >  	if (signal_pending_state(mode, current))
> > > >  		return -ERESTARTSYS;
> > > 
> > > Won't this mean that if a task is signalled and does a final
> > > fput,
> > > that
> > > a CLOSE sent in task_work will never get sent?
> > 
> > It should mean that the close gets sent, but the task won't wait
> > for
> > completion.
> > 
> 
> Good enough, I guess.
> 
> Reviewed-by: Jeff Layton <jlayton@kernel.org>
> 

It ensures that the task can die, and with the actual close RPC call
being asynchronous, it will keep going until either the server comes
back and processes it, or someone force umounts the partition and kills
the call, etc.
diff mbox series

Patch

diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
index 9b45fbdc90ca..73bc39281ef5 100644
--- a/net/sunrpc/sched.c
+++ b/net/sunrpc/sched.c
@@ -276,6 +276,8 @@  EXPORT_SYMBOL_GPL(rpc_destroy_wait_queue);
 
 static int rpc_wait_bit_killable(struct wait_bit_key *key, int mode)
 {
+	if (unlikely(current->flags & PF_EXITING))
+		return -EINTR;
 	schedule();
 	if (signal_pending_state(mode, current))
 		return -ERESTARTSYS;