rcu: Pull rcu_gp_kthread() FQS loop into separate function
The rcu_gp_kthread() function is long and deeply indented, so this commit pulls the loop that repeatedly invokes rcu_gp_fqs() into a new rcu_gp_fqs_loop() function. Signed-off-by: Paul E. McKenney <paulmck@linux.vnet.ibm.com>
This commit is contained in:
parent
4e95020cdd
commit
c3854a055b
|
@ -1976,6 +1976,71 @@ static void rcu_gp_fqs(bool first_time)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Loop doing repeated quiescent-state forcing until the grace period ends.
|
||||
*/
|
||||
static void rcu_gp_fqs_loop(void)
|
||||
{
|
||||
bool first_gp_fqs;
|
||||
int gf;
|
||||
unsigned long j;
|
||||
int ret;
|
||||
struct rcu_node *rnp = rcu_get_root();
|
||||
|
||||
first_gp_fqs = true;
|
||||
j = jiffies_till_first_fqs;
|
||||
ret = 0;
|
||||
for (;;) {
|
||||
if (!ret) {
|
||||
rcu_state.jiffies_force_qs = jiffies + j;
|
||||
WRITE_ONCE(rcu_state.jiffies_kick_kthreads,
|
||||
jiffies + 3 * j);
|
||||
}
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqswait"));
|
||||
rcu_state.gp_state = RCU_GP_WAIT_FQS;
|
||||
ret = swait_event_idle_timeout_exclusive(
|
||||
rcu_state.gp_wq, rcu_gp_fqs_check_wake(&gf), j);
|
||||
rcu_state.gp_state = RCU_GP_DOING_FQS;
|
||||
/* Locking provides needed memory barriers. */
|
||||
/* If grace period done, leave loop. */
|
||||
if (!READ_ONCE(rnp->qsmask) &&
|
||||
!rcu_preempt_blocked_readers_cgp(rnp))
|
||||
break;
|
||||
/* If time for quiescent-state forcing, do it. */
|
||||
if (ULONG_CMP_GE(jiffies, rcu_state.jiffies_force_qs) ||
|
||||
(gf & RCU_GP_FLAG_FQS)) {
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqsstart"));
|
||||
rcu_gp_fqs(first_gp_fqs);
|
||||
first_gp_fqs = false;
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqsend"));
|
||||
cond_resched_tasks_rcu_qs();
|
||||
WRITE_ONCE(rcu_state.gp_activity, jiffies);
|
||||
ret = 0; /* Force full wait till next FQS. */
|
||||
j = jiffies_till_next_fqs;
|
||||
} else {
|
||||
/* Deal with stray signal. */
|
||||
cond_resched_tasks_rcu_qs();
|
||||
WRITE_ONCE(rcu_state.gp_activity, jiffies);
|
||||
WARN_ON(signal_pending(current));
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqswaitsig"));
|
||||
ret = 1; /* Keep old FQS timing. */
|
||||
j = jiffies;
|
||||
if (time_after(jiffies, rcu_state.jiffies_force_qs))
|
||||
j = 1;
|
||||
else
|
||||
j = rcu_state.jiffies_force_qs - j;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Clean up after the old grace period.
|
||||
*/
|
||||
|
@ -2066,12 +2131,6 @@ static void rcu_gp_cleanup(void)
|
|||
*/
|
||||
static int __noreturn rcu_gp_kthread(void *unused)
|
||||
{
|
||||
bool first_gp_fqs;
|
||||
int gf;
|
||||
unsigned long j;
|
||||
int ret;
|
||||
struct rcu_node *rnp = rcu_get_root();
|
||||
|
||||
rcu_bind_gp_kthread();
|
||||
for (;;) {
|
||||
|
||||
|
@ -2097,59 +2156,7 @@ static int __noreturn rcu_gp_kthread(void *unused)
|
|||
}
|
||||
|
||||
/* Handle quiescent-state forcing. */
|
||||
first_gp_fqs = true;
|
||||
j = jiffies_till_first_fqs;
|
||||
ret = 0;
|
||||
for (;;) {
|
||||
if (!ret) {
|
||||
rcu_state.jiffies_force_qs = jiffies + j;
|
||||
WRITE_ONCE(rcu_state.jiffies_kick_kthreads,
|
||||
jiffies + 3 * j);
|
||||
}
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqswait"));
|
||||
rcu_state.gp_state = RCU_GP_WAIT_FQS;
|
||||
ret = swait_event_idle_timeout_exclusive(rcu_state.gp_wq,
|
||||
rcu_gp_fqs_check_wake(&gf), j);
|
||||
rcu_state.gp_state = RCU_GP_DOING_FQS;
|
||||
/* Locking provides needed memory barriers. */
|
||||
/* If grace period done, leave loop. */
|
||||
if (!READ_ONCE(rnp->qsmask) &&
|
||||
!rcu_preempt_blocked_readers_cgp(rnp))
|
||||
break;
|
||||
/* If time for quiescent-state forcing, do it. */
|
||||
if (ULONG_CMP_GE(jiffies, rcu_state.jiffies_force_qs) ||
|
||||
(gf & RCU_GP_FLAG_FQS)) {
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqsstart"));
|
||||
rcu_gp_fqs(first_gp_fqs);
|
||||
first_gp_fqs = false;
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqsend"));
|
||||
cond_resched_tasks_rcu_qs();
|
||||
WRITE_ONCE(rcu_state.gp_activity, jiffies);
|
||||
ret = 0; /* Force full wait till next FQS. */
|
||||
j = jiffies_till_next_fqs;
|
||||
} else {
|
||||
/* Deal with stray signal. */
|
||||
cond_resched_tasks_rcu_qs();
|
||||
WRITE_ONCE(rcu_state.gp_activity, jiffies);
|
||||
WARN_ON(signal_pending(current));
|
||||
trace_rcu_grace_period(rcu_state.name,
|
||||
READ_ONCE(rcu_state.gp_seq),
|
||||
TPS("fqswaitsig"));
|
||||
ret = 1; /* Keep old FQS timing. */
|
||||
j = jiffies;
|
||||
if (time_after(jiffies,
|
||||
rcu_state.jiffies_force_qs))
|
||||
j = 1;
|
||||
else
|
||||
j = rcu_state.jiffies_force_qs - j;
|
||||
}
|
||||
}
|
||||
rcu_gp_fqs_loop();
|
||||
|
||||
/* Handle grace-period end. */
|
||||
rcu_state.gp_state = RCU_GP_CLEANUP;
|
||||
|
|
Loading…
Reference in New Issue