// SPDX-License-Identifier: GPL-2.0+
/*
 * Read-Copy Update module-based torture test facility
 *
 * Copyright (C) IBM Corporation, 2005, 2006
 *
 * Authors: Paul E. McKenney <paulmck@linux.ibm.com>
 *	  Josh Triplett <josh@joshtriplett.org>
 *
 * See also:  Documentation/RCU/torture.rst
 */

#define pr_fmt(fmt) fmt

#include <linux/types.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/kthread.h>
#include <linux/err.h>
#include <linux/spinlock.h>
#include <linux/smp.h>
#include <linux/rcupdate_wait.h>
#include <linux/interrupt.h>
#include <linux/sched/signal.h>
#include <uapi/linux/sched/types.h>
#include <linux/atomic.h>
#include <linux/bitops.h>
#include <linux/completion.h>
#include <linux/moduleparam.h>
#include <linux/percpu.h>
#include <linux/notifier.h>
#include <linux/reboot.h>
#include <linux/freezer.h>
#include <linux/cpu.h>
#include <linux/delay.h>
#include <linux/stat.h>
#include <linux/srcu.h>
#include <linux/slab.h>
#include <linux/trace_clock.h>
#include <asm/byteorder.h>
#include <linux/torture.h>
#include <linux/vmalloc.h>
#include <linux/sched/debug.h>
#include <linux/sched/sysctl.h>
#include <linux/oom.h>
#include <linux/tick.h>
#include <linux/rcupdate_trace.h>
#include <linux/nmi.h>

#include "rcu.h"

MODULE_LICENSE("GPL");
MODULE_AUTHOR("Paul E. McKenney <paulmck@linux.ibm.com> and Josh Triplett <josh@joshtriplett.org>");

/* Bits for ->extendables field, extendables param, and related definitions. */
#define RCUTORTURE_RDR_SHIFT_1	 8	/* Put SRCU index in upper bits. */
#define RCUTORTURE_RDR_MASK_1	 (1 << RCUTORTURE_RDR_SHIFT_1)
#define RCUTORTURE_RDR_SHIFT_2	 9	/* Put SRCU index in upper bits. */
#define RCUTORTURE_RDR_MASK_2	 (1 << RCUTORTURE_RDR_SHIFT_2)
#define RCUTORTURE_RDR_BH	 0x01	/* Extend readers by disabling bh. */
#define RCUTORTURE_RDR_IRQ	 0x02	/*  ... disabling interrupts. */
#define RCUTORTURE_RDR_PREEMPT	 0x04	/*  ... disabling preemption. */
#define RCUTORTURE_RDR_RBH	 0x08	/*  ... rcu_read_lock_bh(). */
#define RCUTORTURE_RDR_SCHED	 0x10	/*  ... rcu_read_lock_sched(). */
#define RCUTORTURE_RDR_RCU_1	 0x20	/*  ... entering another RCU reader. */
#define RCUTORTURE_RDR_RCU_2	 0x40	/*  ... entering another RCU reader. */
#define RCUTORTURE_RDR_NBITS	 7	/* Number of bits defined above. */
#define RCUTORTURE_MAX_EXTEND	 \
	(RCUTORTURE_RDR_BH | RCUTORTURE_RDR_IRQ | RCUTORTURE_RDR_PREEMPT | \
	 RCUTORTURE_RDR_RBH | RCUTORTURE_RDR_SCHED)
#define RCUTORTURE_RDR_MAX_LOOPS 0x7	/* Maximum reader extensions. */
					/* Must be power of two minus one. */
#define RCUTORTURE_RDR_MAX_SEGS (RCUTORTURE_RDR_MAX_LOOPS + 3)

torture_param(int, extendables, RCUTORTURE_MAX_EXTEND,
	      "Extend readers by disabling bh (1), irqs (2), or preempt (4)");
torture_param(int, fqs_duration, 0,
	      "Duration of fqs bursts (us), 0 to disable");
torture_param(int, fqs_holdoff, 0, "Holdoff time within fqs bursts (us)");
torture_param(int, fqs_stutter, 3, "Wait time between fqs bursts (s)");
torture_param(int, fwd_progress, 1, "Test grace-period forward progress");
torture_param(int, fwd_progress_div, 4, "Fraction of CPU stall to wait");
torture_param(int, fwd_progress_holdoff, 60,
	      "Time between forward-progress tests (s)");
torture_param(bool, fwd_progress_need_resched, 1,
	      "Hide cond_resched() behind need_resched()");
torture_param(bool, gp_cond, false, "Use conditional/async GP wait primitives");
torture_param(bool, gp_exp, false, "Use expedited GP wait primitives");
torture_param(bool, gp_normal, false,
	     "Use normal (non-expedited) GP wait primitives");
torture_param(bool, gp_poll, false, "Use polling GP wait primitives");
torture_param(bool, gp_sync, false, "Use synchronous GP wait primitives");
torture_param(int, irqreader, 1, "Allow RCU readers from irq handlers");
torture_param(int, leakpointer, 0, "Leak pointer dereferences from readers");
torture_param(int, n_barrier_cbs, 0,
	     "# of callbacks/kthreads for barrier testing");
torture_param(int, nfakewriters, 4, "Number of RCU fake writer threads");
torture_param(int, nreaders, -1, "Number of RCU reader threads");
torture_param(int, object_debug, 0,
	     "Enable debug-object double call_rcu() testing");
torture_param(int, onoff_holdoff, 0, "Time after boot before CPU hotplugs (s)");
torture_param(int, onoff_interval, 0,
	     "Time between CPU hotplugs (jiffies), 0=disable");
torture_param(int, nocbs_nthreads, 0, "Number of NOCB toggle threads, 0 to disable");
torture_param(int, nocbs_toggle, 1000, "Time between toggling nocb state (ms)");
torture_param(int, read_exit_delay, 13,
	      "Delay between read-then-exit episodes (s)");
torture_param(int, read_exit_burst, 16,
	      "# of read-then-exit bursts per episode, zero to disable");
torture_param(int, shuffle_interval, 3, "Number of seconds between shuffles");
torture_param(int, shutdown_secs, 0, "Shutdown time (s), <= zero to disable.");
torture_param(int, stall_cpu, 0, "Stall duration (s), zero to disable.");
torture_param(int, stall_cpu_holdoff, 10,
	     "Time to wait before starting stall (s).");
torture_param(bool, stall_no_softlockup, false,
	     "Avoid softlockup warning during cpu stall.");
torture_param(int, stall_cpu_irqsoff, 0, "Disable interrupts while stalling.");
torture_param(int, stall_cpu_block, 0, "Sleep while stalling.");
torture_param(int, stall_gp_kthread, 0,
	      "Grace-period kthread stall duration (s).");
torture_param(int, stat_interval, 60,
	     "Number of seconds between stats printk()s");
torture_param(int, stutter, 5, "Number of seconds to run/halt test");
torture_param(int, test_boost, 1, "Test RCU prio boost: 0=no, 1=maybe, 2=yes.");
torture_param(int, test_boost_duration, 4,
	     "Duration of each boost test, seconds.");
torture_param(int, test_boost_interval, 7,
	     "Interval between boost tests, seconds.");
torture_param(bool, test_no_idle_hz, true,
	     "Test support for tickless idle CPUs");
torture_param(int, verbose, 1,
	     "Enable verbose debugging printk()s");

static char *torture_type = "rcu";
module_param(torture_type, charp, 0444);
MODULE_PARM_DESC(torture_type, "Type of RCU to torture (rcu, srcu, ...)");

static int nrealnocbers;
static int nrealreaders;
static struct task_struct *writer_task;
static struct task_struct **fakewriter_tasks;
static struct task_struct **reader_tasks;
static struct task_struct **nocb_tasks;
static struct task_struct *stats_task;
static struct task_struct *fqs_task;
static struct task_struct *boost_tasks[NR_CPUS];
static struct task_struct *stall_task;
static struct task_struct **fwd_prog_tasks;
static struct task_struct **barrier_cbs_tasks;
static struct task_struct *barrier_task;
static struct task_struct *read_exit_task;

#define RCU_TORTURE_PIPE_LEN 10

// Mailbox-like structure to check RCU global memory ordering.
struct rcu_torture_reader_check {
	unsigned long rtc_myloops;
	int rtc_chkrdr;
	unsigned long rtc_chkloops;
	int rtc_ready;
	struct rcu_torture_reader_check *rtc_assigner;
} ____cacheline_internodealigned_in_smp;

// Update-side data structure used to check RCU readers.
struct rcu_torture {
	struct rcu_head rtort_rcu;
	int rtort_pipe_count;
	struct list_head rtort_free;
	int rtort_mbtest;
	struct rcu_torture_reader_check *rtort_chkp;
};

static LIST_HEAD(rcu_torture_freelist);
static struct rcu_torture __rcu *rcu_torture_current;
static unsigned long rcu_torture_current_version;
static struct rcu_torture rcu_tortures[10 * RCU_TORTURE_PIPE_LEN];
static DEFINE_SPINLOCK(rcu_torture_lock);
static DEFINE_PER_CPU(long [RCU_TORTURE_PIPE_LEN + 1], rcu_torture_count);
static DEFINE_PER_CPU(long [RCU_TORTURE_PIPE_LEN + 1], rcu_torture_batch);
static atomic_t rcu_torture_wcount[RCU_TORTURE_PIPE_LEN + 1];
static struct rcu_torture_reader_check *rcu_torture_reader_mbchk;
static atomic_t n_rcu_torture_alloc;
static atomic_t n_rcu_torture_alloc_fail;
static atomic_t n_rcu_torture_free;
static atomic_t n_rcu_torture_mberror;
static atomic_t n_rcu_torture_mbchk_fail;
static atomic_t n_rcu_torture_mbchk_tries;
static atomic_t n_rcu_torture_error;
static long n_rcu_torture_barrier_error;
static long n_rcu_torture_boost_ktrerror;
static long n_rcu_torture_boost_rterror;
static long n_rcu_torture_boost_failure;
static long n_rcu_torture_boosts;
static atomic_long_t n_rcu_torture_timers;
static long n_barrier_attempts;
static long n_barrier_successes; /* did rcu_barrier test succeed? */
static unsigned long n_read_exits;
static struct list_head rcu_torture_removed;
static unsigned long shutdown_jiffies;
static unsigned long start_gp_seq;
static atomic_long_t n_nocb_offload;
static atomic_long_t n_nocb_deoffload;

static int rcu_torture_writer_state;
#define RTWS_FIXED_DELAY	0
#define RTWS_DELAY		1
#define RTWS_REPLACE		2
#define RTWS_DEF_FREE		3
#define RTWS_EXP_SYNC		4
#define RTWS_COND_GET		5
#define RTWS_COND_SYNC		6
#define RTWS_POLL_GET		7
#define RTWS_POLL_WAIT		8
#define RTWS_SYNC		9
#define RTWS_STUTTER		10
#define RTWS_STOPPING		11
static const char * const rcu_torture_writer_state_names[] = {
	"RTWS_FIXED_DELAY",
	"RTWS_DELAY",
	"RTWS_REPLACE",
	"RTWS_DEF_FREE",
	"RTWS_EXP_SYNC",
	"RTWS_COND_GET",
	"RTWS_COND_SYNC",
	"RTWS_POLL_GET",
	"RTWS_POLL_WAIT",
	"RTWS_SYNC",
	"RTWS_STUTTER",
	"RTWS_STOPPING",
};

/* Record reader segment types and duration for first failing read. */
struct rt_read_seg {
	int rt_readstate;
	unsigned long rt_delay_jiffies;
	unsigned long rt_delay_ms;
	unsigned long rt_delay_us;
	bool rt_preempted;
};
static int err_segs_recorded;
static struct rt_read_seg err_segs[RCUTORTURE_RDR_MAX_SEGS];
static int rt_read_nsegs;

static const char *rcu_torture_writer_state_getname(void)
{
	unsigned int i = READ_ONCE(rcu_torture_writer_state);

	if (i >= ARRAY_SIZE(rcu_torture_writer_state_names))
		return "???";
	return rcu_torture_writer_state_names[i];
}

#ifdef CONFIG_RCU_TRACE
static u64 notrace rcu_trace_clock_local(void)
{
	u64 ts = trace_clock_local();

	(void)do_div(ts, NSEC_PER_USEC);
	return ts;
}
#else /* #ifdef CONFIG_RCU_TRACE */
static u64 notrace rcu_trace_clock_local(void)
{
	return 0ULL;
}
#endif /* #else #ifdef CONFIG_RCU_TRACE */

/*
 * Stop aggressive CPU-hog tests a bit before the end of the test in order
 * to avoid interfering with test shutdown.
 */
static bool shutdown_time_arrived(void)
{
	return shutdown_secs && time_after(jiffies, shutdown_jiffies - 30 * HZ);
}

static unsigned long boost_starttime;	/* jiffies of next boost test start. */
static DEFINE_MUTEX(boost_mutex);	/* protect setting boost_starttime */
					/*  and boost task create/destroy. */
static atomic_t barrier_cbs_count;	/* Barrier callbacks registered. */
static bool barrier_phase;		/* Test phase. */
static atomic_t barrier_cbs_invoked;	/* Barrier callbacks invoked. */
static wait_queue_head_t *barrier_cbs_wq; /* Coordinate barrier testing. */
static DECLARE_WAIT_QUEUE_HEAD(barrier_wq);

static atomic_t rcu_fwd_cb_nodelay;	/* Short rcu_torture_delay() delays. */

/*
 * Allocate an element from the rcu_tortures pool.
 */
static struct rcu_torture *
rcu_torture_alloc(void)
{
	struct list_head *p;

	spin_lock_bh(&rcu_torture_lock);
	if (list_empty(&rcu_torture_freelist)) {
		atomic_inc(&n_rcu_torture_alloc_fail);
		spin_unlock_bh(&rcu_torture_lock);
		return NULL;
	}
	atomic_inc(&n_rcu_torture_alloc);
	p = rcu_torture_freelist.next;
	list_del_init(p);
	spin_unlock_bh(&rcu_torture_lock);
	return container_of(p, struct rcu_torture, rtort_free);
}

/*
 * Free an element to the rcu_tortures pool.
 */
static void
rcu_torture_free(struct rcu_torture *p)
{
	atomic_inc(&n_rcu_torture_free);
	spin_lock_bh(&rcu_torture_lock);
	list_add_tail(&p->rtort_free, &rcu_torture_freelist);
	spin_unlock_bh(&rcu_torture_lock);
}

/*
 * Operations vector for selecting different types of tests.
 */

struct rcu_torture_ops {
	int ttype;
	void (*init)(void);
	void (*cleanup)(void);
	int (*readlock)(void);
	void (*read_delay)(struct torture_random_state *rrsp,
			   struct rt_read_seg *rtrsp);
	void (*readunlock)(int idx);
	int (*readlock_held)(void);
	unsigned long (*get_gp_seq)(void);
	unsigned long (*gp_diff)(unsigned long new, unsigned long old);
	void (*deferred_free)(struct rcu_torture *p);
	void (*sync)(void);
	void (*exp_sync)(void);
	unsigned long (*get_gp_state)(void);
	unsigned long (*start_gp_poll)(void);
	bool (*poll_gp_state)(unsigned long oldstate);
	void (*cond_sync)(unsigned long oldstate);
	call_rcu_func_t call;
	void (*cb_barrier)(void);
	void (*fqs)(void);
	void (*stats)(void);
	void (*gp_kthread_dbg)(void);
	bool (*check_boost_failed)(unsigned long gp_state, int *cpup);
	int (*stall_dur)(void);
	long cbflood_max;
	int irq_capable;
	int can_boost;
	int extendables;
	int slow_gps;
	int no_pi_lock;
	const char *name;
};

static struct rcu_torture_ops *cur_ops;

/*
 * Definitions for rcu torture testing.
 */

static int torture_readlock_not_held(void)
{
	return rcu_read_lock_bh_held() || rcu_read_lock_sched_held();
}

static int rcu_torture_read_lock(void) __acquires(RCU)
{
	rcu_read_lock();
	return 0;
}

static void
rcu_read_delay(struct torture_random_state *rrsp, struct rt_read_seg *rtrsp)
{
	unsigned long started;
	unsigned long completed;
	const unsigned long shortdelay_us = 200;
	unsigned long longdelay_ms = 300;
	unsigned long long ts;

	/* We want a short delay sometimes to make a reader delay the grace
	 * period, and we want a long delay occasionally to trigger
	 * force_quiescent_state. */

	if (!atomic_read(&rcu_fwd_cb_nodelay) &&
	    !(torture_random(rrsp) % (nrealreaders * 2000 * longdelay_ms))) {
		started = cur_ops->get_gp_seq();
		ts = rcu_trace_clock_local();
		if (preempt_count() & (SOFTIRQ_MASK | HARDIRQ_MASK))
			longdelay_ms = 5; /* Avoid triggering BH limits. */
		mdelay(longdelay_ms);
		rtrsp->rt_delay_ms = longdelay_ms;
		completed = cur_ops->get_gp_seq();
		do_trace_rcu_torture_read(cur_ops->name, NULL, ts,
					  started, completed);
	}
	if (!(torture_random(rrsp) % (nrealreaders * 2 * shortdelay_us))) {
		udelay(shortdelay_us);
		rtrsp->rt_delay_us = shortdelay_us;
	}
	if (!preempt_count() &&
	    !(torture_random(rrsp) % (nrealreaders * 500))) {
		torture_preempt_schedule();  /* QS only if preemptible. */
		rtrsp->rt_preempted = true;
	}
}

static void rcu_torture_read_unlock(int idx) __releases(RCU)
{
	rcu_read_unlock();
}

/*
 * Update callback in the pipe.  This should be invoked after a grace period.
 */
static bool
rcu_torture_pipe_update_one(struct rcu_torture *rp)
{
	int i;
	struct rcu_torture_reader_check *rtrcp = READ_ONCE(rp->rtort_chkp);

	if (rtrcp) {
		WRITE_ONCE(rp->rtort_chkp, NULL);
		smp_store_release(&rtrcp->rtc_ready, 1); // Pair with smp_load_acquire().
	}
	i = READ_ONCE(rp->rtort_pipe_count);
	if (i > RCU_TORTURE_PIPE_LEN)
		i = RCU_TORTURE_PIPE_LEN;
	atomic_inc(&rcu_torture_wcount[i]);
	WRITE_ONCE(rp->rtort_pipe_count, i + 1);
	if (rp->rtort_pipe_count >= RCU_TORTURE_PIPE_LEN) {
		rp->rtort_mbtest = 0;
		return true;
	}
	return false;
}

/*
 * Update all callbacks in the pipe.  Suitable for synchronous grace-period
 * primitives.
 */
static void
rcu_torture_pipe_update(struct rcu_torture *old_rp)
{
	struct rcu_torture *rp;
	struct rcu_torture *rp1;

	if (old_rp)
		list_add(&old_rp->rtort_free, &rcu_torture_removed);
	list_for_each_entry_safe(rp, rp1, &rcu_torture_removed, rtort_free) {
		if (rcu_torture_pipe_update_one(rp)) {
			list_del(&rp->rtort_free);
			rcu_torture_free(rp);
		}
	}
}

static void
rcu_torture_cb(struct rcu_head *p)
{
	struct rcu_torture *rp = container_of(p, struct rcu_torture, rtort_rcu);

	if (torture_must_stop_irq()) {
		/* Test is ending, just drop callbacks on the floor. */
		/* The next initialization will pick up the pieces. */
		return;
	}
	if (rcu_torture_pipe_update_one(rp))
		rcu_torture_free(rp);
	else
		cur_ops->deferred_free(rp);
}

static unsigned long rcu_no_completed(void)
{
	return 0;
}

static void rcu_torture_deferred_free(struct rcu_torture *p)
{
	call_rcu(&p->rtort_rcu, rcu_torture_cb);
}

static void rcu_sync_torture_init(void)
{
	INIT_LIST_HEAD(&rcu_torture_removed);
}

static struct rcu_torture_ops rcu_ops = {
	.ttype			= RCU_FLAVOR,
	.init			= rcu_sync_torture_init,
	.readlock		= rcu_torture_read_lock,
	.read_delay		= rcu_read_delay,
	.readunlock		= rcu_torture_read_unlock,
	.readlock_held		= torture_readlock_not_held,
	.get_gp_seq		= rcu_get_gp_seq,
	.gp_diff		= rcu_seq_diff,
	.deferred_free		= rcu_torture_deferred_free,
	.sync			= synchronize_rcu,
	.exp_sync		= synchronize_rcu_expedited,
	.get_gp_state		= get_state_synchronize_rcu,
	.start_gp_poll		= start_poll_synchronize_rcu,
	.poll_gp_state		= poll_state_synchronize_rcu,
	.cond_sync		= cond_synchronize_rcu,
	.call			= call_rcu,
	.cb_barrier		= rcu_barrier,
	.fqs			= rcu_force_quiescent_state,
	.stats			= NULL,
	.gp_kthread_dbg		= show_rcu_gp_kthreads,
	.check_boost_failed	= rcu_check_boost_fail,
	.stall_dur		= rcu_jiffies_till_stall_check,
	.irq_capable		= 1,
	.can_boost		= IS_ENABLED(CONFIG_RCU_BOOST),
	.extendables		= RCUTORTURE_MAX_EXTEND,
	.name			= "rcu"
};

/*
 * Don't even think about trying any of these in real life!!!
 * The names includes "busted", and they really means it!
 * The only purpose of these functions is to provide a buggy RCU
 * implementation to make sure that rcutorture correctly emits
 * buggy-RCU error messages.
 */
static void rcu_busted_torture_deferred_free(struct rcu_torture *p)
{
	/* This is a deliberate bug for testing purposes only! */
	rcu_torture_cb(&p->rtort_rcu);
}

static void synchronize_rcu_busted(void)
{
	/* This is a deliberate bug for testing purposes only! */
}

static void
call_rcu_busted(struct rcu_head *head, rcu_callback_t func)
{
	/* This is a deliberate bug for testing purposes only! */
	func(head);
}

static struct rcu_torture_ops rcu_busted_ops = {
	.ttype		= INVALID_RCU_FLAVOR,
	.init		= rcu_sync_torture_init,
	.readlock	= rcu_torture_read_lock,
	.read_delay	= rcu_read_delay,  /* just reuse rcu's version. */
	.readunlock	= rcu_torture_read_unlock,
	.readlock_held	= torture_readlock_not_held,
	.get_gp_seq	= rcu_no_completed,
	.deferred_free	= rcu_busted_torture_deferred_free,
	.sync		= synchronize_rcu_busted,
	.exp_sync	= synchronize_rcu_busted,
	.call		= call_rcu_busted,
	.cb_barrier	= NULL,
	.fqs		= NULL,
	.stats		= NULL,
	.irq_capable	= 1,
	.name		= "busted"
};

/*
 * Definitions for srcu torture testing.
 */

DEFINE_STATIC_SRCU(srcu_ctl);
static struct srcu_struct srcu_ctld;
static struct srcu_struct *srcu_ctlp = &srcu_ctl;

static int srcu_torture_read_lock(void) __acquires(srcu_ctlp)
{
	return srcu_read_lock(srcu_ctlp);
}

static void
srcu_read_delay(struct torture_random_state *rrsp, struct rt_read_seg *rtrsp)
{
	long delay;
	const long uspertick = 1000000 / HZ;
	const long longdelay = 10;

	/* We want there to be long-running readers, but not all the time. */

	delay = torture_random(rrsp) %
		(nrealreaders * 2 * longdelay * uspertick);
	if (!delay && in_task()) {
		schedule_timeout_interruptible(longdelay);
		rtrsp->rt_delay_jiffies = longdelay;
	} else {
		rcu_read_delay(rrsp, rtrsp);
	}
}

static void srcu_torture_read_unlock(int idx) __releases(srcu_ctlp)
{
	srcu_read_unlock(srcu_ctlp, idx);
}

static int torture_srcu_read_lock_held(void)
{
	return srcu_read_lock_held(srcu_ctlp);
}

static unsigned long srcu_torture_completed(void)
{
	return srcu_batches_completed(srcu_ctlp);
}

static void srcu_torture_deferred_free(struct rcu_torture *rp)
{
	call_srcu(srcu_ctlp, &rp->rtort_rcu, rcu_torture_cb);
}

static void srcu_torture_synchronize(void)
{
	synchronize_srcu(srcu_ctlp);
}

static unsigned long srcu_torture_get_gp_state(void)
{
	return get_state_synchronize_srcu(srcu_ctlp);
}

static unsigned long srcu_torture_start_gp_poll(void)
{
	return start_poll_synchronize_srcu(srcu_ctlp);
}

static bool srcu_torture_poll_gp_state(unsigned long oldstate)
{
	return poll_state_synchronize_srcu(srcu_ctlp, oldstate);
}

static void srcu_torture_call(struct rcu_head *head,
			      rcu_callback_t func)
{
	call_srcu(srcu_ctlp, head, func);
}

static void srcu_torture_barrier(void)
{
	srcu_barrier(srcu_ctlp);
}

static void srcu_torture_stats(void)
{
	srcu_torture_stats_print(srcu_ctlp, torture_type, TORTURE_FLAG);
}

static void srcu_torture_synchronize_expedited(void)
{
	synchronize_srcu_expedited(srcu_ctlp);
}

static struct rcu_torture_ops srcu_ops = {
	.ttype		= SRCU_FLAVOR,
	.init		= rcu_sync_torture_init,
	.readlock	= srcu_torture_read_lock,
	.read_delay	= srcu_read_delay,
	.readunlock	= srcu_torture_read_unlock,
	.readlock_held	= torture_srcu_read_lock_held,
	.get_gp_seq	= srcu_torture_completed,
	.deferred_free	= srcu_torture_deferred_free,
	.sync		= srcu_torture_synchronize,
	.exp_sync	= srcu_torture_synchronize_expedited,
	.get_gp_state	= srcu_torture_get_gp_state,
	.start_gp_poll	= srcu_torture_start_gp_poll,
	.poll_gp_state	= srcu_torture_poll_gp_state,
	.call		= srcu_torture_call,
	.cb_barrier	= srcu_torture_barrier,
	.stats		= srcu_torture_stats,
	.cbflood_max	= 50000,
	.irq_capable	= 1,
	.no_pi_lock	= IS_ENABLED(CONFIG_TINY_SRCU),
	.name		= "srcu"
};

static void srcu_torture_init(void)
{
	rcu_sync_torture_init();
	WARN_ON(init_srcu_struct(&srcu_ctld));
	srcu_ctlp = &srcu_ctld;
}

static void srcu_torture_cleanup(void)
{
	cleanup_srcu_struct(&srcu_ctld);
	srcu_ctlp = &srcu_ctl; /* In case of a later rcutorture run. */
}

/* As above, but dynamically allocated. */
static struct rcu_torture_ops srcud_ops = {
	.ttype		= SRCU_FLAVOR,
	.init		= srcu_torture_init,
	.cleanup	= srcu_torture_cleanup,
	.readlock	= srcu_torture_read_lock,
	.read_delay	= srcu_read_delay,
	.readunlock	= srcu_torture_read_unlock,
	.readlock_held	= torture_srcu_read_lock_held,
	.get_gp_seq	= srcu_torture_completed,
	.deferred_free	= srcu_torture_deferred_free,
	.sync		= srcu_torture_synchronize,
	.exp_sync	= srcu_torture_synchronize_expedited,
	.call		= srcu_torture_call,
	.cb_barrier	= srcu_torture_barrier,
	.stats		= srcu_torture_stats,
	.cbflood_max	= 50000,
	.irq_capable	= 1,
	.no_pi_lock	= IS_ENABLED(CONFIG_TINY_SRCU),
	.name		= "srcud"
};

/* As above, but broken due to inappropriate reader extension. */
static struct rcu_torture_ops busted_srcud_ops = {
	.ttype		= SRCU_FLAVOR,
	.init		= srcu_torture_init,
	.cleanup	= srcu_torture_cleanup,
	.readlock	= srcu_torture_read_lock,
	.read_delay	= rcu_read_delay,
	.readunlock	= srcu_torture_read_unlock,
	.readlock_held	= torture_srcu_read_lock_held,
	.get_gp_seq	= srcu_torture_completed,
	.deferred_free	= srcu_torture_deferred_free,
	.sync		= srcu_torture_synchronize,
	.exp_sync	= srcu_torture_synchronize_expedited,
	.call		= srcu_torture_call,
	.cb_barrier	= srcu_torture_barrier,
	.stats		= srcu_torture_stats,
	.irq_capable	= 1,
	.no_pi_lock	= IS_ENABLED(CONFIG_TINY_SRCU),
	.extendables	= RCUTORTURE_MAX_EXTEND,
	.name		= "busted_srcud"
};

/*
 * Definitions for RCU-tasks torture testing.
 */

static int tasks_torture_read_lock(void)
{
	return 0;
}

static void tasks_torture_read_unlock(int idx)
{
}

static void rcu_tasks_torture_deferred_free(struct rcu_torture *p)
{
	call_rcu_tasks(&p->rtort_rcu, rcu_torture_cb);
}

static void synchronize_rcu_mult_test(void)
{
	synchronize_rcu_mult(call_rcu_tasks, call_rcu);
}

static struct rcu_torture_ops tasks_ops = {
	.ttype		= RCU_TASKS_FLAVOR,
	.init		= rcu_sync_torture_init,
	.readlock	= tasks_torture_read_lock,
	.read_delay	= rcu_read_delay,  /* just reuse rcu's version. */
	.readunlock	= tasks_torture_read_unlock,
	.get_gp_seq	= rcu_no_completed,
	.deferred_free	= rcu_tasks_torture_deferred_free,
	.sync		= synchronize_rcu_tasks,
	.exp_sync	= synchronize_rcu_mult_test,
	.call		= call_rcu_tasks,
	.cb_barrier	= rcu_barrier_tasks,
	.gp_kthread_dbg	= show_rcu_tasks_classic_gp_kthread,
	.fqs		= NULL,
	.stats		= NULL,
	.irq_capable	= 1,
	.slow_gps	= 1,
	.name		= "tasks"
};

/*
 * Definitions for trivial CONFIG_PREEMPT=n-only torture testing.
 * This implementation does not necessarily work well with CPU hotplug.
 */

static void synchronize_rcu_trivial(void)
{
	int cpu;

	for_each_online_cpu(cpu) {
		rcutorture_sched_setaffinity(current->pid, cpumask_of(cpu));
		WARN_ON_ONCE(raw_smp_processor_id() != cpu);
	}
}

static int rcu_torture_read_lock_trivial(void) __acquires(RCU)
{
	preempt_disable();
	return 0;
}

static void rcu_torture_read_unlock_trivial(int idx) __releases(RCU)
{
	preempt_enable();
}

static struct rcu_torture_ops trivial_ops = {
	.ttype		= RCU_TRIVIAL_FLAVOR,
	.init		= rcu_sync_torture_init,
	.readlock	= rcu_torture_read_lock_trivial,
	.read_delay	= rcu_read_delay,  /* just reuse rcu's version. */
	.readunlock	= rcu_torture_read_unlock_trivial,
	.readlock_held	= torture_readlock_not_held,
	.get_gp_seq	= rcu_no_completed,
	.sync		= synchronize_rcu_trivial,
	.exp_sync	= synchronize_rcu_trivial,
	.fqs		= NULL,
	.stats		= NULL,
	.irq_capable	= 1,
	.name		= "trivial"
};

/*
 * Definitions for rude RCU-tasks torture testing.
 */

static void rcu_tasks_rude_torture_deferred_free(struct rcu_torture *p)
{
	call_rcu_tasks_rude(&p->rtort_rcu, rcu_torture_cb);
}

static struct rcu_torture_ops tasks_rude_ops = {
	.ttype		= RCU_TASKS_RUDE_FLAVOR,
	.init		= rcu_sync_torture_init,
	.readlock	= rcu_torture_read_lock_trivial,
	.read_delay	= rcu_read_delay,  /* just reuse rcu's version. */
	.readunlock	= rcu_torture_read_unlock_trivial,
	.get_gp_seq	= rcu_no_completed,
	.deferred_free	= rcu_tasks_rude_torture_deferred_free,
	.sync		= synchronize_rcu_tasks_rude,
	.exp_sync	= synchronize_rcu_tasks_rude,
	.call		= call_rcu_tasks_rude,
	.cb_barrier	= rcu_barrier_tasks_rude,
	.gp_kthread_dbg	= show_rcu_tasks_rude_gp_kthread,
	.cbflood_max	= 50000,
	.fqs		= NULL,
	.stats		= NULL,
	.irq_capable	= 1,
	.name		= "tasks-rude"
};

/*
 * Definitions for tracing RCU-tasks torture testing.
 */

static int tasks_tracing_torture_read_lock(void)
{
	rcu_read_lock_trace();
	return 0;
}

static void tasks_tracing_torture_read_unlock(int idx)
{
	rcu_read_unlock_trace();
}

static void rcu_tasks_tracing_torture_deferred_free(struct rcu_torture *p)
{
	call_rcu_tasks_trace(&p->rtort_rcu, rcu_torture_cb);
}

static struct rcu_torture_ops tasks_tracing_ops = {
	.ttype		= RCU_TASKS_TRACING_FLAVOR,
	.init		= rcu_sync_torture_init,
	.readlock	= tasks_tracing_torture_read_lock,
	.read_delay	= srcu_read_delay,  /* just reuse srcu's version. */
	.readunlock	= tasks_tracing_torture_read_unlock,
	.readlock_held	= rcu_read_lock_trace_held,
	.get_gp_seq	= rcu_no_completed,
	.deferred_free	= rcu_tasks_tracing_torture_deferred_free,
	.sync		= synchronize_rcu_tasks_trace,
	.exp_sync	= synchronize_rcu_tasks_trace,
	.call		= call_rcu_tasks_trace,
	.cb_barrier	= rcu_barrier_tasks_trace,
	.gp_kthread_dbg	= show_rcu_tasks_trace_gp_kthread,
	.cbflood_max	= 50000,
	.fqs		= NULL,
	.stats		= NULL,
	.irq_capable	= 1,
	.slow_gps	= 1,
	.name		= "tasks-tracing"
};

static unsigned long rcutorture_seq_diff(unsigned long new, unsigned long old)
{
	if (!cur_ops->gp_diff)
		return new - old;
	return cur_ops->gp_diff(new, old);
}

/*
 * RCU torture priority-boost testing.  Runs one real-time thread per
 * CPU for moderate bursts, repeatedly starting grace periods and waiting
 * for them to complete.  If a given grace period takes too long, we assume
 * that priority inversion has occurred.
 */

static int old_rt_runtime = -1;

static void rcu_torture_disable_rt_throttle(void)
{
	/*
	 * Disable RT throttling so that rcutorture's boost threads don't get
	 * throttled. Only possible if rcutorture is built-in otherwise the
	 * user should manually do this by setting the sched_rt_period_us and
	 * sched_rt_runtime sysctls.
	 */
	if (!IS_BUILTIN(CONFIG_RCU_TORTURE_TEST) || old_rt_runtime != -1)
		return;

	old_rt_runtime = sysctl_sched_rt_runtime;
	sysctl_sched_rt_runtime = -1;
}

static void rcu_torture_enable_rt_throttle(void)
{
	if (!IS_BUILTIN(CONFIG_RCU_TORTURE_TEST) || old_rt_runtime == -1)
		return;

	sysctl_sched_rt_runtime = old_rt_runtime;
	old_rt_runtime = -1;
}

static bool rcu_torture_boost_failed(unsigned long gp_state, unsigned long *start)
{
	int cpu;
	static int dbg_done;
	unsigned long end = jiffies;
	bool gp_done;
	unsigned long j;
	static unsigned long last_persist;
	unsigned long lp;
	unsigned long mininterval = test_boost_duration * HZ - HZ / 2;

	if (end - *start > mininterval) {
		// Recheck after checking time to avoid false positives.
		smp_mb(); // Time check before grace-period check.
		if (cur_ops->poll_gp_state(gp_state))
			return false; // passed, though perhaps just barely
		if (cur_ops->check_boost_failed && !cur_ops->check_boost_failed(gp_state, &cpu)) {
			// At most one persisted message per boost test.
			j = jiffies;
			lp = READ_ONCE(last_persist);
			if (time_after(j, lp + mininterval) && cmpxchg(&last_persist, lp, j) == lp)
				pr_info("Boost inversion persisted: No QS from CPU %d\n", cpu);
			return false; // passed on a technicality
		}
		VERBOSE_TOROUT_STRING("rcu_torture_boost boosting failed");
		n_rcu_torture_boost_failure++;
		if (!xchg(&dbg_done, 1) && cur_ops->gp_kthread_dbg) {
			pr_info("Boost inversion thread ->rt_priority %u gp_state %lu jiffies %lu\n",
				current->rt_priority, gp_state, end - *start);
			cur_ops->gp_kthread_dbg();
			// Recheck after print to flag grace period ending during splat.
			gp_done = cur_ops->poll_gp_state(gp_state);
			pr_info("Boost inversion: GP %lu %s.\n", gp_state,
				gp_done ? "ended already" : "still pending");

		}

		return true; // failed
	} else if (cur_ops->check_boost_failed && !cur_ops->check_boost_failed(gp_state, NULL)) {
		*start = jiffies;
	}

	return false; // passed
}

static int rcu_torture_boost(void *arg)
{
	unsigned long endtime;
	unsigned long gp_state;
	unsigned long gp_state_time;
	unsigned long oldstarttime;

	VERBOSE_TOROUT_STRING("rcu_torture_boost started");

	/* Set real-time priority. */
	sched_set_fifo_low(current);

	/* Each pass through the following loop does one boost-test cycle. */
	do {
		bool failed = false; // Test failed already in this test interval
		bool gp_initiated = false;

		if (kthread_should_stop())
			goto checkwait;

		/* Wait for the next test interval. */
		oldstarttime = READ_ONCE(boost_starttime);
		while (time_before(jiffies, oldstarttime)) {
			schedule_timeout_interruptible(oldstarttime - jiffies);
			if (stutter_wait("rcu_torture_boost"))
				sched_set_fifo_low(current);
			if (torture_must_stop())
				goto checkwait;
		}

		// Do one boost-test interval.
		endtime = oldstarttime + test_boost_duration * HZ;
		while (time_before(jiffies, endtime)) {
			// Has current GP gone too long?
			if (gp_initiated && !failed && !cur_ops->poll_gp_state(gp_state))
				failed = rcu_torture_boost_failed(gp_state, &gp_state_time);
			// If we don't have a grace period in flight, start one.
			if (!gp_initiated || cur_ops->poll_gp_state(gp_state)) {
				gp_state = cur_ops->start_gp_poll();
				gp_initiated = true;
				gp_state_time = jiffies;
			}
			if (stutter_wait("rcu_torture_boost")) {
				sched_set_fifo_low(current);
				// If the grace period already ended,
				// we don't know when that happened, so
				// start over.
				if (cur_ops->poll_gp_state(gp_state))
					gp_initiated = false;
			}
			if (torture_must_stop())
				goto checkwait;
		}

		// In case the grace period extended beyond the end of the loop.
		if (gp_initiated && !failed && !cur_ops->poll_gp_state(gp_state))
			rcu_torture_boost_failed(gp_state, &gp_state_time);

		/*
		 * Set the start time of the next test interval.
		 * Yes, this is vulnerable to long delays, but such
		 * delays simply cause a false negative for the next
		 * interval.  Besides, we are running at RT priority,
		 * so delays should be relatively rare.
		 */
		while (oldstarttime == READ_ONCE(boost_starttime) && !kthread_should_stop()) {
			if (mutex_trylock(&boost_mutex)) {
				if (oldstarttime == boost_starttime) {
					WRITE_ONCE(boost_starttime,
						   jiffies + test_boost_interval * HZ);
					n_rcu_torture_boosts++;
				}
				mutex_unlock(&boost_mutex);
				break;
			}
			schedule_timeout_uninterruptible(1);
		}

		/* Go do the stutter. */
checkwait:	if (stutter_wait("rcu_torture_boost"))
			sched_set_fifo_low(current);
	} while (!torture_must_stop());

	/* Clean up and exit. */
	while (!kthread_should_stop()) {
		torture_shutdown_absorb("rcu_torture_boost");
		schedule_timeout_uninterruptible(1);
	}
	torture_kthread_stopping("rcu_torture_boost");
	return 0;
}

/*
 * RCU torture force-quiescent-state kthread.  Repeatedly induces
 * bursts of calls to force_quiescent_state(), increasing the probability
 * of occurrence of some important types of race conditions.
 */
static int
rcu_torture_fqs(void *arg)
{
	unsigned long fqs_resume_time;
	int fqs_burst_remaining;
	int oldnice = task_nice(current);

	VERBOSE_TOROUT_STRING("rcu_torture_fqs task started");
	do {
		fqs_resume_time = jiffies + fqs_stutter * HZ;
		while (time_before(jiffies, fqs_resume_time) &&
		       !kthread_should_stop()) {
			schedule_timeout_interruptible(1);
		}
		fqs_burst_remaining = fqs_duration;
		while (fqs_burst_remaining > 0 &&
		       !kthread_should_stop()) {
			cur_ops->fqs();
			udelay(fqs_holdoff);
			fqs_burst_remaining -= fqs_holdoff;
		}
		if (stutter_wait("rcu_torture_fqs"))
			sched_set_normal(current, oldnice);
	} while (!torture_must_stop());
	torture_kthread_stopping("rcu_torture_fqs");
	return 0;
}

// Used by writers to randomly choose from the available grace-period
// primitives.  The only purpose of the initialization is to size the array.
static int synctype[] = { RTWS_DEF_FREE, RTWS_EXP_SYNC, RTWS_COND_GET, RTWS_POLL_GET, RTWS_SYNC };
static int nsynctypes;

/*
 * Determine which grace-period primitives are available.
 */
static void rcu_torture_write_types(void)
{
	bool gp_cond1 = gp_cond, gp_exp1 = gp_exp, gp_normal1 = gp_normal;
	bool gp_poll1 = gp_poll, gp_sync1 = gp_sync;

	/* Initialize synctype[] array.  If none set, take default. */
	if (!gp_cond1 && !gp_exp1 && !gp_normal1 && !gp_poll1 && !gp_sync1)
		gp_cond1 = gp_exp1 = gp_normal1 = gp_poll1 = gp_sync1 = true;
	if (gp_cond1 && cur_ops->get_gp_state && cur_ops->cond_sync) {
		synctype[nsynctypes++] = RTWS_COND_GET;
		pr_info("%s: Testing conditional GPs.\n", __func__);
	} else if (gp_cond && (!cur_ops->get_gp_state || !cur_ops->cond_sync)) {
		pr_alert("%s: gp_cond without primitives.\n", __func__);
	}
	if (gp_exp1 && cur_ops->exp_sync) {
		synctype[nsynctypes++] = RTWS_EXP_SYNC;
		pr_info("%s: Testing expedited GPs.\n", __func__);
	} else if (gp_exp && !cur_ops->exp_sync) {
		pr_alert("%s: gp_exp without primitives.\n", __func__);
	}
	if (gp_normal1 && cur_ops->deferred_free) {
		synctype[nsynctypes++] = RTWS_DEF_FREE;
		pr_info("%s: Testing asynchronous GPs.\n", __func__);
	} else if (gp_normal && !cur_ops->deferred_free) {
		pr_alert("%s: gp_normal without primitives.\n", __func__);
	}
	if (gp_poll1 && cur_ops->start_gp_poll && cur_ops->poll_gp_state) {
		synctype[nsynctypes++] = RTWS_POLL_GET;
		pr_info("%s: Testing polling GPs.\n", __func__);
	} else if (gp_poll && (!cur_ops->start_gp_poll || !cur_ops->poll_gp_state)) {
		pr_alert("%s: gp_poll without primitives.\n", __func__);
	}
	if (gp_sync1 && cur_ops->sync) {
		synctype[nsynctypes++] = RTWS_SYNC;
		pr_info("%s: Testing normal GPs.\n", __func__);
	} else if (gp_sync && !cur_ops->sync) {
		pr_alert("%s: gp_sync without primitives.\n", __func__);
	}
}

/*
 * RCU torture writer kthread.  Repeatedly substitutes a new structure
 * for that pointed to by rcu_torture_current, freeing the old structure
 * after a series of grace periods (the "pipeline").
 */
static int
rcu_torture_writer(void *arg)
{
	bool boot_ended;
	bool can_expedite = !rcu_gp_is_expedited() && !rcu_gp_is_normal();
	unsigned long cookie;
	int expediting = 0;
	unsigned long gp_snap;
	int i;
	int idx;
	int oldnice = task_nice(current);
	struct rcu_torture *rp;
	struct rcu_torture *old_rp;
	static DEFINE_TORTURE_RANDOM(rand);
	bool stutter_waited;

	VERBOSE_TOROUT_STRING("rcu_torture_writer task started");
	if (!can_expedite)
		pr_alert("%s" TORTURE_FLAG
			 " GP expediting controlled from boot/sysfs for %s.\n",
			 torture_type, cur_ops->name);
	if (WARN_ONCE(nsynctypes == 0,
		      "rcu_torture_writer: No update-side primitives.\n")) {
		/*
		 * No updates primitives, so don't try updating.
		 * The resulting test won't be testing much, hence the
		 * above WARN_ONCE().
		 */
		rcu_torture_writer_state = RTWS_STOPPING;
		torture_kthread_stopping("rcu_torture_writer");
	}

	do {
		rcu_torture_writer_state = RTWS_FIXED_DELAY;
		torture_hrtimeout_us(500, 1000, &rand);
		rp = rcu_torture_alloc();
		if (rp == NULL)
			continue;
		rp->rtort_pipe_count = 0;
		rcu_torture_writer_state = RTWS_DELAY;
		udelay(torture_random(&rand) & 0x3ff);
		rcu_torture_writer_state = RTWS_REPLACE;
		old_rp = rcu_dereference_check(rcu_torture_current,
					       current == writer_task);
		rp->rtort_mbtest = 1;
		rcu_assign_pointer(rcu_torture_current, rp);
		smp_wmb(); /* Mods to old_rp must follow rcu_assign_pointer() */
		if (old_rp) {
			i = old_rp->rtort_pipe_count;
			if (i > RCU_TORTURE_PIPE_LEN)
				i = RCU_TORTURE_PIPE_LEN;
			atomic_inc(&rcu_torture_wcount[i]);
			WRITE_ONCE(old_rp->rtort_pipe_count,
				   old_rp->rtort_pipe_count + 1);
			if (cur_ops->get_gp_state && cur_ops->poll_gp_state) {
				idx = cur_ops->readlock();
				cookie = cur_ops->get_gp_state();
				WARN_ONCE(rcu_torture_writer_state != RTWS_DEF_FREE &&
					  cur_ops->poll_gp_state(cookie),
					  "%s: Cookie check 1 failed %s(%d) %lu->%lu\n",
					  __func__,
					  rcu_torture_writer_state_getname(),
					  rcu_torture_writer_state,
					  cookie, cur_ops->get_gp_state());
				cur_ops->readunlock(idx);
			}
			switch (synctype[torture_random(&rand) % nsynctypes]) {
			case RTWS_DEF_FREE:
				rcu_torture_writer_state = RTWS_DEF_FREE;
				cur_ops->deferred_free(old_rp);
				break;
			case RTWS_EXP_SYNC:
				rcu_torture_writer_state = RTWS_EXP_SYNC;
				cur_ops->exp_sync();
				rcu_torture_pipe_update(old_rp);
				break;
			case RTWS_COND_GET:
				rcu_torture_writer_state = RTWS_COND_GET;
				gp_snap = cur_ops->get_gp_state();
				torture_hrtimeout_jiffies(torture_random(&rand) % 16, &rand);
				rcu_torture_writer_state = RTWS_COND_SYNC;
				cur_ops->cond_sync(gp_snap);
				rcu_torture_pipe_update(old_rp);
				break;
			case RTWS_POLL_GET:
				rcu_torture_writer_state = RTWS_POLL_GET;
				gp_snap = cur_ops->start_gp_poll();
				rcu_torture_writer_state = RTWS_POLL_WAIT;
				while (!cur_ops->poll_gp_state(gp_snap))
					torture_hrtimeout_jiffies(torture_random(&rand) % 16,
								  &rand);
				rcu_torture_pipe_update(old_rp);
				break;
			case RTWS_SYNC:
				rcu_torture_writer_state = RTWS_SYNC;
				cur_ops->sync();
				rcu_torture_pipe_update(old_rp);
				break;
			default:
				WARN_ON_ONCE(1);
				break;
			}
		}
		WRITE_ONCE(rcu_torture_current_version,
			   rcu_torture_current_version + 1);
		/* Cycle through nesting levels of rcu_expedite_gp() calls. */
		if (can_expedite &&
		    !(torture_random(&rand) & 0xff & (!!expediting - 1))) {
			WARN_ON_ONCE(expediting == 0 && rcu_gp_is_expedited());
			if (expediting >= 0)
				rcu_expedite_gp();
			else
				rcu_unexpedite_gp();
			if (++expediting > 3)
				expediting = -expediting;
		} else if (!can_expedite) { /* Disabled during boot, recheck. */
			can_expedite = !rcu_gp_is_expedited() &&
				       !rcu_gp_is_normal();
		}
		rcu_torture_writer_state = RTWS_STUTTER;
		boot_ended = rcu_inkernel_boot_has_ended();
		stutter_waited = stutter_wait("rcu_torture_writer");
		if (stutter_waited &&
		    !atomic_read(&rcu_fwd_cb_nodelay) &&
		    !cur_ops->slow_gps &&
		    !torture_must_stop() &&
		    boot_ended)
			for (i = 0; i < ARRAY_SIZE(rcu_tortures); i++)
				if (list_empty(&rcu_tortures[i].rtort_free) &&
				    rcu_access_pointer(rcu_torture_current) !=
				    &rcu_tortures[i]) {
					rcu_ftrace_dump(DUMP_ALL);
					WARN(1, "%s: rtort_pipe_count: %d\n", __func__, rcu_tortures[i].rtort_pipe_count);
				}
		if (stutter_waited)
			sched_set_normal(current, oldnice);
	} while (!torture_must_stop());
	rcu_torture_current = NULL;  // Let stats task know that we are done.
	/* Reset expediting back to unexpedited. */
	if (expediting > 0)
		expediting = -expediting;
	while (can_expedite && expediting++ < 0)
		rcu_unexpedite_gp();
	WARN_ON_ONCE(can_expedite && rcu_gp_is_expedited());
	if (!can_expedite)
		pr_alert("%s" TORTURE_FLAG
			 " Dynamic grace-period expediting was disabled.\n",
			 torture_type);
	rcu_torture_writer_state = RTWS_STOPPING;
	torture_kthread_stopping("rcu_torture_writer");
	return 0;
}

/*
 * RCU torture fake writer kthread.  Repeatedly calls sync, with a random
 * delay between calls.
 */
static int
rcu_torture_fakewriter(void *arg)
{
	unsigned long gp_snap;
	DEFINE_TORTURE_RANDOM(rand);

	VERBOSE_TOROUT_STRING("rcu_torture_fakewriter task started");
	set_user_nice(current, MAX_NICE);

	do {
		torture_hrtimeout_jiffies(torture_random(&rand) % 10, &rand);
		if (cur_ops->cb_barrier != NULL &&
		    torture_random(&rand) % (nfakewriters * 8) == 0) {
			cur_ops->cb_barrier();
		} else {
			switch (synctype[torture_random(&rand) % nsynctypes]) {
			case RTWS_DEF_FREE:
				break;
			case RTWS_EXP_SYNC:
				cur_ops->exp_sync();
				break;
			case RTWS_COND_GET:
				gp_snap = cur_ops->get_gp_state();
				torture_hrtimeout_jiffies(torture_random(&rand) % 16, &rand);
				cur_ops->cond_sync(gp_snap);
				break;
			case RTWS_POLL_GET:
				gp_snap = cur_ops->start_gp_poll();
				while (!cur_ops->poll_gp_state(gp_snap)) {
					torture_hrtimeout_jiffies(torture_random(&rand) % 16,
								  &rand);
				}
				break;
			case RTWS_SYNC:
				cur_ops->sync();
				break;
			default:
				WARN_ON_ONCE(1);
				break;
			}
		}
		stutter_wait("rcu_torture_fakewriter");
	} while (!torture_must_stop());

	torture_kthread_stopping("rcu_torture_fakewriter");
	return 0;
}

static void rcu_torture_timer_cb(struct rcu_head *rhp)
{
	kfree(rhp);
}

// Set up and carry out testing of RCU's global memory ordering
static void rcu_torture_reader_do_mbchk(long myid, struct rcu_torture *rtp,
					struct torture_random_state *trsp)
{
	unsigned long loops;
	int noc = torture_num_online_cpus();
	int rdrchked;
	int rdrchker;
	struct rcu_torture_reader_check *rtrcp; // Me.
	struct rcu_torture_reader_check *rtrcp_assigner; // Assigned us to do checking.
	struct rcu_torture_reader_check *rtrcp_chked; // Reader being checked.
	struct rcu_torture_reader_check *rtrcp_chker; // Reader doing checking when not me.

	if (myid < 0)
		return; // Don't try this from timer handlers.

	// Increment my counter.
	rtrcp = &rcu_torture_reader_mbchk[myid];
	WRITE_ONCE(rtrcp->rtc_myloops, rtrcp->rtc_myloops + 1);

	// Attempt to assign someone else some checking work.
	rdrchked = torture_random(trsp) % nrealreaders;
	rtrcp_chked = &rcu_torture_reader_mbchk[rdrchked];
	rdrchker = torture_random(trsp) % nrealreaders;
	rtrcp_chker = &rcu_torture_reader_mbchk[rdrchker];
	if (rdrchked != myid && rdrchked != rdrchker && noc >= rdrchked && noc >= rdrchker &&
	    smp_load_acquire(&rtrcp->rtc_chkrdr) < 0 && // Pairs with smp_store_release below.
	    !READ_ONCE(rtp->rtort_chkp) &&
	    !smp_load_acquire(&rtrcp_chker->rtc_assigner)) { // Pairs with smp_store_release below.
		rtrcp->rtc_chkloops = READ_ONCE(rtrcp_chked->rtc_myloops);
		WARN_ON_ONCE(rtrcp->rtc_chkrdr >= 0);
		rtrcp->rtc_chkrdr = rdrchked;
		WARN_ON_ONCE(rtrcp->rtc_ready); // This gets set after the grace period ends.
		if (cmpxchg_relaxed(&rtrcp_chker->rtc_assigner, NULL, rtrcp) ||
		    cmpxchg_relaxed(&rtp->rtort_chkp, NULL, rtrcp))
			(void)cmpxchg_relaxed(&rtrcp_chker->rtc_assigner, rtrcp, NULL); // Back out.
	}

	// If assigned some completed work, do it!
	rtrcp_assigner = READ_ONCE(rtrcp->rtc_assigner);
	if (!rtrcp_assigner || !smp_load_acquire(&rtrcp_assigner->rtc_ready))
		return; // No work or work not yet ready.
	rdrchked = rtrcp_assigner->rtc_chkrdr;
	if (WARN_ON_ONCE(rdrchked < 0))
		return;
	rtrcp_chked = &rcu_torture_reader_mbchk[rdrchked];
	loops = READ_ONCE(rtrcp_chked->rtc_myloops);
	atomic_inc(&n_rcu_torture_mbchk_tries);
	if (ULONG_CMP_LT(loops, rtrcp_assigner->rtc_chkloops))
		atomic_inc(&n_rcu_torture_mbchk_fail);
	rtrcp_assigner->rtc_chkloops = loops + ULONG_MAX / 2;
	rtrcp_assigner->rtc_ready = 0;
	smp_store_release(&rtrcp->rtc_assigner, NULL); // Someone else can assign us work.
	smp_store_release(&rtrcp_assigner->rtc_chkrdr, -1); // Assigner can again assign.
}

/*
 * Do one extension of an RCU read-side critical section using the
 * current reader state in readstate (set to zero for initial entry
 * to extended critical section), set the new state as specified by
 * newstate (set to zero for final exit from extended critical section),
 * and random-number-generator state in trsp.  If this is neither the
 * beginning or end of the critical section and if there was actually a
 * change, do a ->read_delay().
 */
static void rcutorture_one_extend(int *readstate, int newstate,
				  struct torture_random_state *trsp,
				  struct rt_read_seg *rtrsp)
{
	unsigned long flags;
	int idxnew1 = -1;
	int idxnew2 = -1;
	int idxold1 = *readstate;
	int idxold2 = idxold1;
	int statesnew = ~*readstate & newstate;
	int statesold = *readstate & ~newstate;

	WARN_ON_ONCE(idxold2 < 0);
	WARN_ON_ONCE((idxold2 >> RCUTORTURE_RDR_SHIFT_2) > 1);
	rtrsp->rt_readstate = newstate;

	/* First, put new protection in place to avoid critical-section gap. */
	if (statesnew & RCUTORTURE_RDR_BH)
		local_bh_disable();
	if (statesnew & RCUTORTURE_RDR_RBH)
		rcu_read_lock_bh();
	if (statesnew & RCUTORTURE_RDR_IRQ)
		local_irq_disable();
	if (statesnew & RCUTORTURE_RDR_PREEMPT)
		preempt_disable();
	if (statesnew & RCUTORTURE_RDR_SCHED)
		rcu_read_lock_sched();
	if (statesnew & RCUTORTURE_RDR_RCU_1)
		idxnew1 = (cur_ops->readlock() & 0x1) << RCUTORTURE_RDR_SHIFT_1;
	if (statesnew & RCUTORTURE_RDR_RCU_2)
		idxnew2 = (cur_ops->readlock() & 0x1) << RCUTORTURE_RDR_SHIFT_2;

	/*
	 * Next, remove old protection, in decreasing order of strength
	 * to avoid unlock paths that aren't safe in the stronger
	 * context. Namely: BH can not be enabled with disabled interrupts.
	 * Additionally PREEMPT_RT requires that BH is enabled in preemptible
	 * context.
	 */
	if (statesold & RCUTORTURE_RDR_IRQ)
		local_irq_enable();
	if (statesold & RCUTORTURE_RDR_PREEMPT)
		preempt_enable();
	if (statesold & RCUTORTURE_RDR_SCHED)
		rcu_read_unlock_sched();
	if (statesold & RCUTORTURE_RDR_BH)
		local_bh_enable();
	if (statesold & RCUTORTURE_RDR_RBH)
		rcu_read_unlock_bh();
	if (statesold & RCUTORTURE_RDR_RCU_2) {
		cur_ops->readunlock((idxold2 >> RCUTORTURE_RDR_SHIFT_2) & 0x1);
		WARN_ON_ONCE(idxnew2 != -1);
		idxold2 = 0;
	}
	if (statesold & RCUTORTURE_RDR_RCU_1) {
		bool lockit;

		lockit = !cur_ops->no_pi_lock && !statesnew && !(torture_random(trsp) & 0xffff);
		if (lockit)
			raw_spin_lock_irqsave(&current->pi_lock, flags);
		cur_ops->readunlock((idxold1 >> RCUTORTURE_RDR_SHIFT_1) & 0x1);
		WARN_ON_ONCE(idxnew1 != -1);
		idxold1 = 0;
		if (lockit)
			raw_spin_unlock_irqrestore(&current->pi_lock, flags);
	}

	/* Delay if neither beginning nor end and there was a change. */
	if ((statesnew || statesold) && *readstate && newstate)
		cur_ops->read_delay(trsp, rtrsp);

	/* Update the reader state. */
	if (idxnew1 == -1)
		idxnew1 = idxold1 & RCUTORTURE_RDR_MASK_1;
	WARN_ON_ONCE(idxnew1 < 0);
	if (WARN_ON_ONCE((idxnew1 >> RCUTORTURE_RDR_SHIFT_1) > 1))
		pr_info("Unexpected idxnew1 value of %#x\n", idxnew1);
	if (idxnew2 == -1)
		idxnew2 = idxold2 & RCUTORTURE_RDR_MASK_2;
	WARN_ON_ONCE(idxnew2 < 0);
	WARN_ON_ONCE((idxnew2 >> RCUTORTURE_RDR_SHIFT_2) > 1);
	*readstate = idxnew1 | idxnew2 | newstate;
	WARN_ON_ONCE(*readstate < 0);
	if (WARN_ON_ONCE((*readstate >> RCUTORTURE_RDR_SHIFT_2) > 1))
		pr_info("Unexpected idxnew2 value of %#x\n", idxnew2);
}

/* Return the biggest extendables mask given current RCU and boot parameters. */
static int rcutorture_extend_mask_max(void)
{
	int mask;

	WARN_ON_ONCE(extendables & ~RCUTORTURE_MAX_EXTEND);
	mask = extendables & RCUTORTURE_MAX_EXTEND & cur_ops->extendables;
	mask = mask | RCUTORTURE_RDR_RCU_1 | RCUTORTURE_RDR_RCU_2;
	return mask;
}

/* Return a random protection state mask, but with at least one bit set. */
static int
rcutorture_extend_mask(int oldmask, struct torture_random_state *trsp)
{
	int mask = rcutorture_extend_mask_max();
	unsigned long randmask1 = torture_random(trsp) >> 8;
	unsigned long randmask2 = randmask1 >> 3;
	unsigned long preempts = RCUTORTURE_RDR_PREEMPT | RCUTORTURE_RDR_SCHED;
	unsigned long preempts_irq = preempts | RCUTORTURE_RDR_IRQ;
	unsigned long bhs = RCUTORTURE_RDR_BH | RCUTORTURE_RDR_RBH;

	WARN_ON_ONCE(mask >> RCUTORTURE_RDR_SHIFT_1);
	/* Mostly only one bit (need preemption!), sometimes lots of bits. */
	if (!(randmask1 & 0x7))
		mask = mask & randmask2;
	else
		mask = mask & (1 << (randmask2 % RCUTORTURE_RDR_NBITS));

	// Can't have nested RCU reader without outer RCU reader.
	if (!(mask & RCUTORTURE_RDR_RCU_1) && (mask & RCUTORTURE_RDR_RCU_2)) {
		if (oldmask & RCUTORTURE_RDR_RCU_1)
			mask &= ~RCUTORTURE_RDR_RCU_2;
		else
			mask |= RCUTORTURE_RDR_RCU_1;
	}

	/*
	 * Can't enable bh w/irq disabled.
	 */
	if (mask & RCUTORTURE_RDR_IRQ)
		mask |= oldmask & bhs;

	/*
	 * Ideally these sequences would be detected in debug builds
	 * (regardless of RT), but until then don't stop testing
	 * them on non-RT.
	 */
	if (IS_ENABLED(CONFIG_PREEMPT_RT)) {
		/* Can't modify BH in atomic context */
		if (oldmask & preempts_irq)
			mask &= ~bhs;
		if ((oldmask | mask) & preempts_irq)
			mask |= oldmask & bhs;
	}

	return mask ?: RCUTORTURE_RDR_RCU_1;
}

/*
 * Do a randomly selected number of extensions of an existing RCU read-side
 * critical section.
 */
static struct rt_read_seg *
rcutorture_loop_extend(int *readstate, struct torture_random_state *trsp,
		       struct rt_read_seg *rtrsp)
{
	int i;
	int j;
	int mask = rcutorture_extend_mask_max();

	WARN_ON_ONCE(!*readstate); /* -Existing- RCU read-side critsect! */
	if (!((mask - 1) & mask))
		return rtrsp;  /* Current RCU reader not extendable. */
	/* Bias towards larger numbers of loops. */
	i = (torture_random(trsp) >> 3);
	i = ((i | (i >> 3)) & RCUTORTURE_RDR_MAX_LOOPS) + 1;
	for (j = 0; j < i; j++) {
		mask = rcutorture_extend_mask(*readstate, trsp);
		rcutorture_one_extend(readstate, mask, trsp, &rtrsp[j]);
	}
	return &rtrsp[j];
}

/*
 * Do one read-side critical section, returning false if there was
 * no data to read.  Can be invoked both from process context and
 * from a timer handler.
 */
static bool rcu_torture_one_read(struct torture_random_state *trsp, long myid)
{
	unsigned long cookie;
	int i;
	unsigned long started;
	unsigned long completed;
	int newstate;
	struct rcu_torture *p;
	int pipe_count;
	int readstate = 0;
	struct rt_read_seg rtseg[RCUTORTURE_RDR_MAX_SEGS] = { { 0 } };
	struct rt_read_seg *rtrsp = &rtseg[0];
	struct rt_read_seg *rtrsp1;
	unsigned long long ts;

	WARN_ON_ONCE(!rcu_is_watching());
	newstate = rcutorture_extend_mask(readstate, trsp);
	rcutorture_one_extend(&readstate, newstate, trsp, rtrsp++);
	if (cur_ops->get_gp_state && cur_ops->poll_gp_state)
		cookie = cur_ops->get_gp_state();
	started = cur_ops->get_gp_seq();
	ts = rcu_trace_clock_local();
	p = rcu_dereference_check(rcu_torture_current,
				  !cur_ops->readlock_held || cur_ops->readlock_held());
	if (p == NULL) {
		/* Wait for rcu_torture_writer to get underway */
		rcutorture_one_extend(&readstate, 0, trsp, rtrsp);
		return false;
	}
	if (p->rtort_mbtest == 0)
		atomic_inc(&n_rcu_torture_mberror);
	rcu_torture_reader_do_mbchk(myid, p, trsp);
	rtrsp = rcutorture_loop_extend(&readstate, trsp, rtrsp);
	preempt_disable();
	pipe_count = READ_ONCE(p->rtort_pipe_count);
	if (pipe_count > RCU_TORTURE_PIPE_LEN) {
		/* Should not happen, but... */
		pipe_count = RCU_TORTURE_PIPE_LEN;
	}
	completed = cur_ops->get_gp_seq();
	if (pipe_count > 1) {
		do_trace_rcu_torture_read(cur_ops->name, &p->rtort_rcu,
					  ts, started, completed);
		rcu_ftrace_dump(DUMP_ALL);
	}
	__this_cpu_inc(rcu_torture_count[pipe_count]);
	completed = rcutorture_seq_diff(completed, started);
	if (completed > RCU_TORTURE_PIPE_LEN) {
		/* Should not happen, but... */
		completed = RCU_TORTURE_PIPE_LEN;
	}
	__this_cpu_inc(rcu_torture_batch[completed]);
	preempt_enable();
	if (cur_ops->get_gp_state && cur_ops->poll_gp_state)
		WARN_ONCE(cur_ops->poll_gp_state(cookie),
			  "%s: Cookie check 2 failed %s(%d) %lu->%lu\n",
			  __func__,
			  rcu_torture_writer_state_getname(),
			  rcu_torture_writer_state,
			  cookie, cur_ops->get_gp_state());
	rcutorture_one_extend(&readstate, 0, trsp, rtrsp);
	WARN_ON_ONCE(readstate);
	// This next splat is expected behavior if leakpointer, especially
	// for CONFIG_RCU_STRICT_GRACE_PERIOD=y kernels.
	WARN_ON_ONCE(leakpointer && READ_ONCE(p->rtort_pipe_count) > 1);

	/* If error or close call, record the sequence of reader protections. */
	if ((pipe_count > 1 || completed > 1) && !xchg(&err_segs_recorded, 1)) {
		i = 0;
		for (rtrsp1 = &rtseg[0]; rtrsp1 < rtrsp; rtrsp1++)
			err_segs[i++] = *rtrsp1;
		rt_read_nsegs = i;
	}

	return true;
}

static DEFINE_TORTURE_RANDOM_PERCPU(rcu_torture_timer_rand);

/*
 * RCU torture reader from timer handler.  Dereferences rcu_torture_current,
 * incrementing the corresponding element of the pipeline array.  The
 * counter in the element should never be greater than 1, otherwise, the
 * RCU implementation is broken.
 */
static void rcu_torture_timer(struct timer_list *unused)
{
	atomic_long_inc(&n_rcu_torture_timers);
	(void)rcu_torture_one_read(this_cpu_ptr(&rcu_torture_timer_rand), -1);

	/* Test call_rcu() invocation from interrupt handler. */
	if (cur_ops->call) {
		struct rcu_head *rhp = kmalloc(sizeof(*rhp), GFP_NOWAIT);

		if (rhp)
			cur_ops->call(rhp, rcu_torture_timer_cb);
	}
}

/*
 * RCU torture reader kthread.  Repeatedly dereferences rcu_torture_current,
 * incrementing the corresponding element of the pipeline array.  The
 * counter in the element should never be greater than 1, otherwise, the
 * RCU implementation is broken.
 */
static int
rcu_torture_reader(void *arg)
{
	unsigned long lastsleep = jiffies;
	long myid = (long)arg;
	int mynumonline = myid;
	DEFINE_TORTURE_RANDOM(rand);
	struct timer_list t;

	VERBOSE_TOROUT_STRING("rcu_torture_reader task started");
	set_user_nice(current, MAX_NICE);
	if (irqreader && cur_ops->irq_capable)
		timer_setup_on_stack(&t, rcu_torture_timer, 0);
	tick_dep_set_task(current, TICK_DEP_BIT_RCU);
	do {
		if (irqreader && cur_ops->irq_capable) {
			if (!timer_pending(&t))
				mod_timer(&t, jiffies + 1);
		}
		if (!rcu_torture_one_read(&rand, myid) && !torture_must_stop())
			schedule_timeout_interruptible(HZ);
		if (time_after(jiffies, lastsleep) && !torture_must_stop()) {
			torture_hrtimeout_us(500, 1000, &rand);
			lastsleep = jiffies + 10;
		}
		while (torture_num_online_cpus() < mynumonline && !torture_must_stop())
			schedule_timeout_interruptible(HZ / 5);
		stutter_wait("rcu_torture_reader");
	} while (!torture_must_stop());
	if (irqreader && cur_ops->irq_capable) {
		del_timer_sync(&t);
		destroy_timer_on_stack(&t);
	}
	tick_dep_clear_task(current, TICK_DEP_BIT_RCU);
	torture_kthread_stopping("rcu_torture_reader");
	return 0;
}

/*
 * Randomly Toggle CPUs' callback-offload state.  This uses hrtimers to
 * increase race probabilities and fuzzes the interval between toggling.
 */
static int rcu_nocb_toggle(void *arg)
{
	int cpu;
	int maxcpu = -1;
	int oldnice = task_nice(current);
	long r;
	DEFINE_TORTURE_RANDOM(rand);
	ktime_t toggle_delay;
	unsigned long toggle_fuzz;
	ktime_t toggle_interval = ms_to_ktime(nocbs_toggle);

	VERBOSE_TOROUT_STRING("rcu_nocb_toggle task started");
	while (!rcu_inkernel_boot_has_ended())
		schedule_timeout_interruptible(HZ / 10);
	for_each_online_cpu(cpu)
		maxcpu = cpu;
	WARN_ON(maxcpu < 0);
	if (toggle_interval > ULONG_MAX)
		toggle_fuzz = ULONG_MAX >> 3;
	else
		toggle_fuzz = toggle_interval >> 3;
	if (toggle_fuzz <= 0)
		toggle_fuzz = NSEC_PER_USEC;
	do {
		r = torture_random(&rand);
		cpu = (r >> 4) % (maxcpu + 1);
		if (r & 0x1) {
			rcu_nocb_cpu_offload(cpu);
			atomic_long_inc(&n_nocb_offload);
		} else {
			rcu_nocb_cpu_deoffload(cpu);
			atomic_long_inc(&n_nocb_deoffload);
		}
		toggle_delay = torture_random(&rand) % toggle_fuzz + toggle_interval;
		set_current_state(TASK_INTERRUPTIBLE);
		schedule_hrtimeout(&toggle_delay, HRTIMER_MODE_REL);
		if (stutter_wait("rcu_nocb_toggle"))
			sched_set_normal(current, oldnice);
	} while (!torture_must_stop());
	torture_kthread_stopping("rcu_nocb_toggle");
	return 0;
}

/*
 * Print torture statistics.  Caller must ensure that there is only
 * one call to this function at a given time!!!  This is normally
 * accomplished by relying on the module system to only have one copy
 * of the module loaded, and then by giving the rcu_torture_stats
 * kthread full control (or the init/cleanup functions when rcu_torture_stats
 * thread is not running).
 */
static void
rcu_torture_stats_print(void)
{
	int cpu;
	int i;
	long pipesummary[RCU_TORTURE_PIPE_LEN + 1] = { 0 };
	long batchsummary[RCU_TORTURE_PIPE_LEN + 1] = { 0 };
	struct rcu_torture *rtcp;
	static unsigned long rtcv_snap = ULONG_MAX;
	static bool splatted;
	struct task_struct *wtp;

	for_each_possible_cpu(cpu) {
		for (i = 0; i < RCU_TORTURE_PIPE_LEN + 1; i++) {
			pipesummary[i] += READ_ONCE(per_cpu(rcu_torture_count, cpu)[i]);
			batchsummary[i] += READ_ONCE(per_cpu(rcu_torture_batch, cpu)[i]);
		}
	}
	for (i = RCU_TORTURE_PIPE_LEN - 1; i >= 0; i--) {
		if (pipesummary[i] != 0)
			break;
	}

	pr_alert("%s%s ", torture_type, TORTURE_FLAG);
	rtcp = rcu_access_pointer(rcu_torture_current);
	pr_cont("rtc: %p %s: %lu tfle: %d rta: %d rtaf: %d rtf: %d ",
		rtcp,
		rtcp && !rcu_stall_is_suppressed_at_boot() ? "ver" : "VER",
		rcu_torture_current_version,
		list_empty(&rcu_torture_freelist),
		atomic_read(&n_rcu_torture_alloc),
		atomic_read(&n_rcu_torture_alloc_fail),
		atomic_read(&n_rcu_torture_free));
	pr_cont("rtmbe: %d rtmbkf: %d/%d rtbe: %ld rtbke: %ld rtbre: %ld ",
		atomic_read(&n_rcu_torture_mberror),
		atomic_read(&n_rcu_torture_mbchk_fail), atomic_read(&n_rcu_torture_mbchk_tries),
		n_rcu_torture_barrier_error,
		n_rcu_torture_boost_ktrerror,
		n_rcu_torture_boost_rterror);
	pr_cont("rtbf: %ld rtb: %ld nt: %ld ",
		n_rcu_torture_boost_failure,
		n_rcu_torture_boosts,
		atomic_long_read(&n_rcu_torture_timers));
	torture_onoff_stats();
	pr_cont("barrier: %ld/%ld:%ld ",
		data_race(n_barrier_successes),
		data_race(n_barrier_attempts),
		data_race(n_rcu_torture_barrier_error));
	pr_cont("read-exits: %ld ", data_race(n_read_exits)); // Statistic.
	pr_cont("nocb-toggles: %ld:%ld\n",
		atomic_long_read(&n_nocb_offload), atomic_long_read(&n_nocb_deoffload));

	pr_alert("%s%s ", torture_type, TORTURE_FLAG);
	if (atomic_read(&n_rcu_torture_mberror) ||
	    atomic_read(&n_rcu_torture_mbchk_fail) ||
	    n_rcu_torture_barrier_error || n_rcu_torture_boost_ktrerror ||
	    n_rcu_torture_boost_rterror || n_rcu_torture_boost_failure ||
	    i > 1) {
		pr_cont("%s", "!!! ");
		atomic_inc(&n_rcu_torture_error);
		WARN_ON_ONCE(atomic_read(&n_rcu_torture_mberror));
		WARN_ON_ONCE(atomic_read(&n_rcu_torture_mbchk_fail));
		WARN_ON_ONCE(n_rcu_torture_barrier_error);  // rcu_barrier()
		WARN_ON_ONCE(n_rcu_torture_boost_ktrerror); // no boost kthread
		WARN_ON_ONCE(n_rcu_torture_boost_rterror); // can't set RT prio
		WARN_ON_ONCE(n_rcu_torture_boost_failure); // boost failed (TIMER_SOFTIRQ RT prio?)
		WARN_ON_ONCE(i > 1); // Too-short grace period
	}
	pr_cont("Reader Pipe: ");
	for (i = 0; i < RCU_TORTURE_PIPE_LEN + 1; i++)
		pr_cont(" %ld", pipesummary[i]);
	pr_cont("\n");

	pr_alert("%s%s ", torture_type, TORTURE_FLAG);
	pr_cont("Reader Batch: ");
	for (i = 0; i < RCU_TORTURE_PIPE_LEN + 1; i++)
		pr_cont(" %ld", batchsummary[i]);
	pr_cont("\n");

	pr_alert("%s%s ", torture_type, TORTURE_FLAG);
	pr_cont("Free-Block Circulation: ");
	for (i = 0; i < RCU_TORTURE_PIPE_LEN + 1; i++) {
		pr_cont(" %d", atomic_read(&rcu_torture_wcount[i]));
	}
	pr_cont("\n");

	if (cur_ops->stats)
		cur_ops->stats();
	if (rtcv_snap == rcu_torture_current_version &&
	    rcu_access_pointer(rcu_torture_current) &&
	    !rcu_stall_is_suppressed()) {
		int __maybe_unused flags = 0;
		unsigned long __maybe_unused gp_seq = 0;

		rcutorture_get_gp_data(cur_ops->ttype,
				       &flags, &gp_seq);
		srcutorture_get_gp_data(cur_ops->ttype, srcu_ctlp,
					&flags, &gp_seq);
		wtp = READ_ONCE(writer_task);
		pr_alert("??? Writer stall state %s(%d) g%lu f%#x ->state %#x cpu %d\n",
			 rcu_torture_writer_state_getname(),
			 rcu_torture_writer_state, gp_seq, flags,
			 wtp == NULL ? ~0U : wtp->__state,
			 wtp == NULL ? -1 : (int)task_cpu(wtp));
		if (!splatted && wtp) {
			sched_show_task(wtp);
			splatted = true;
		}
		if (cur_ops->gp_kthread_dbg)
			cur_ops->gp_kthread_dbg();
		rcu_ftrace_dump(DUMP_ALL);
	}
	rtcv_snap = rcu_torture_current_version;
}

/*
 * Periodically prints torture statistics, if periodic statistics printing
 * was specified via the stat_interval module parameter.
 */
static int
rcu_torture_stats(void *arg)
{
	VERBOSE_TOROUT_STRING("rcu_torture_stats task started");
	do {
		schedule_timeout_interruptible(stat_interval * HZ);
		rcu_torture_stats_print();
		torture_shutdown_absorb("rcu_torture_stats");
	} while (!torture_must_stop());
	torture_kthread_stopping("rcu_torture_stats");
	return 0;
}

/* Test mem_dump_obj() and friends.  */
static void rcu_torture_mem_dump_obj(void)
{
	struct rcu_head *rhp;
	struct kmem_cache *kcp;
	static int z;

	kcp = kmem_cache_create("rcuscale", 136, 8, SLAB_STORE_USER, NULL);
	rhp = kmem_cache_alloc(kcp, GFP_KERNEL);
	pr_alert("mem_dump_obj() slab test: rcu_torture_stats = %px, &rhp = %px, rhp = %px, &z = %px\n", stats_task, &rhp, rhp, &z);
	pr_alert("mem_dump_obj(ZERO_SIZE_PTR):");
	mem_dump_obj(ZERO_SIZE_PTR);
	pr_alert("mem_dump_obj(NULL):");
	mem_dump_obj(NULL);
	pr_alert("mem_dump_obj(%px):", &rhp);
	mem_dump_obj(&rhp);
	pr_alert("mem_dump_obj(%px):", rhp);
	mem_dump_obj(rhp);
	pr_alert("mem_dump_obj(%px):", &rhp->func);
	mem_dump_obj(&rhp->func);
	pr_alert("mem_dump_obj(%px):", &z);
	mem_dump_obj(&z);
	kmem_cache_free(kcp, rhp);
	kmem_cache_destroy(kcp);
	rhp = kmalloc(sizeof(*rhp), GFP_KERNEL);
	pr_alert("mem_dump_obj() kmalloc test: rcu_torture_stats = %px, &rhp = %px, rhp = %px\n", stats_task, &rhp, rhp);
	pr_alert("mem_dump_obj(kmalloc %px):", rhp);
	mem_dump_obj(rhp);
	pr_alert("mem_dump_obj(kmalloc %px):", &rhp->func);
	mem_dump_obj(&rhp->func);
	kfree(rhp);
	rhp = vmalloc(4096);
	pr_alert("mem_dump_obj() vmalloc test: rcu_torture_stats = %px, &rhp = %px, rhp = %px\n", stats_task, &rhp, rhp);
	pr_alert("mem_dump_obj(vmalloc %px):", rhp);
	mem_dump_obj(rhp);
	pr_alert("mem_dump_obj(vmalloc %px):", &rhp->func);
	mem_dump_obj(&rhp->func);
	vfree(rhp);
}

static void
rcu_torture_print_module_parms(struct rcu_torture_ops *cur_ops, const char *tag)
{
	pr_alert("%s" TORTURE_FLAG
		 "--- %s: nreaders=%d nfakewriters=%d "
		 "stat_interval=%d verbose=%d test_no_idle_hz=%d "
		 "shuffle_interval=%d stutter=%d irqreader=%d "
		 "fqs_duration=%d fqs_holdoff=%d fqs_stutter=%d "
		 "test_boost=%d/%d test_boost_interval=%d "
		 "test_boost_duration=%d shutdown_secs=%d "
		 "stall_cpu=%d stall_cpu_holdoff=%d stall_cpu_irqsoff=%d "
		 "stall_cpu_block=%d "
		 "n_barrier_cbs=%d "
		 "onoff_interval=%d onoff_holdoff=%d "
		 "read_exit_delay=%d read_exit_burst=%d "
		 "nocbs_nthreads=%d nocbs_toggle=%d\n",
		 torture_type, tag, nrealreaders, nfakewriters,
		 stat_interval, verbose, test_no_idle_hz, shuffle_interval,
		 stutter, irqreader, fqs_duration, fqs_holdoff, fqs_stutter,
		 test_boost, cur_ops->can_boost,
		 test_boost_interval, test_boost_duration, shutdown_secs,
		 stall_cpu, stall_cpu_holdoff, stall_cpu_irqsoff,
		 stall_cpu_block,
		 n_barrier_cbs,
		 onoff_interval, onoff_holdoff,
		 read_exit_delay, read_exit_burst,
		 nocbs_nthreads, nocbs_toggle);
}

static int rcutorture_booster_cleanup(unsigned int cpu)
{
	struct task_struct *t;

	if (boost_tasks[cpu] == NULL)
		return 0;
	mutex_lock(&boost_mutex);
	t = boost_tasks[cpu];
	boost_tasks[cpu] = NULL;
	rcu_torture_enable_rt_throttle();
	mutex_unlock(&boost_mutex);

	/* This must be outside of the mutex, otherwise deadlock! */
	torture_stop_kthread(rcu_torture_boost, t);
	return 0;
}

static int rcutorture_booster_init(unsigned int cpu)
{
	int retval;

	if (boost_tasks[cpu] != NULL)
		return 0;  /* Already created, nothing more to do. */

	/* Don't allow time recalculation while creating a new task. */
	mutex_lock(&boost_mutex);
	rcu_torture_disable_rt_throttle();
	VERBOSE_TOROUT_STRING("Creating rcu_torture_boost task");
	boost_tasks[cpu] = kthread_run_on_cpu(rcu_torture_boost, NULL,
					      cpu, "rcu_torture_boost_%u");
	if (IS_ERR(boost_tasks[cpu])) {
		retval = PTR_ERR(boost_tasks[cpu]);
		VERBOSE_TOROUT_STRING("rcu_torture_boost task create failed");
		n_rcu_torture_boost_ktrerror++;
		boost_tasks[cpu] = NULL;
		mutex_unlock(&boost_mutex);
		return retval;
	}
	mutex_unlock(&boost_mutex);
	return 0;
}

/*
 * CPU-stall kthread.  It waits as specified by stall_cpu_holdoff, then
 * induces a CPU stall for the time specified by stall_cpu.
 */
static int rcu_torture_stall(void *args)
{
	int idx;
	unsigned long stop_at;

	VERBOSE_TOROUT_STRING("rcu_torture_stall task started");
	if (stall_cpu_holdoff > 0) {
		VERBOSE_TOROUT_STRING("rcu_torture_stall begin holdoff");
		schedule_timeout_interruptible(stall_cpu_holdoff * HZ);
		VERBOSE_TOROUT_STRING("rcu_torture_stall end holdoff");
	}
	if (!kthread_should_stop() && stall_gp_kthread > 0) {
		VERBOSE_TOROUT_STRING("rcu_torture_stall begin GP stall");
		rcu_gp_set_torture_wait(stall_gp_kthread * HZ);
		for (idx = 0; idx < stall_gp_kthread + 2; idx++) {
			if (kthread_should_stop())
				break;
			schedule_timeout_uninterruptible(HZ);
		}
	}
	if (!kthread_should_stop() && stall_cpu > 0) {
		VERBOSE_TOROUT_STRING("rcu_torture_stall begin CPU stall");
		stop_at = ktime_get_seconds() + stall_cpu;
		/* RCU CPU stall is expected behavior in following code. */
		idx = cur_ops->readlock();
		if (stall_cpu_irqsoff)
			local_irq_disable();
		else if (!stall_cpu_block)
			preempt_disable();
		pr_alert("%s start on CPU %d.\n",
			  __func__, raw_smp_processor_id());
		while (ULONG_CMP_LT((unsigned long)ktime_get_seconds(),
				    stop_at))
			if (stall_cpu_block) {
#ifdef CONFIG_PREEMPTION
				preempt_schedule();
#else
				schedule_timeout_uninterruptible(HZ);
#endif
			} else if (stall_no_softlockup) {
				touch_softlockup_watchdog();
			}
		if (stall_cpu_irqsoff)
			local_irq_enable();
		else if (!stall_cpu_block)
			preempt_enable();
		cur_ops->readunlock(idx);
	}
	pr_alert("%s end.\n", __func__);
	torture_shutdown_absorb("rcu_torture_stall");
	while (!kthread_should_stop())
		schedule_timeout_interruptible(10 * HZ);
	return 0;
}

/* Spawn CPU-stall kthread, if stall_cpu specified. */
static int __init rcu_torture_stall_init(void)
{
	if (stall_cpu <= 0 && stall_gp_kthread <= 0)
		return 0;
	return torture_create_kthread(rcu_torture_stall, NULL, stall_task);
}

/* State structure for forward-progress self-propagating RCU callback. */
struct fwd_cb_state {
	struct rcu_head rh;
	int stop;
};

/*
 * Forward-progress self-propagating RCU callback function.  Because
 * callbacks run from softirq, this function is an implicit RCU read-side
 * critical section.
 */
static void rcu_torture_fwd_prog_cb(struct rcu_head *rhp)
{
	struct fwd_cb_state *fcsp = container_of(rhp, struct fwd_cb_state, rh);

	if (READ_ONCE(fcsp->stop)) {
		WRITE_ONCE(fcsp->stop, 2);
		return;
	}
	cur_ops->call(&fcsp->rh, rcu_torture_fwd_prog_cb);
}

/* State for continuous-flood RCU callbacks. */
struct rcu_fwd_cb {
	struct rcu_head rh;
	struct rcu_fwd_cb *rfc_next;
	struct rcu_fwd *rfc_rfp;
	int rfc_gps;
};

#define MAX_FWD_CB_JIFFIES	(8 * HZ) /* Maximum CB test duration. */
#define MIN_FWD_CB_LAUNDERS	3	/* This many CB invocations to count. */
#define MIN_FWD_CBS_LAUNDERED	100	/* Number of counted CBs. */
#define FWD_CBS_HIST_DIV	10	/* Histogram buckets/second. */
#define N_LAUNDERS_HIST (2 * MAX_FWD_CB_JIFFIES / (HZ / FWD_CBS_HIST_DIV))

struct rcu_launder_hist {
	long n_launders;
	unsigned long launder_gp_seq;
};

struct rcu_fwd {
	spinlock_t rcu_fwd_lock;
	struct rcu_fwd_cb *rcu_fwd_cb_head;
	struct rcu_fwd_cb **rcu_fwd_cb_tail;
	long n_launders_cb;
	unsigned long rcu_fwd_startat;
	struct rcu_launder_hist n_launders_hist[N_LAUNDERS_HIST];
	unsigned long rcu_launder_gp_seq_start;
	int rcu_fwd_id;
};

static DEFINE_MUTEX(rcu_fwd_mutex);
static struct rcu_fwd *rcu_fwds;
static unsigned long rcu_fwd_seq;
static atomic_long_t rcu_fwd_max_cbs;
static bool rcu_fwd_emergency_stop;

static void rcu_torture_fwd_cb_hist(struct rcu_fwd *rfp)
{
	unsigned long gps;
	unsigned long gps_old;
	int i;
	int j;

	for (i = ARRAY_SIZE(rfp->n_launders_hist) - 1; i > 0; i--)
		if (rfp->n_launders_hist[i].n_launders > 0)
			break;
	pr_alert("%s: Callback-invocation histogram %d (duration %lu jiffies):",
		 __func__, rfp->rcu_fwd_id, jiffies - rfp->rcu_fwd_startat);
	gps_old = rfp->rcu_launder_gp_seq_start;
	for (j = 0; j <= i; j++) {
		gps = rfp->n_launders_hist[j].launder_gp_seq;
		pr_cont(" %ds/%d: %ld:%ld",
			j + 1, FWD_CBS_HIST_DIV,
			rfp->n_launders_hist[j].n_launders,
			rcutorture_seq_diff(gps, gps_old));
		gps_old = gps;
	}
	pr_cont("\n");
}

/* Callback function for continuous-flood RCU callbacks. */
static void rcu_torture_fwd_cb_cr(struct rcu_head *rhp)
{
	unsigned long flags;
	int i;
	struct rcu_fwd_cb *rfcp = container_of(rhp, struct rcu_fwd_cb, rh);
	struct rcu_fwd_cb **rfcpp;
	struct rcu_fwd *rfp = rfcp->rfc_rfp;

	rfcp->rfc_next = NULL;
	rfcp->rfc_gps++;
	spin_lock_irqsave(&rfp->rcu_fwd_lock, flags);
	rfcpp = rfp->rcu_fwd_cb_tail;
	rfp->rcu_fwd_cb_tail = &rfcp->rfc_next;
	WRITE_ONCE(*rfcpp, rfcp);
	WRITE_ONCE(rfp->n_launders_cb, rfp->n_launders_cb + 1);
	i = ((jiffies - rfp->rcu_fwd_startat) / (HZ / FWD_CBS_HIST_DIV));
	if (i >= ARRAY_SIZE(rfp->n_launders_hist))
		i = ARRAY_SIZE(rfp->n_launders_hist) - 1;
	rfp->n_launders_hist[i].n_launders++;
	rfp->n_launders_hist[i].launder_gp_seq = cur_ops->get_gp_seq();
	spin_unlock_irqrestore(&rfp->rcu_fwd_lock, flags);
}

// Give the scheduler a chance, even on nohz_full CPUs.
static void rcu_torture_fwd_prog_cond_resched(unsigned long iter)
{
	if (IS_ENABLED(CONFIG_PREEMPTION) && IS_ENABLED(CONFIG_NO_HZ_FULL)) {
		// Real call_rcu() floods hit userspace, so emulate that.
		if (need_resched() || (iter & 0xfff))
			schedule();
		return;
	}
	// No userspace emulation: CB invocation throttles call_rcu()
	cond_resched();
}

/*
 * Free all callbacks on the rcu_fwd_cb_head list, either because the
 * test is over or because we hit an OOM event.
 */
static unsigned long rcu_torture_fwd_prog_cbfree(struct rcu_fwd *rfp)
{
	unsigned long flags;
	unsigned long freed = 0;
	struct rcu_fwd_cb *rfcp;

	for (;;) {
		spin_lock_irqsave(&rfp->rcu_fwd_lock, flags);
		rfcp = rfp->rcu_fwd_cb_head;
		if (!rfcp) {
			spin_unlock_irqrestore(&rfp->rcu_fwd_lock, flags);
			break;
		}
		rfp->rcu_fwd_cb_head = rfcp->rfc_next;
		if (!rfp->rcu_fwd_cb_head)
			rfp->rcu_fwd_cb_tail = &rfp->rcu_fwd_cb_head;
		spin_unlock_irqrestore(&rfp->rcu_fwd_lock, flags);
		kfree(rfcp);
		freed++;
		rcu_torture_fwd_prog_cond_resched(freed);
		if (tick_nohz_full_enabled()) {
			local_irq_save(flags);
			rcu_momentary_dyntick_idle();
			local_irq_restore(flags);
		}
	}
	return freed;
}

/* Carry out need_resched()/cond_resched() forward-progress testing. */
static void rcu_torture_fwd_prog_nr(struct rcu_fwd *rfp,
				    int *tested, int *tested_tries)
{
	unsigned long cver;
	unsigned long dur;
	struct fwd_cb_state fcs;
	unsigned long gps;
	int idx;
	int sd;
	int sd4;
	bool selfpropcb = false;
	unsigned long stopat;
	static DEFINE_TORTURE_RANDOM(trs);

	pr_alert("%s: Starting forward-progress test %d\n", __func__, rfp->rcu_fwd_id);
	if (!cur_ops->sync)
		return; // Cannot do need_resched() forward progress testing without ->sync.
	if (cur_ops->call && cur_ops->cb_barrier) {
		init_rcu_head_on_stack(&fcs.rh);
		selfpropcb = true;
	}

	/* Tight loop containing cond_resched(). */
	atomic_inc(&rcu_fwd_cb_nodelay);
	cur_ops->sync(); /* Later readers see above write. */
	if  (selfpropcb) {
		WRITE_ONCE(fcs.stop, 0);
		cur_ops->call(&fcs.rh, rcu_torture_fwd_prog_cb);
	}
	cver = READ_ONCE(rcu_torture_current_version);
	gps = cur_ops->get_gp_seq();
	sd = cur_ops->stall_dur() + 1;
	sd4 = (sd + fwd_progress_div - 1) / fwd_progress_div;
	dur = sd4 + torture_random(&trs) % (sd - sd4);
	WRITE_ONCE(rfp->rcu_fwd_startat, jiffies);
	stopat = rfp->rcu_fwd_startat + dur;
	while (time_before(jiffies, stopat) &&
	       !shutdown_time_arrived() &&
	       !READ_ONCE(rcu_fwd_emergency_stop) && !torture_must_stop()) {
		idx = cur_ops->readlock();
		udelay(10);
		cur_ops->readunlock(idx);
		if (!fwd_progress_need_resched || need_resched())
			cond_resched();
	}
	(*tested_tries)++;
	if (!time_before(jiffies, stopat) &&
	    !shutdown_time_arrived() &&
	    !READ_ONCE(rcu_fwd_emergency_stop) && !torture_must_stop()) {
		(*tested)++;
		cver = READ_ONCE(rcu_torture_current_version) - cver;
		gps = rcutorture_seq_diff(cur_ops->get_gp_seq(), gps);
		WARN_ON(!cver && gps < 2);
		pr_alert("%s: %d Duration %ld cver %ld gps %ld\n", __func__,
			 rfp->rcu_fwd_id, dur, cver, gps);
	}
	if (selfpropcb) {
		WRITE_ONCE(fcs.stop, 1);
		cur_ops->sync(); /* Wait for running CB to complete. */
		pr_alert("%s: Waiting for CBs: %pS() %d\n", __func__, cur_ops->cb_barrier, rfp->rcu_fwd_id);
		cur_ops->cb_barrier(); /* Wait for queued callbacks. */
	}

	if (selfpropcb) {
		WARN_ON(READ_ONCE(fcs.stop) != 2);
		destroy_rcu_head_on_stack(&fcs.rh);
	}
	schedule_timeout_uninterruptible(HZ / 10); /* Let kthreads recover. */
	atomic_dec(&rcu_fwd_cb_nodelay);
}

/* Carry out call_rcu() forward-progress testing. */
static void rcu_torture_fwd_prog_cr(struct rcu_fwd *rfp)
{
	unsigned long cver;
	unsigned long flags;
	unsigned long gps;
	int i;
	long n_launders;
	long n_launders_cb_snap;
	long n_launders_sa;
	long n_max_cbs;
	long n_max_gps;
	struct rcu_fwd_cb *rfcp;
	struct rcu_fwd_cb *rfcpn;
	unsigned long stopat;
	unsigned long stoppedat;

	pr_alert("%s: Starting forward-progress test %d\n", __func__, rfp->rcu_fwd_id);
	if (READ_ONCE(rcu_fwd_emergency_stop))
		return; /* Get out of the way quickly, no GP wait! */
	if (!cur_ops->call)
		return; /* Can't do call_rcu() fwd prog without ->call. */

	/* Loop continuously posting RCU callbacks. */
	atomic_inc(&rcu_fwd_cb_nodelay);
	cur_ops->sync(); /* Later readers see above write. */
	WRITE_ONCE(rfp->rcu_fwd_startat, jiffies);
	stopat = rfp->rcu_fwd_startat + MAX_FWD_CB_JIFFIES;
	n_launders = 0;
	rfp->n_launders_cb = 0; // Hoist initialization for multi-kthread
	n_launders_sa = 0;
	n_max_cbs = 0;
	n_max_gps = 0;
	for (i = 0; i < ARRAY_SIZE(rfp->n_launders_hist); i++)
		rfp->n_launders_hist[i].n_launders = 0;
	cver = READ_ONCE(rcu_torture_current_version);
	gps = cur_ops->get_gp_seq();
	rfp->rcu_launder_gp_seq_start = gps;
	tick_dep_set_task(current, TICK_DEP_BIT_RCU);
	while (time_before(jiffies, stopat) &&
	       !shutdown_time_arrived() &&
	       !READ_ONCE(rcu_fwd_emergency_stop) && !torture_must_stop()) {
		rfcp = READ_ONCE(rfp->rcu_fwd_cb_head);
		rfcpn = NULL;
		if (rfcp)
			rfcpn = READ_ONCE(rfcp->rfc_next);
		if (rfcpn) {
			if (rfcp->rfc_gps >= MIN_FWD_CB_LAUNDERS &&
			    ++n_max_gps >= MIN_FWD_CBS_LAUNDERED)
				break;
			rfp->rcu_fwd_cb_head = rfcpn;
			n_launders++;
			n_launders_sa++;
		} else if (!cur_ops->cbflood_max || cur_ops->cbflood_max > n_max_cbs) {
			rfcp = kmalloc(sizeof(*rfcp), GFP_KERNEL);
			if (WARN_ON_ONCE(!rfcp)) {
				schedule_timeout_interruptible(1);
				continue;
			}
			n_max_cbs++;
			n_launders_sa = 0;
			rfcp->rfc_gps = 0;
			rfcp->rfc_rfp = rfp;
		} else {
			rfcp = NULL;
		}
		if (rfcp)
			cur_ops->call(&rfcp->rh, rcu_torture_fwd_cb_cr);
		rcu_torture_fwd_prog_cond_resched(n_launders + n_max_cbs);
		if (tick_nohz_full_enabled()) {
			local_irq_save(flags);
			rcu_momentary_dyntick_idle();
			local_irq_restore(flags);
		}
	}
	stoppedat = jiffies;
	n_launders_cb_snap = READ_ONCE(rfp->n_launders_cb);
	cver = READ_ONCE(rcu_torture_current_version) - cver;
	gps = rcutorture_seq_diff(cur_ops->get_gp_seq(), gps);
	pr_alert("%s: Waiting for CBs: %pS() %d\n", __func__, cur_ops->cb_barrier, rfp->rcu_fwd_id);
	cur_ops->cb_barrier(); /* Wait for callbacks to be invoked. */
	(void)rcu_torture_fwd_prog_cbfree(rfp);

	if (!torture_must_stop() && !READ_ONCE(rcu_fwd_emergency_stop) &&
	    !shutdown_time_arrived()) {
		WARN_ON(n_max_gps < MIN_FWD_CBS_LAUNDERED);
		pr_alert("%s Duration %lu barrier: %lu pending %ld n_launders: %ld n_launders_sa: %ld n_max_gps: %ld n_max_cbs: %ld cver %ld gps %ld\n",
			 __func__,
			 stoppedat - rfp->rcu_fwd_startat, jiffies - stoppedat,
			 n_launders + n_max_cbs - n_launders_cb_snap,
			 n_launders, n_launders_sa,
			 n_max_gps, n_max_cbs, cver, gps);
		atomic_long_add(n_max_cbs, &rcu_fwd_max_cbs);
		mutex_lock(&rcu_fwd_mutex); // Serialize histograms.
		rcu_torture_fwd_cb_hist(rfp);
		mutex_unlock(&rcu_fwd_mutex);
	}
	schedule_timeout_uninterruptible(HZ); /* Let CBs drain. */
	tick_dep_clear_task(current, TICK_DEP_BIT_RCU);
	atomic_dec(&rcu_fwd_cb_nodelay);
}


/*
 * OOM notifier, but this only prints diagnostic information for the
 * current forward-progress test.
 */
static int rcutorture_oom_notify(struct notifier_block *self,
				 unsigned long notused, void *nfreed)
{
	int i;
	long ncbs;
	struct rcu_fwd *rfp;

	mutex_lock(&rcu_fwd_mutex);
	rfp = rcu_fwds;
	if (!rfp) {
		mutex_unlock(&rcu_fwd_mutex);
		return NOTIFY_OK;
	}
	WARN(1, "%s invoked upon OOM during forward-progress testing.\n",
	     __func__);
	for (i = 0; i < fwd_progress; i++) {
		rcu_torture_fwd_cb_hist(&rfp[i]);
		rcu_fwd_progress_check(1 + (jiffies - READ_ONCE(rfp[i].rcu_fwd_startat)) / 2);
	}
	WRITE_ONCE(rcu_fwd_emergency_stop, true);
	smp_mb(); /* Emergency stop before free and wait to avoid hangs. */
	ncbs = 0;
	for (i = 0; i < fwd_progress; i++)
		ncbs += rcu_torture_fwd_prog_cbfree(&rfp[i]);
	pr_info("%s: Freed %lu RCU callbacks.\n", __func__, ncbs);
	rcu_barrier();
	ncbs = 0;
	for (i = 0; i < fwd_progress; i++)
		ncbs += rcu_torture_fwd_prog_cbfree(&rfp[i]);
	pr_info("%s: Freed %lu RCU callbacks.\n", __func__, ncbs);
	rcu_barrier();
	ncbs = 0;
	for (i = 0; i < fwd_progress; i++)
		ncbs += rcu_torture_fwd_prog_cbfree(&rfp[i]);
	pr_info("%s: Freed %lu RCU callbacks.\n", __func__, ncbs);
	smp_mb(); /* Frees before return to avoid redoing OOM. */
	(*(unsigned long *)nfreed)++; /* Forward progress CBs freed! */
	pr_info("%s returning after OOM processing.\n", __func__);
	mutex_unlock(&rcu_fwd_mutex);
	return NOTIFY_OK;
}

static struct notifier_block rcutorture_oom_nb = {
	.notifier_call = rcutorture_oom_notify
};

/* Carry out grace-period forward-progress testing. */
static int rcu_torture_fwd_prog(void *args)
{
	bool firsttime = true;
	long max_cbs;
	int oldnice = task_nice(current);
	unsigned long oldseq = READ_ONCE(rcu_fwd_seq);
	struct rcu_fwd *rfp = args;
	int tested = 0;
	int tested_tries = 0;

	VERBOSE_TOROUT_STRING("rcu_torture_fwd_progress task started");
	rcu_bind_current_to_nocb();
	if (!IS_ENABLED(CONFIG_SMP) || !IS_ENABLED(CONFIG_RCU_BOOST))
		set_user_nice(current, MAX_NICE);
	do {
		if (!rfp->rcu_fwd_id) {
			schedule_timeout_interruptible(fwd_progress_holdoff * HZ);
			WRITE_ONCE(rcu_fwd_emergency_stop, false);
			if (!firsttime) {
				max_cbs = atomic_long_xchg(&rcu_fwd_max_cbs, 0);
				pr_alert("%s n_max_cbs: %ld\n", __func__, max_cbs);
			}
			firsttime = false;
			WRITE_ONCE(rcu_fwd_seq, rcu_fwd_seq + 1);
		} else {
			while (READ_ONCE(rcu_fwd_seq) == oldseq && !torture_must_stop())
				schedule_timeout_interruptible(1);
			oldseq = READ_ONCE(rcu_fwd_seq);
		}
		pr_alert("%s: Starting forward-progress test %d\n", __func__, rfp->rcu_fwd_id);
		if (rcu_inkernel_boot_has_ended() && torture_num_online_cpus() > rfp->rcu_fwd_id)
			rcu_torture_fwd_prog_cr(rfp);
		if ((cur_ops->stall_dur && cur_ops->stall_dur() > 0) &&
		    (!IS_ENABLED(CONFIG_TINY_RCU) ||
		     (rcu_inkernel_boot_has_ended() &&
		      torture_num_online_cpus() > rfp->rcu_fwd_id)))
			rcu_torture_fwd_prog_nr(rfp, &tested, &tested_tries);

		/* Avoid slow periods, better to test when busy. */
		if (stutter_wait("rcu_torture_fwd_prog"))
			sched_set_normal(current, oldnice);
	} while (!torture_must_stop());
	/* Short runs might not contain a valid forward-progress attempt. */
	if (!rfp->rcu_fwd_id) {
		WARN_ON(!tested && tested_tries >= 5);
		pr_alert("%s: tested %d tested_tries %d\n", __func__, tested, tested_tries);
	}
	torture_kthread_stopping("rcu_torture_fwd_prog");
	return 0;
}

/* If forward-progress checking is requested and feasible, spawn the thread. */
static int __init rcu_torture_fwd_prog_init(void)
{
	int i;
	int ret = 0;
	struct rcu_fwd *rfp;

	if (!fwd_progress)
		return 0; /* Not requested, so don't do it. */
	if (fwd_progress >= nr_cpu_ids) {
		VERBOSE_TOROUT_STRING("rcu_torture_fwd_prog_init: Limiting fwd_progress to # CPUs.\n");
		fwd_progress = nr_cpu_ids;
	} else if (fwd_progress < 0) {
		fwd_progress = nr_cpu_ids;
	}
	if ((!cur_ops->sync && !cur_ops->call) ||
	    (!cur_ops->cbflood_max && (!cur_ops->stall_dur || cur_ops->stall_dur() <= 0)) ||
	    cur_ops == &rcu_busted_ops) {
		VERBOSE_TOROUT_STRING("rcu_torture_fwd_prog_init: Disabled, unsupported by RCU flavor under test");
		fwd_progress = 0;
		return 0;
	}
	if (stall_cpu > 0) {
		VERBOSE_TOROUT_STRING("rcu_torture_fwd_prog_init: Disabled, conflicts with CPU-stall testing");
		fwd_progress = 0;
		if (IS_MODULE(CONFIG_RCU_TORTURE_TEST))
			return -EINVAL; /* In module, can fail back to user. */
		WARN_ON(1); /* Make sure rcutorture notices conflict. */
		return 0;
	}
	if (fwd_progress_holdoff <= 0)
		fwd_progress_holdoff = 1;
	if (fwd_progress_div <= 0)
		fwd_progress_div = 4;
	rfp = kcalloc(fwd_progress, sizeof(*rfp), GFP_KERNEL);
	fwd_prog_tasks = kcalloc(fwd_progress, sizeof(*fwd_prog_tasks), GFP_KERNEL);
	if (!rfp || !fwd_prog_tasks) {
		kfree(rfp);
		kfree(fwd_prog_tasks);
		fwd_prog_tasks = NULL;
		fwd_progress = 0;
		return -ENOMEM;
	}
	for (i = 0; i < fwd_progress; i++) {
		spin_lock_init(&rfp[i].rcu_fwd_lock);
		rfp[i].rcu_fwd_cb_tail = &rfp[i].rcu_fwd_cb_head;
		rfp[i].rcu_fwd_id = i;
	}
	mutex_lock(&rcu_fwd_mutex);
	rcu_fwds = rfp;
	mutex_unlock(&rcu_fwd_mutex);
	register_oom_notifier(&rcutorture_oom_nb);
	for (i = 0; i < fwd_progress; i++) {
		ret = torture_create_kthread(rcu_torture_fwd_prog, &rcu_fwds[i], fwd_prog_tasks[i]);
		if (ret) {
			fwd_progress = i;
			return ret;
		}
	}
	return 0;
}

static void rcu_torture_fwd_prog_cleanup(void)
{
	int i;
	struct rcu_fwd *rfp;

	if (!rcu_fwds || !fwd_prog_tasks)
		return;
	for (i = 0; i < fwd_progress; i++)
		torture_stop_kthread(rcu_torture_fwd_prog, fwd_prog_tasks[i]);
	unregister_oom_notifier(&rcutorture_oom_nb);
	mutex_lock(&rcu_fwd_mutex);
	rfp = rcu_fwds;
	rcu_fwds = NULL;
	mutex_unlock(&rcu_fwd_mutex);
	kfree(rfp);
	kfree(fwd_prog_tasks);
	fwd_prog_tasks = NULL;
}

/* Callback function for RCU barrier testing. */
static void rcu_torture_barrier_cbf(struct rcu_head *rcu)
{
	atomic_inc(&barrier_cbs_invoked);
}

/* IPI handler to get callback posted on desired CPU, if online. */
static void rcu_torture_barrier1cb(void *rcu_void)
{
	struct rcu_head *rhp = rcu_void;

	cur_ops->call(rhp, rcu_torture_barrier_cbf);
}

/* kthread function to register callbacks used to test RCU barriers. */
static int rcu_torture_barrier_cbs(void *arg)
{
	long myid = (long)arg;
	bool lastphase = false;
	bool newphase;
	struct rcu_head rcu;

	init_rcu_head_on_stack(&rcu);
	VERBOSE_TOROUT_STRING("rcu_torture_barrier_cbs task started");
	set_user_nice(current, MAX_NICE);
	do {
		wait_event(barrier_cbs_wq[myid],
			   (newphase =
			    smp_load_acquire(&barrier_phase)) != lastphase ||
			   torture_must_stop());
		lastphase = newphase;
		if (torture_must_stop())
			break;
		/*
		 * The above smp_load_acquire() ensures barrier_phase load
		 * is ordered before the following ->call().
		 */
		if (smp_call_function_single(myid, rcu_torture_barrier1cb,
					     &rcu, 1)) {
			// IPI failed, so use direct call from current CPU.
			cur_ops->call(&rcu, rcu_torture_barrier_cbf);
		}
		if (atomic_dec_and_test(&barrier_cbs_count))
			wake_up(&barrier_wq);
	} while (!torture_must_stop());
	if (cur_ops->cb_barrier != NULL)
		cur_ops->cb_barrier();
	destroy_rcu_head_on_stack(&rcu);
	torture_kthread_stopping("rcu_torture_barrier_cbs");
	return 0;
}

/* kthread function to drive and coordinate RCU barrier testing. */
static int rcu_torture_barrier(void *arg)
{
	int i;

	VERBOSE_TOROUT_STRING("rcu_torture_barrier task starting");
	do {
		atomic_set(&barrier_cbs_invoked, 0);
		atomic_set(&barrier_cbs_count, n_barrier_cbs);
		/* Ensure barrier_phase ordered after prior assignments. */
		smp_store_release(&barrier_phase, !barrier_phase);
		for (i = 0; i < n_barrier_cbs; i++)
			wake_up(&barrier_cbs_wq[i]);
		wait_event(barrier_wq,
			   atomic_read(&barrier_cbs_count) == 0 ||
			   torture_must_stop());
		if (torture_must_stop())
			break;
		n_barrier_attempts++;
		cur_ops->cb_barrier(); /* Implies smp_mb() for wait_event(). */
		if (atomic_read(&barrier_cbs_invoked) != n_barrier_cbs) {
			n_rcu_torture_barrier_error++;
			pr_err("barrier_cbs_invoked = %d, n_barrier_cbs = %d\n",
			       atomic_read(&barrier_cbs_invoked),
			       n_barrier_cbs);
			WARN_ON(1);
			// Wait manually for the remaining callbacks
			i = 0;
			do {
				if (WARN_ON(i++ > HZ))
					i = INT_MIN;
				schedule_timeout_interruptible(1);
				cur_ops->cb_barrier();
			} while (atomic_read(&barrier_cbs_invoked) !=
				 n_barrier_cbs &&
				 !torture_must_stop());
			smp_mb(); // Can't trust ordering if broken.
			if (!torture_must_stop())
				pr_err("Recovered: barrier_cbs_invoked = %d\n",
				       atomic_read(&barrier_cbs_invoked));
		} else {
			n_barrier_successes++;
		}
		schedule_timeout_interruptible(HZ / 10);
	} while (!torture_must_stop());
	torture_kthread_stopping("rcu_torture_barrier");
	return 0;
}

/* Initialize RCU barrier testing. */
static int rcu_torture_barrier_init(void)
{
	int i;
	int ret;

	if (n_barrier_cbs <= 0)
		return 0;
	if (cur_ops->call == NULL || cur_ops->cb_barrier == NULL) {
		pr_alert("%s" TORTURE_FLAG
			 " Call or barrier ops missing for %s,\n",
			 torture_type, cur_ops->name);
		pr_alert("%s" TORTURE_FLAG
			 " RCU barrier testing omitted from run.\n",
			 torture_type);
		return 0;
	}
	atomic_set(&barrier_cbs_count, 0);
	atomic_set(&barrier_cbs_invoked, 0);
	barrier_cbs_tasks =
		kcalloc(n_barrier_cbs, sizeof(barrier_cbs_tasks[0]),
			GFP_KERNEL);
	barrier_cbs_wq =
		kcalloc(n_barrier_cbs, sizeof(barrier_cbs_wq[0]), GFP_KERNEL);
	if (barrier_cbs_tasks == NULL || !barrier_cbs_wq)
		return -ENOMEM;
	for (i = 0; i < n_barrier_cbs; i++) {
		init_waitqueue_head(&barrier_cbs_wq[i]);
		ret = torture_create_kthread(rcu_torture_barrier_cbs,
					     (void *)(long)i,
					     barrier_cbs_tasks[i]);
		if (ret)
			return ret;
	}
	return torture_create_kthread(rcu_torture_barrier, NULL, barrier_task);
}

/* Clean up after RCU barrier testing. */
static void rcu_torture_barrier_cleanup(void)
{
	int i;

	torture_stop_kthread(rcu_torture_barrier, barrier_task);
	if (barrier_cbs_tasks != NULL) {
		for (i = 0; i < n_barrier_cbs; i++)
			torture_stop_kthread(rcu_torture_barrier_cbs,
					     barrier_cbs_tasks[i]);
		kfree(barrier_cbs_tasks);
		barrier_cbs_tasks = NULL;
	}
	if (barrier_cbs_wq != NULL) {
		kfree(barrier_cbs_wq);
		barrier_cbs_wq = NULL;
	}
}

static bool rcu_torture_can_boost(void)
{
	static int boost_warn_once;
	int prio;

	if (!(test_boost == 1 && cur_ops->can_boost) && test_boost != 2)
		return false;
	if (!cur_ops->start_gp_poll || !cur_ops->poll_gp_state)
		return false;

	prio = rcu_get_gp_kthreads_prio();
	if (!prio)
		return false;

	if (prio < 2) {
		if (boost_warn_once == 1)
			return false;

		pr_alert("%s: WARN: RCU kthread priority too low to test boosting.  Skipping RCU boost test. Try passing rcutree.kthread_prio > 1 on the kernel command line.\n", KBUILD_MODNAME);
		boost_warn_once = 1;
		return false;
	}

	return true;
}

static bool read_exit_child_stop;
static bool read_exit_child_stopped;
static wait_queue_head_t read_exit_wq;

// Child kthread which just does an rcutorture reader and exits.
static int rcu_torture_read_exit_child(void *trsp_in)
{
	struct torture_random_state *trsp = trsp_in;

	set_user_nice(current, MAX_NICE);
	// Minimize time between reading and exiting.
	while (!kthread_should_stop())
		schedule_timeout_uninterruptible(1);
	(void)rcu_torture_one_read(trsp, -1);
	return 0;
}

// Parent kthread which creates and destroys read-exit child kthreads.
static int rcu_torture_read_exit(void *unused)
{
	int count = 0;
	bool errexit = false;
	int i;
	struct task_struct *tsp;
	DEFINE_TORTURE_RANDOM(trs);

	// Allocate and initialize.
	set_user_nice(current, MAX_NICE);
	VERBOSE_TOROUT_STRING("rcu_torture_read_exit: Start of test");

	// Each pass through this loop does one read-exit episode.
	do {
		if (++count > read_exit_burst) {
			VERBOSE_TOROUT_STRING("rcu_torture_read_exit: End of episode");
			rcu_barrier(); // Wait for task_struct free, avoid OOM.
			for (i = 0; i < read_exit_delay; i++) {
				schedule_timeout_uninterruptible(HZ);
				if (READ_ONCE(read_exit_child_stop))
					break;
			}
			if (!READ_ONCE(read_exit_child_stop))
				VERBOSE_TOROUT_STRING("rcu_torture_read_exit: Start of episode");
			count = 0;
		}
		if (READ_ONCE(read_exit_child_stop))
			break;
		// Spawn child.
		tsp = kthread_run(rcu_torture_read_exit_child,
				     &trs, "%s",
				     "rcu_torture_read_exit_child");
		if (IS_ERR(tsp)) {
			TOROUT_ERRSTRING("out of memory");
			errexit = true;
			tsp = NULL;
			break;
		}
		cond_resched();
		kthread_stop(tsp);
		n_read_exits ++;
		stutter_wait("rcu_torture_read_exit");
	} while (!errexit && !READ_ONCE(read_exit_child_stop));

	// Clean up and exit.
	smp_store_release(&read_exit_child_stopped, true); // After reaping.
	smp_mb(); // Store before wakeup.
	wake_up(&read_exit_wq);
	while (!torture_must_stop())
		schedule_timeout_uninterruptible(1);
	torture_kthread_stopping("rcu_torture_read_exit");
	return 0;
}

static int rcu_torture_read_exit_init(void)
{
	if (read_exit_burst <= 0)
		return 0;
	init_waitqueue_head(&read_exit_wq);
	read_exit_child_stop = false;
	read_exit_child_stopped = false;
	return torture_create_kthread(rcu_torture_read_exit, NULL,
				      read_exit_task);
}

static void rcu_torture_read_exit_cleanup(void)
{
	if (!read_exit_task)
		return;
	WRITE_ONCE(read_exit_child_stop, true);
	smp_mb(); // Above write before wait.
	wait_event(read_exit_wq, smp_load_acquire(&read_exit_child_stopped));
	torture_stop_kthread(rcutorture_read_exit, read_exit_task);
}

static enum cpuhp_state rcutor_hp;

static void
rcu_torture_cleanup(void)
{
	int firsttime;
	int flags = 0;
	unsigned long gp_seq = 0;
	int i;

	if (torture_cleanup_begin()) {
		if (cur_ops->cb_barrier != NULL) {
			pr_info("%s: Invoking %pS().\n", __func__, cur_ops->cb_barrier);
			cur_ops->cb_barrier();
		}
		return;
	}
	if (!cur_ops) {
		torture_cleanup_end();
		return;
	}

	if (cur_ops->gp_kthread_dbg)
		cur_ops->gp_kthread_dbg();
	rcu_torture_read_exit_cleanup();
	rcu_torture_barrier_cleanup();
	rcu_torture_fwd_prog_cleanup();
	torture_stop_kthread(rcu_torture_stall, stall_task);
	torture_stop_kthread(rcu_torture_writer, writer_task);

	if (nocb_tasks) {
		for (i = 0; i < nrealnocbers; i++)
			torture_stop_kthread(rcu_nocb_toggle, nocb_tasks[i]);
		kfree(nocb_tasks);
		nocb_tasks = NULL;
	}

	if (reader_tasks) {
		for (i = 0; i < nrealreaders; i++)
			torture_stop_kthread(rcu_torture_reader,
					     reader_tasks[i]);
		kfree(reader_tasks);
		reader_tasks = NULL;
	}
	kfree(rcu_torture_reader_mbchk);
	rcu_torture_reader_mbchk = NULL;

	if (fakewriter_tasks) {
		for (i = 0; i < nfakewriters; i++)
			torture_stop_kthread(rcu_torture_fakewriter,
					     fakewriter_tasks[i]);
		kfree(fakewriter_tasks);
		fakewriter_tasks = NULL;
	}

	rcutorture_get_gp_data(cur_ops->ttype, &flags, &gp_seq);
	srcutorture_get_gp_data(cur_ops->ttype, srcu_ctlp, &flags, &gp_seq);
	pr_alert("%s:  End-test grace-period state: g%ld f%#x total-gps=%ld\n",
		 cur_ops->name, (long)gp_seq, flags,
		 rcutorture_seq_diff(gp_seq, start_gp_seq));
	torture_stop_kthread(rcu_torture_stats, stats_task);
	torture_stop_kthread(rcu_torture_fqs, fqs_task);
	if (rcu_torture_can_boost() && rcutor_hp >= 0)
		cpuhp_remove_state(rcutor_hp);

	/*
	 * Wait for all RCU callbacks to fire, then do torture-type-specific
	 * cleanup operations.
	 */
	if (cur_ops->cb_barrier != NULL) {
		pr_info("%s: Invoking %pS().\n", __func__, cur_ops->cb_barrier);
		cur_ops->cb_barrier();
	}
	if (cur_ops->cleanup != NULL)
		cur_ops->cleanup();

	rcu_torture_mem_dump_obj();

	rcu_torture_stats_print();  /* -After- the stats thread is stopped! */

	if (err_segs_recorded) {
		pr_alert("Failure/close-call rcutorture reader segments:\n");
		if (rt_read_nsegs == 0)
			pr_alert("\t: No segments recorded!!!\n");
		firsttime = 1;
		for (i = 0; i < rt_read_nsegs; i++) {
			pr_alert("\t%d: %#x ", i, err_segs[i].rt_readstate);
			if (err_segs[i].rt_delay_jiffies != 0) {
				pr_cont("%s%ldjiffies", firsttime ? "" : "+",
					err_segs[i].rt_delay_jiffies);
				firsttime = 0;
			}
			if (err_segs[i].rt_delay_ms != 0) {
				pr_cont("%s%ldms", firsttime ? "" : "+",
					err_segs[i].rt_delay_ms);
				firsttime = 0;
			}
			if (err_segs[i].rt_delay_us != 0) {
				pr_cont("%s%ldus", firsttime ? "" : "+",
					err_segs[i].rt_delay_us);
				firsttime = 0;
			}
			pr_cont("%s\n",
				err_segs[i].rt_preempted ? "preempted" : "");

		}
	}
	if (atomic_read(&n_rcu_torture_error) || n_rcu_torture_barrier_error)
		rcu_torture_print_module_parms(cur_ops, "End of test: FAILURE");
	else if (torture_onoff_failures())
		rcu_torture_print_module_parms(cur_ops,
					       "End of test: RCU_HOTPLUG");
	else
		rcu_torture_print_module_parms(cur_ops, "End of test: SUCCESS");
	torture_cleanup_end();
}

#ifdef CONFIG_DEBUG_OBJECTS_RCU_HEAD
static void rcu_torture_leak_cb(struct rcu_head *rhp)
{
}

static void rcu_torture_err_cb(struct rcu_head *rhp)
{
	/*
	 * This -might- happen due to race conditions, but is unlikely.
	 * The scenario that leads to this happening is that the
	 * first of the pair of duplicate callbacks is queued,
	 * someone else starts a grace period that includes that
	 * callback, then the second of the pair must wait for the
	 * next grace period.  Unlikely, but can happen.  If it
	 * does happen, the debug-objects subsystem won't have splatted.
	 */
	pr_alert("%s: duplicated callback was invoked.\n", KBUILD_MODNAME);
}
#endif /* #ifdef CONFIG_DEBUG_OBJECTS_RCU_HEAD */

/*
 * Verify that double-free causes debug-objects to complain, but only
 * if CONFIG_DEBUG_OBJECTS_RCU_HEAD=y.  Otherwise, say that the test
 * cannot be carried out.
 */
static void rcu_test_debug_objects(void)
{
#ifdef CONFIG_DEBUG_OBJECTS_RCU_HEAD
	struct rcu_head rh1;
	struct rcu_head rh2;
	struct rcu_head *rhp = kmalloc(sizeof(*rhp), GFP_KERNEL);

	init_rcu_head_on_stack(&rh1);
	init_rcu_head_on_stack(&rh2);
	pr_alert("%s: WARN: Duplicate call_rcu() test starting.\n", KBUILD_MODNAME);

	/* Try to queue the rh2 pair of callbacks for the same grace period. */
	preempt_disable(); /* Prevent preemption from interrupting test. */
	rcu_read_lock(); /* Make it impossible to finish a grace period. */
	call_rcu(&rh1, rcu_torture_leak_cb); /* Start grace period. */
	local_irq_disable(); /* Make it harder to start a new grace period. */
	call_rcu(&rh2, rcu_torture_leak_cb);
	call_rcu(&rh2, rcu_torture_err_cb); /* Duplicate callback. */
	if (rhp) {
		call_rcu(rhp, rcu_torture_leak_cb);
		call_rcu(rhp, rcu_torture_err_cb); /* Another duplicate callback. */
	}
	local_irq_enable();
	rcu_read_unlock();
	preempt_enable();

	/* Wait for them all to get done so we can safely return. */
	rcu_barrier();
	pr_alert("%s: WARN: Duplicate call_rcu() test complete.\n", KBUILD_MODNAME);
	destroy_rcu_head_on_stack(&rh1);
	destroy_rcu_head_on_stack(&rh2);
#else /* #ifdef CONFIG_DEBUG_OBJECTS_RCU_HEAD */
	pr_alert("%s: !CONFIG_DEBUG_OBJECTS_RCU_HEAD, not testing duplicate call_rcu()\n", KBUILD_MODNAME);
#endif /* #else #ifdef CONFIG_DEBUG_OBJECTS_RCU_HEAD */
}

static void rcutorture_sync(void)
{
	static unsigned long n;

	if (cur_ops->sync && !(++n & 0xfff))
		cur_ops->sync();
}

static int __init
rcu_torture_init(void)
{
	long i;
	int cpu;
	int firsterr = 0;
	int flags = 0;
	unsigned long gp_seq = 0;
	static struct rcu_torture_ops *torture_ops[] = {
		&rcu_ops, &rcu_busted_ops, &srcu_ops, &srcud_ops,
		&busted_srcud_ops, &tasks_ops, &tasks_rude_ops,
		&tasks_tracing_ops, &trivial_ops,
	};

	if (!torture_init_begin(torture_type, verbose))
		return -EBUSY;

	/* Process args and tell the world that the torturer is on the job. */
	for (i = 0; i < ARRAY_SIZE(torture_ops); i++) {
		cur_ops = torture_ops[i];
		if (strcmp(torture_type, cur_ops->name) == 0)
			break;
	}
	if (i == ARRAY_SIZE(torture_ops)) {
		pr_alert("rcu-torture: invalid torture type: \"%s\"\n",
			 torture_type);
		pr_alert("rcu-torture types:");
		for (i = 0; i < ARRAY_SIZE(torture_ops); i++)
			pr_cont(" %s", torture_ops[i]->name);
		pr_cont("\n");
		firsterr = -EINVAL;
		cur_ops = NULL;
		goto unwind;
	}
	if (cur_ops->fqs == NULL && fqs_duration != 0) {
		pr_alert("rcu-torture: ->fqs NULL and non-zero fqs_duration, fqs disabled.\n");
		fqs_duration = 0;
	}
	if (cur_ops->init)
		cur_ops->init();

	if (nreaders >= 0) {
		nrealreaders = nreaders;
	} else {
		nrealreaders = num_online_cpus() - 2 - nreaders;
		if (nrealreaders <= 0)
			nrealreaders = 1;
	}
	rcu_torture_print_module_parms(cur_ops, "Start of test");
	rcutorture_get_gp_data(cur_ops->ttype, &flags, &gp_seq);
	srcutorture_get_gp_data(cur_ops->ttype, srcu_ctlp, &flags, &gp_seq);
	start_gp_seq = gp_seq;
	pr_alert("%s:  Start-test grace-period state: g%ld f%#x\n",
		 cur_ops->name, (long)gp_seq, flags);

	/* Set up the freelist. */

	INIT_LIST_HEAD(&rcu_torture_freelist);
	for (i = 0; i < ARRAY_SIZE(rcu_tortures); i++) {
		rcu_tortures[i].rtort_mbtest = 0;
		list_add_tail(&rcu_tortures[i].rtort_free,
			      &rcu_torture_freelist);
	}

	/* Initialize the statistics so that each run gets its own numbers. */

	rcu_torture_current = NULL;
	rcu_torture_current_version = 0;
	atomic_set(&n_rcu_torture_alloc, 0);
	atomic_set(&n_rcu_torture_alloc_fail, 0);
	atomic_set(&n_rcu_torture_free, 0);
	atomic_set(&n_rcu_torture_mberror, 0);
	atomic_set(&n_rcu_torture_mbchk_fail, 0);
	atomic_set(&n_rcu_torture_mbchk_tries, 0);
	atomic_set(&n_rcu_torture_error, 0);
	n_rcu_torture_barrier_error = 0;
	n_rcu_torture_boost_ktrerror = 0;
	n_rcu_torture_boost_rterror = 0;
	n_rcu_torture_boost_failure = 0;
	n_rcu_torture_boosts = 0;
	for (i = 0; i < RCU_TORTURE_PIPE_LEN + 1; i++)
		atomic_set(&rcu_torture_wcount[i], 0);
	for_each_possible_cpu(cpu) {
		for (i = 0; i < RCU_TORTURE_PIPE_LEN + 1; i++) {
			per_cpu(rcu_torture_count, cpu)[i] = 0;
			per_cpu(rcu_torture_batch, cpu)[i] = 0;
		}
	}
	err_segs_recorded = 0;
	rt_read_nsegs = 0;

	/* Start up the kthreads. */

	rcu_torture_write_types();
	firsterr = torture_create_kthread(rcu_torture_writer, NULL,
					  writer_task);
	if (torture_init_error(firsterr))
		goto unwind;
	if (nfakewriters > 0) {
		fakewriter_tasks = kcalloc(nfakewriters,
					   sizeof(fakewriter_tasks[0]),
					   GFP_KERNEL);
		if (fakewriter_tasks == NULL) {
			TOROUT_ERRSTRING("out of memory");
			firsterr = -ENOMEM;
			goto unwind;
		}
	}
	for (i = 0; i < nfakewriters; i++) {
		firsterr = torture_create_kthread(rcu_torture_fakewriter,
						  NULL, fakewriter_tasks[i]);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	reader_tasks = kcalloc(nrealreaders, sizeof(reader_tasks[0]),
			       GFP_KERNEL);
	rcu_torture_reader_mbchk = kcalloc(nrealreaders, sizeof(*rcu_torture_reader_mbchk),
					   GFP_KERNEL);
	if (!reader_tasks || !rcu_torture_reader_mbchk) {
		TOROUT_ERRSTRING("out of memory");
		firsterr = -ENOMEM;
		goto unwind;
	}
	for (i = 0; i < nrealreaders; i++) {
		rcu_torture_reader_mbchk[i].rtc_chkrdr = -1;
		firsterr = torture_create_kthread(rcu_torture_reader, (void *)i,
						  reader_tasks[i]);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	nrealnocbers = nocbs_nthreads;
	if (WARN_ON(nrealnocbers < 0))
		nrealnocbers = 1;
	if (WARN_ON(nocbs_toggle < 0))
		nocbs_toggle = HZ;
	if (nrealnocbers > 0) {
		nocb_tasks = kcalloc(nrealnocbers, sizeof(nocb_tasks[0]), GFP_KERNEL);
		if (nocb_tasks == NULL) {
			TOROUT_ERRSTRING("out of memory");
			firsterr = -ENOMEM;
			goto unwind;
		}
	} else {
		nocb_tasks = NULL;
	}
	for (i = 0; i < nrealnocbers; i++) {
		firsterr = torture_create_kthread(rcu_nocb_toggle, NULL, nocb_tasks[i]);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	if (stat_interval > 0) {
		firsterr = torture_create_kthread(rcu_torture_stats, NULL,
						  stats_task);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	if (test_no_idle_hz && shuffle_interval > 0) {
		firsterr = torture_shuffle_init(shuffle_interval * HZ);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	if (stutter < 0)
		stutter = 0;
	if (stutter) {
		int t;

		t = cur_ops->stall_dur ? cur_ops->stall_dur() : stutter * HZ;
		firsterr = torture_stutter_init(stutter * HZ, t);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	if (fqs_duration < 0)
		fqs_duration = 0;
	if (fqs_duration) {
		/* Create the fqs thread */
		firsterr = torture_create_kthread(rcu_torture_fqs, NULL,
						  fqs_task);
		if (torture_init_error(firsterr))
			goto unwind;
	}
	if (test_boost_interval < 1)
		test_boost_interval = 1;
	if (test_boost_duration < 2)
		test_boost_duration = 2;
	if (rcu_torture_can_boost()) {

		boost_starttime = jiffies + test_boost_interval * HZ;

		firsterr = cpuhp_setup_state(CPUHP_AP_ONLINE_DYN, "RCU_TORTURE",
					     rcutorture_booster_init,
					     rcutorture_booster_cleanup);
		rcutor_hp = firsterr;
		if (torture_init_error(firsterr))
			goto unwind;

		// Testing RCU priority boosting requires rcutorture do
		// some serious abuse.  Counter this by running ksoftirqd
		// at higher priority.
		if (IS_BUILTIN(CONFIG_RCU_TORTURE_TEST)) {
			for_each_online_cpu(cpu) {
				struct sched_param sp;
				struct task_struct *t;

				t = per_cpu(ksoftirqd, cpu);
				WARN_ON_ONCE(!t);
				sp.sched_priority = 2;
				sched_setscheduler_nocheck(t, SCHED_FIFO, &sp);
			}
		}
	}
	shutdown_jiffies = jiffies + shutdown_secs * HZ;
	firsterr = torture_shutdown_init(shutdown_secs, rcu_torture_cleanup);
	if (torture_init_error(firsterr))
		goto unwind;
	firsterr = torture_onoff_init(onoff_holdoff * HZ, onoff_interval,
				      rcutorture_sync);
	if (torture_init_error(firsterr))
		goto unwind;
	firsterr = rcu_torture_stall_init();
	if (torture_init_error(firsterr))
		goto unwind;
	firsterr = rcu_torture_fwd_prog_init();
	if (torture_init_error(firsterr))
		goto unwind;
	firsterr = rcu_torture_barrier_init();
	if (torture_init_error(firsterr))
		goto unwind;
	firsterr = rcu_torture_read_exit_init();
	if (torture_init_error(firsterr))
		goto unwind;
	if (object_debug)
		rcu_test_debug_objects();
	torture_init_end();
	return 0;

unwind:
	torture_init_end();
	rcu_torture_cleanup();
	if (shutdown_secs) {
		WARN_ON(!IS_MODULE(CONFIG_RCU_TORTURE_TEST));
		kernel_power_off();
	}
	return firsterr;
}

module_init(rcu_torture_init);
module_exit(rcu_torture_cleanup);
