From: "Paul E. McKenney" <paulmck@kernel.org>
To: rcu@vger.kernel.org
Cc: linux-kernel@vger.kernel.org, kernel-team@fb.com,
mingo@kernel.org, jiangshanlai@gmail.com,
akpm@linux-foundation.org, mathieu.desnoyers@efficios.com,
josh@joshtriplett.org, tglx@linutronix.de, peterz@infradead.org,
rostedt@goodmis.org, dhowells@redhat.com, edumazet@google.com,
fweisbec@gmail.com, oleg@redhat.com, joel@joelfernandes.org,
"Paul E. McKenney" <paulmck@kernel.org>,
Sebastian Andrzej Siewior <bigeasy@linutronix.de>,
Scott Wood <swood@redhat.com>
Subject: [PATCH tip/core/rcu 10/19] rcu: Make RCU priority boosting work on single-CPU rcu_node structures
Date: Tue, 11 May 2021 15:52:55 -0700 [thread overview]
Message-ID: <20210511225304.2893154-10-paulmck@kernel.org> (raw)
In-Reply-To: <20210511225241.GA2893003@paulmck-ThinkPad-P17-Gen-1>
When any CPU comes online, it checks to see if an RCU-boost kthread has
already been created for that CPU's leaf rcu_node structure, and if
not, it creates one. Unfortunately, it also verifies that this leaf
rcu_node structure actually has at least one online CPU, and if not,
it declines to create the kthread. Although this behavior makes sense
during early boot, especially on systems that claim far more CPUs than
they actually have, it makes no sense for the first CPU to come online
for a given rcu_node structure. There is no point in checking because
we know there is a CPU on its way in.
The problem is that timing differences can cause this incoming CPU to not
yet be reflected in the various bit masks even at rcutree_online_cpu()
time, and there is no chance at rcutree_prepare_cpu() time. Plus it
would be better to create the RCU-boost kthread at rcutree_prepare_cpu()
to handle the case where the CPU is involved in an RCU priority inversion
very shortly after it comes online.
This commit therefore moves the checking to rcu_prepare_kthreads(), which
is called only at early boot, when the check is appropriate. In addition,
it makes rcutree_prepare_cpu() invoke rcu_spawn_one_boost_kthread(), which
no longer does any checking for online CPUs.
With this change, RCU priority boosting tests now pass for short rcutorture
runs, even with single-CPU leaf rcu_node structures.
Cc: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
Cc: Scott Wood <swood@redhat.com>
Cc: Thomas Gleixner <tglx@linutronix.de>
Signed-off-by: Paul E. McKenney <paulmck@kernel.org>
---
kernel/rcu/tree.c | 2 +-
kernel/rcu/tree.h | 2 +-
kernel/rcu/tree_plugin.h | 29 +++++++----------------------
3 files changed, 9 insertions(+), 24 deletions(-)
diff --git a/kernel/rcu/tree.c b/kernel/rcu/tree.c
index 2532e584e95f..00a3ebca70b8 100644
--- a/kernel/rcu/tree.c
+++ b/kernel/rcu/tree.c
@@ -4166,7 +4166,7 @@ int rcutree_prepare_cpu(unsigned int cpu)
rdp->rcu_iw_gp_seq = rdp->gp_seq - 1;
trace_rcu_grace_period(rcu_state.name, rdp->gp_seq, TPS("cpuonl"));
raw_spin_unlock_irqrestore_rcu_node(rnp, flags);
- rcu_prepare_kthreads(cpu);
+ rcu_spawn_one_boost_kthread(rnp);
rcu_spawn_cpu_nocb_kthread(cpu);
WRITE_ONCE(rcu_state.n_online_cpus, rcu_state.n_online_cpus + 1);
diff --git a/kernel/rcu/tree.h b/kernel/rcu/tree.h
index 5fd0c443517e..b5508f44ff29 100644
--- a/kernel/rcu/tree.h
+++ b/kernel/rcu/tree.h
@@ -418,8 +418,8 @@ static void rcu_initiate_boost(struct rcu_node *rnp, unsigned long flags);
static void rcu_preempt_boost_start_gp(struct rcu_node *rnp);
static bool rcu_is_callbacks_kthread(void);
static void rcu_cpu_kthread_setup(unsigned int cpu);
+static void rcu_spawn_one_boost_kthread(struct rcu_node *rnp);
static void __init rcu_spawn_boost_kthreads(void);
-static void rcu_prepare_kthreads(int cpu);
static void rcu_cleanup_after_idle(void);
static void rcu_prepare_for_idle(void);
static bool rcu_preempt_has_tasks(struct rcu_node *rnp);
diff --git a/kernel/rcu/tree_plugin.h b/kernel/rcu/tree_plugin.h
index ef004cc7101d..3c90dad00d3c 100644
--- a/kernel/rcu/tree_plugin.h
+++ b/kernel/rcu/tree_plugin.h
@@ -1198,22 +1198,16 @@ static void rcu_preempt_boost_start_gp(struct rcu_node *rnp)
*/
static void rcu_spawn_one_boost_kthread(struct rcu_node *rnp)
{
- int rnp_index = rnp - rcu_get_root();
unsigned long flags;
+ int rnp_index = rnp - rcu_get_root();
struct sched_param sp;
struct task_struct *t;
- if (!IS_ENABLED(CONFIG_PREEMPT_RCU))
- return;
-
- if (!rcu_scheduler_fully_active || rcu_rnp_online_cpus(rnp) == 0)
+ if (rnp->boost_kthread_task || !rcu_scheduler_fully_active)
return;
rcu_state.boost = 1;
- if (rnp->boost_kthread_task != NULL)
- return;
-
t = kthread_create(rcu_boost_kthread, (void *)rnp,
"rcub/%d", rnp_index);
if (WARN_ON_ONCE(IS_ERR(t)))
@@ -1265,17 +1259,8 @@ static void __init rcu_spawn_boost_kthreads(void)
struct rcu_node *rnp;
rcu_for_each_leaf_node(rnp)
- rcu_spawn_one_boost_kthread(rnp);
-}
-
-static void rcu_prepare_kthreads(int cpu)
-{
- struct rcu_data *rdp = per_cpu_ptr(&rcu_data, cpu);
- struct rcu_node *rnp = rdp->mynode;
-
- /* Fire up the incoming CPU's kthread and leaf rcu_node kthread. */
- if (rcu_scheduler_fully_active)
- rcu_spawn_one_boost_kthread(rnp);
+ if (rcu_rnp_online_cpus(rnp))
+ rcu_spawn_one_boost_kthread(rnp);
}
#else /* #ifdef CONFIG_RCU_BOOST */
@@ -1295,15 +1280,15 @@ static void rcu_preempt_boost_start_gp(struct rcu_node *rnp)
{
}
-static void rcu_boost_kthread_setaffinity(struct rcu_node *rnp, int outgoingcpu)
+static void rcu_spawn_one_boost_kthread(struct rcu_node *rnp)
{
}
-static void __init rcu_spawn_boost_kthreads(void)
+static void rcu_boost_kthread_setaffinity(struct rcu_node *rnp, int outgoingcpu)
{
}
-static void rcu_prepare_kthreads(int cpu)
+static void __init rcu_spawn_boost_kthreads(void)
{
}
--
2.31.1.189.g2e36527f23
next prev parent reply other threads:[~2021-05-11 22:53 UTC|newest]
Thread overview: 20+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-05-11 22:52 [PATCH tip/core/rcu 0/19] Miscellaneous fixes for v5.14 Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 01/19] rcu: Fix typo in comment: kthead -> kthread Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 02/19] rcu: Remove the unused rcu_irq_exit_preempt() function Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 03/19] rcu: Improve tree.c comments and add code cleanups Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 04/19] rcu: Invoke rcu_spawn_core_kthreads() from rcu_spawn_gp_kthread() Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 05/19] rcu: Add ->rt_priority and ->gp_start to show_rcu_gp_kthreads() output Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 06/19] rcu: Add ->gp_max " Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 07/19] lockdep: Explicitly flag likely false-positive report Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 08/19] rcu: Reject RCU_LOCKDEP_WARN() false positives Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 09/19] rcu: Add quiescent states and boost states to show_rcu_gp_kthreads() output Paul E. McKenney
2021-05-11 22:52 ` Paul E. McKenney [this message]
2021-05-11 22:52 ` [PATCH tip/core/rcu 11/19] rcu: Make show_rcu_gp_kthreads() dump rcu_node structures blocking GP Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 12/19] rcu: Restrict RCU_STRICT_GRACE_PERIOD to at most four CPUs Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 13/19] rcu: Make rcu_gp_cleanup() be noinline for tracing Paul E. McKenney
2021-05-11 22:52 ` [PATCH tip/core/rcu 14/19] rcu: Point to documentation of ordering guarantees Paul E. McKenney
2021-05-11 22:53 ` [PATCH tip/core/rcu 15/19] rcu: Create an unrcu_pointer() to remove __rcu from a pointer Paul E. McKenney
2021-05-11 22:53 ` [PATCH tip/core/rcu 16/19] sched/isolation: reconcile rcu_nocbs= and nohz_full= Paul E. McKenney
2021-05-11 22:53 ` [PATCH tip/core/rcu 17/19] rcu: Improve comments describing RCU read-side critical sections Paul E. McKenney
2021-05-11 22:53 ` [PATCH tip/core/rcu 18/19] rcu: Remove obsolete rcu_read_unlock() deadlock commentary Paul E. McKenney
2021-05-11 22:53 ` [PATCH tip/core/rcu 19/19] rcu: Add missing __releases() annotation Paul E. McKenney
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=20210511225304.2893154-10-paulmck@kernel.org \
--to=paulmck@kernel.org \
--cc=akpm@linux-foundation.org \
--cc=bigeasy@linutronix.de \
--cc=dhowells@redhat.com \
--cc=edumazet@google.com \
--cc=fweisbec@gmail.com \
--cc=jiangshanlai@gmail.com \
--cc=joel@joelfernandes.org \
--cc=josh@joshtriplett.org \
--cc=kernel-team@fb.com \
--cc=linux-kernel@vger.kernel.org \
--cc=mathieu.desnoyers@efficios.com \
--cc=mingo@kernel.org \
--cc=oleg@redhat.com \
--cc=peterz@infradead.org \
--cc=rcu@vger.kernel.org \
--cc=rostedt@goodmis.org \
--cc=swood@redhat.com \
--cc=tglx@linutronix.de \
/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