Commit 1d289fc5 authored by Paul E. McKenney's avatar Paul E. McKenney
Browse files

Merge branch 'torture.2025.08.14a' into HEAD

Torture-test updates:
* rcutorture: Fix jitter.sh spin time
* torture: Add --do-normal parameter to torture.sh help text
* torture: Announce kernel boot status at torture-test startup
* rcutorture: Suppress "Writer stall state" reports during boot
* rcutorture: Delay rcutorture readers and writers until boot completes
* torture: Delay CPU-hotplug operations until boot completes
* rcutorture: Delay forward-progress testing until boot completes
* rcutorture,refscale: Use kcalloc() instead of kzalloc()
* refperf: Remove redundant kfree() after torture_stop_kthread()
* refperf: Set reader_tasks to NULL after kfree()
parents a590b67d 1441edd1
Loading
Loading
Loading
Loading
+20 −7
Original line number Diff line number Diff line
@@ -1528,7 +1528,7 @@ static void do_rtws_sync(struct torture_random_state *trsp, void (*sync)(void))
static int
rcu_torture_writer(void *arg)
{
	bool boot_ended;
	bool booting_still = false;
	bool can_expedite = !rcu_gp_is_expedited() && !rcu_gp_is_normal();
	unsigned long cookie;
	struct rcu_gp_oldstate cookie_full;
@@ -1539,6 +1539,7 @@ rcu_torture_writer(void *arg)
	struct rcu_gp_oldstate gp_snap1_full;
	int i;
	int idx;
	unsigned long j;
	int oldnice = task_nice(current);
	struct rcu_gp_oldstate *rgo = NULL;
	int rgo_size = 0;
@@ -1571,16 +1572,26 @@ rcu_torture_writer(void *arg)
		return 0;
	}
	if (cur_ops->poll_active > 0) {
		ulo = kzalloc(cur_ops->poll_active * sizeof(ulo[0]), GFP_KERNEL);
		ulo = kcalloc(cur_ops->poll_active, sizeof(*ulo), GFP_KERNEL);
		if (!WARN_ON(!ulo))
			ulo_size = cur_ops->poll_active;
	}
	if (cur_ops->poll_active_full > 0) {
		rgo = kzalloc(cur_ops->poll_active_full * sizeof(rgo[0]), GFP_KERNEL);
		rgo = kcalloc(cur_ops->poll_active_full, sizeof(*rgo), GFP_KERNEL);
		if (!WARN_ON(!rgo))
			rgo_size = cur_ops->poll_active_full;
	}

	// If the system is still booting, let it finish.
	j = jiffies;
	while (!torture_must_stop() && !rcu_inkernel_boot_has_ended()) {
		booting_still = true;
		schedule_timeout_interruptible(HZ);
	}
	if (booting_still)
		pr_alert("%s" TORTURE_FLAG " Waited %lu jiffies for boot to complete.\n",
			 torture_type, jiffies - j);

	do {
		rcu_torture_writer_state = RTWS_FIXED_DELAY;
		torture_hrtimeout_us(500, 1000, &rand);
@@ -1769,13 +1780,11 @@ rcu_torture_writer(void *arg)
				       !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 &&
		    time_after(jiffies, stallsdone))
			for (i = 0; i < ARRAY_SIZE(rcu_tortures); i++)
				if (list_empty(&rcu_tortures[i].rtort_free) &&
@@ -2437,7 +2446,8 @@ rcu_torture_reader(void *arg)
			torture_hrtimeout_us(500, 1000, &rand);
			lastsleep = jiffies + 10;
		}
		while (torture_num_online_cpus() < mynumonline && !torture_must_stop())
		while (!torture_must_stop() &&
		       (torture_num_online_cpus() < mynumonline || !rcu_inkernel_boot_has_ended()))
			schedule_timeout_interruptible(HZ / 5);
		stutter_wait("rcu_torture_reader");
	} while (!torture_must_stop());
@@ -2756,7 +2766,8 @@ rcu_torture_stats_print(void)
		cur_ops->stats();
	if (rtcv_snap == rcu_torture_current_version &&
	    rcu_access_pointer(rcu_torture_current) &&
	    !rcu_stall_is_suppressed()) {
	    !rcu_stall_is_suppressed() &&
	    rcu_inkernel_boot_has_ended()) {
		int __maybe_unused flags = 0;
		unsigned long __maybe_unused gp_seq = 0;

@@ -3446,6 +3457,8 @@ static int rcu_torture_fwd_prog(void *args)
	int tested_tries = 0;

	VERBOSE_TOROUT_STRING("rcu_torture_fwd_progress task started");
	while (!rcu_inkernel_boot_has_ended())
		schedule_timeout_interruptible(HZ / 10);
	rcu_bind_current_to_nocb();
	if (!IS_ENABLED(CONFIG_SMP) || !IS_ENABLED(CONFIG_RCU_BOOST))
		set_user_nice(current, MAX_NICE);
+2 −2
Original line number Diff line number Diff line
@@ -1021,7 +1021,7 @@ static int main_func(void *arg)
	set_user_nice(current, MAX_NICE);

	VERBOSE_SCALEOUT("main_func task started");
	result_avg = kzalloc(nruns * sizeof(*result_avg), GFP_KERNEL);
	result_avg = kcalloc(nruns, sizeof(*result_avg), GFP_KERNEL);
	buf = kzalloc(800 + 64, GFP_KERNEL);
	if (!result_avg || !buf) {
		SCALEOUT_ERRSTRING("out of memory");
@@ -1133,9 +1133,9 @@ ref_scale_cleanup(void)
					     reader_tasks[i].task);
	}
	kfree(reader_tasks);
	reader_tasks = NULL;

	torture_stop_kthread("main_task", main_task);
	kfree(main_task);

	// Do scale-type-specific cleanup operations.
	if (cur_ops->cleanup != NULL)
+5 −2
Original line number Diff line number Diff line
@@ -359,6 +359,8 @@ torture_onoff(void *arg)
		torture_hrtimeout_jiffies(onoff_holdoff, &rand);
		VERBOSE_TOROUT_STRING("torture_onoff end holdoff");
	}
	while (!rcu_inkernel_boot_has_ended())
		schedule_timeout_interruptible(HZ / 10);
	while (!torture_must_stop()) {
		if (disable_onoff_at_boot && !rcu_inkernel_boot_has_ended()) {
			torture_hrtimeout_jiffies(HZ / 10, &rand);
@@ -797,8 +799,9 @@ static unsigned long torture_init_jiffies;
static void
torture_print_module_parms(void)
{
	pr_alert("torture module --- %s:  disable_onoff_at_boot=%d ftrace_dump_at_shutdown=%d verbose_sleep_frequency=%d verbose_sleep_duration=%d random_shuffle=%d\n",
		 torture_type, disable_onoff_at_boot, ftrace_dump_at_shutdown, verbose_sleep_frequency, verbose_sleep_duration, random_shuffle);
	pr_alert("torture module --- %s:  disable_onoff_at_boot=%d ftrace_dump_at_shutdown=%d verbose_sleep_frequency=%d verbose_sleep_duration=%d random_shuffle=%d%s\n",
		 torture_type, disable_onoff_at_boot, ftrace_dump_at_shutdown, verbose_sleep_frequency, verbose_sleep_duration, random_shuffle,
		 rcu_inkernel_boot_has_ended() ? "" : " still booting");
}

/*
+24 −3
Original line number Diff line number Diff line
@@ -39,6 +39,22 @@ do
	fi
done

# Uses global variables startsecs, startns, endsecs, endns, and limit.
# Exit code is success for time not yet elapsed and failure otherwise.
function timecheck {
	local done=`awk -v limit=$limit \
			-v startsecs=$startsecs \
			-v startns=$startns \
			-v endsecs=$endsecs \
			-v endns=$endns < /dev/null '
		BEGIN {
			delta = (endsecs - startsecs) * 1000 * 1000;
			delta += int((endns - startns) / 1000);
			print delta >= limit;
		}'`
	return $done
}

while :
do
	# Check for done.
@@ -85,15 +101,20 @@ do
	n=$(($n+1))
	sleep .$sleeptime

	# Spin a random duration
	# Spin a random duration, but with rather coarse granularity.
	limit=`awk -v me=$me -v n=$n -v spinmax=$spinmax 'BEGIN {
		srand(n + me + systime());
		printf("%06d", int(rand() * spinmax));
	}' < /dev/null`
	n=$(($n+1))
	for i in {1..$limit}
	startsecs=`date +%s`
	startns=`date +%N`
	endsecs=$startns
	endns=$endns
	while timecheck
	do
		echo > /dev/null
		endsecs=`date +%s`
		endns=`date +%N`
	done
done

+1 −0
Original line number Diff line number Diff line
@@ -94,6 +94,7 @@ usage () {
	echo "       --do-kvfree / --do-no-kvfree / --no-kvfree"
	echo "       --do-locktorture / --do-no-locktorture / --no-locktorture"
	echo "       --do-none"
	echo "       --do-normal / --do-no-normal / --no-normal"
	echo "       --do-rcuscale / --do-no-rcuscale / --no-rcuscale"
	echo "       --do-rcutasksflavors / --do-no-rcutasksflavors / --no-rcutasksflavors"
	echo "       --do-rcutorture / --do-no-rcutorture / --no-rcutorture"