From: Joshua Watt <jpewhacker@gmail.com>
To: NeilBrown <neilb@suse.com>, Jeff Layton <jlayton@redhat.com>,
Trond Myklebust <trond.myklebust@primarydata.com>
Cc: linux-nfs@vger.kernel.org, Al Viro <viro@zeniv.linux.org.uk>,
"J . Bruce Fields" <bfields@fieldses.org>,
David Howells <dhowells@redhat.com>,
Joshua Watt <JPEWhacker@gmail.com>
Subject: [RFC 1/4] SUNRPC: Add flag to kill new tasks
Date: Wed, 8 Nov 2017 08:59:39 -0600 [thread overview]
Message-ID: <20171108145942.5127-2-JPEWhacker@gmail.com> (raw)
In-Reply-To: <20171108145942.5127-1-JPEWhacker@gmail.com>
The new flag to rpc_killall_tasks() causes new tasks that are killed
after to call to be killed immediately instead of being executed. This
will all clients (particularly NFS) to prevents these task from delaying
shutdown of the RPC session longer than necessary.
Signed-off-by: Joshua Watt <JPEWhacker@gmail.com>
---
fs/nfs/super.c | 4 ++--
include/linux/sunrpc/clnt.h | 1 +
include/linux/sunrpc/sched.h | 2 +-
net/sunrpc/clnt.c | 13 ++++++++++---
net/sunrpc/sched.c | 7 +++++++
5 files changed, 21 insertions(+), 6 deletions(-)
diff --git a/fs/nfs/super.c b/fs/nfs/super.c
index 216f67d628b3..66fda2dcadd0 100644
--- a/fs/nfs/super.c
+++ b/fs/nfs/super.c
@@ -903,10 +903,10 @@ void nfs_umount_begin(struct super_block *sb)
/* -EIO all pending I/O */
rpc = server->client_acl;
if (!IS_ERR(rpc))
- rpc_killall_tasks(rpc);
+ rpc_killall_tasks(rpc, 0);
rpc = server->client;
if (!IS_ERR(rpc))
- rpc_killall_tasks(rpc);
+ rpc_killall_tasks(rpc, 0);
}
EXPORT_SYMBOL_GPL(nfs_umount_begin);
diff --git a/include/linux/sunrpc/clnt.h b/include/linux/sunrpc/clnt.h
index 71c237e8240e..94f4e464de1b 100644
--- a/include/linux/sunrpc/clnt.h
+++ b/include/linux/sunrpc/clnt.h
@@ -54,6 +54,7 @@ struct rpc_clnt {
cl_noretranstimeo: 1,/* No retransmit timeouts */
cl_autobind : 1,/* use getport() */
cl_chatty : 1;/* be verbose */
+ bool cl_kill_new_tasks; /* Kill all new tasks */
struct rpc_rtt * cl_rtt; /* RTO estimator data */
const struct rpc_timeout *cl_timeout; /* Timeout strategy */
diff --git a/include/linux/sunrpc/sched.h b/include/linux/sunrpc/sched.h
index d96e74e114c0..9b8bebaee0f4 100644
--- a/include/linux/sunrpc/sched.h
+++ b/include/linux/sunrpc/sched.h
@@ -218,7 +218,7 @@ void rpc_put_task_async(struct rpc_task *);
void rpc_exit_task(struct rpc_task *);
void rpc_exit(struct rpc_task *, int);
void rpc_release_calldata(const struct rpc_call_ops *, void *);
-void rpc_killall_tasks(struct rpc_clnt *);
+void rpc_killall_tasks(struct rpc_clnt *clnt, int kill_new_tasks);
void rpc_execute(struct rpc_task *);
void rpc_init_priority_wait_queue(struct rpc_wait_queue *, const char *);
void rpc_init_wait_queue(struct rpc_wait_queue *, const char *);
diff --git a/net/sunrpc/clnt.c b/net/sunrpc/clnt.c
index df4ecb042ebe..70005252b32f 100644
--- a/net/sunrpc/clnt.c
+++ b/net/sunrpc/clnt.c
@@ -814,14 +814,21 @@ EXPORT_SYMBOL_GPL(rpc_clnt_iterate_for_each_xprt);
* Kill all tasks for the given client.
* XXX: kill their descendants as well?
*/
-void rpc_killall_tasks(struct rpc_clnt *clnt)
+void rpc_killall_tasks(struct rpc_clnt *clnt, int kill_new_tasks)
{
struct rpc_task *rovr;
+ dprintk("RPC: killing all tasks for client %p\n", clnt);
+
+ if (kill_new_tasks) {
+ WRITE_ONCE(clnt->cl_kill_new_tasks, true);
+
+ /* Ensure the kill flag is set before checking the task list */
+ smp_mb();
+ }
if (list_empty(&clnt->cl_tasks))
return;
- dprintk("RPC: killing all tasks for client %p\n", clnt);
/*
* Spin lock all_tasks to prevent changes...
*/
@@ -854,7 +861,7 @@ void rpc_shutdown_client(struct rpc_clnt *clnt)
rcu_dereference(clnt->cl_xprt)->servername);
while (!list_empty(&clnt->cl_tasks)) {
- rpc_killall_tasks(clnt);
+ rpc_killall_tasks(clnt, 0);
wait_event_timeout(destroy_wait,
list_empty(&clnt->cl_tasks), 1*HZ);
}
diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
index 0cc83839c13c..c9bf1ab9e941 100644
--- a/net/sunrpc/sched.c
+++ b/net/sunrpc/sched.c
@@ -748,6 +748,13 @@ static void __rpc_execute(struct rpc_task *task)
dprintk("RPC: %5u __rpc_execute flags=0x%x\n",
task->tk_pid, task->tk_flags);
+ /* Ensure the task is in the client task list before checking the kill
+ * flag
+ */
+ smp_mb();
+ if (READ_ONCE(task->tk_client->cl_kill_new_tasks))
+ rpc_exit(task, -EIO);
+
WARN_ON_ONCE(RPC_IS_QUEUED(task));
if (RPC_IS_QUEUED(task))
return;
--
2.13.6
next prev parent reply other threads:[~2017-11-08 15:00 UTC|newest]
Thread overview: 36+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-10-25 17:11 NFS Force Unmounting Joshua Watt
2017-10-30 20:20 ` J. Bruce Fields
2017-10-30 21:04 ` Joshua Watt
2017-10-30 21:09 ` NeilBrown
2017-10-31 14:41 ` Jeff Layton
2017-10-31 14:55 ` Chuck Lever
2017-10-31 17:04 ` Joshua Watt
2017-10-31 19:46 ` Chuck Lever
2017-11-01 0:53 ` NeilBrown
2017-11-01 2:22 ` Chuck Lever
2017-11-01 14:38 ` Joshua Watt
2017-11-02 0:15 ` NeilBrown
2017-11-02 19:46 ` Chuck Lever
2017-11-02 21:51 ` NeilBrown
2017-11-01 17:24 ` Jeff Layton
2017-11-01 23:13 ` NeilBrown
2017-11-02 12:09 ` Jeff Layton
2017-11-02 14:54 ` Joshua Watt
2017-11-08 3:30 ` NeilBrown
2017-11-08 12:08 ` Jeff Layton
2017-11-08 15:52 ` J. Bruce Fields
2017-11-08 22:34 ` NeilBrown
2017-11-08 23:52 ` Trond Myklebust
2017-11-09 19:48 ` Joshua Watt
2017-11-10 0:16 ` NeilBrown
2017-11-08 14:59 ` [RFC 0/4] " Joshua Watt
2017-11-08 14:59 ` Joshua Watt [this message]
2017-11-10 1:39 ` [RFC 1/4] SUNRPC: Add flag to kill new tasks NeilBrown
2017-11-08 14:59 ` [RFC 2/4] SUNRPC: Kill client tasks from debugfs Joshua Watt
2017-11-10 1:47 ` NeilBrown
2017-11-10 14:13 ` Joshua Watt
2017-11-08 14:59 ` [RFC 3/4] SUNRPC: Simplify client shutdown Joshua Watt
2017-11-10 1:50 ` NeilBrown
2017-11-08 14:59 ` [RFC 4/4] NFS: Add forcekill mount option Joshua Watt
2017-11-10 2:01 ` NeilBrown
2017-11-10 14:16 ` Joshua Watt
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20171108145942.5127-2-JPEWhacker@gmail.com \
--to=jpewhacker@gmail.com \
--cc=bfields@fieldses.org \
--cc=dhowells@redhat.com \
--cc=jlayton@redhat.com \
--cc=linux-nfs@vger.kernel.org \
--cc=neilb@suse.com \
--cc=trond.myklebust@primarydata.com \
--cc=viro@zeniv.linux.org.uk \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
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).