Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 101379
b: refs/heads/master
c: d120f65
h: refs/heads/master
i:
  101377: f459ece
  101375: 41a723b
v: v3
  • Loading branch information
Paul E. McKenney authored and Ingo Molnar committed Jun 18, 2008
1 parent adf30a4 commit 4815aca
Show file tree
Hide file tree
Showing 3 changed files with 64 additions and 5 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 5af970a48f3ba0dd96a036b196c79dc923f28231
refs/heads/master: d120f65f3aaf306c957bc4c82e510f5b0f1e9b27
8 changes: 7 additions & 1 deletion trunk/Documentation/RCU/torture.txt
Original file line number Diff line number Diff line change
Expand Up @@ -46,9 +46,15 @@ stat_interval The number of seconds between output of torture

shuffle_interval
The number of seconds to keep the test threads affinitied
to a particular subset of the CPUs, defaults to 5 seconds.
to a particular subset of the CPUs, defaults to 3 seconds.
Used in conjunction with test_no_idle_hz.

stutter The length of time to run the test before pausing for this
same period of time. Defaults to "stutter=5", so as
to run and pause for (roughly) five-second intervals.
Specifying "stutter=0" causes the test to run continuously
without pausing, which is the old default behavior.

test_no_idle_hz Whether or not to test the ability of RCU to operate in
a kernel that disables the scheduling-clock interrupt to
idle CPUs. Boolean parameter, "1" to test, "0" otherwise.
Expand Down
59 changes: 56 additions & 3 deletions trunk/kernel/rcutorture.c
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,8 @@ static int stat_interval; /* Interval between stats, in seconds. */
/* Defaults to "only at end of test". */
static int verbose; /* Print more debug info. */
static int test_no_idle_hz; /* Test RCU's support for tickless idle CPUs. */
static int shuffle_interval = 5; /* Interval between shuffles (in sec)*/
static int shuffle_interval = 3; /* Interval between shuffles (in sec)*/
static int stutter = 5; /* Start/stop testing interval (in sec) */
static char *torture_type = "rcu"; /* What RCU implementation to torture. */

module_param(nreaders, int, 0444);
Expand All @@ -72,6 +73,8 @@ module_param(test_no_idle_hz, bool, 0444);
MODULE_PARM_DESC(test_no_idle_hz, "Test support for tickless idle CPUs");
module_param(shuffle_interval, int, 0444);
MODULE_PARM_DESC(shuffle_interval, "Number of seconds between shuffles");
module_param(stutter, int, 0444);
MODULE_PARM_DESC(stutter, "Number of seconds to run/halt test");
module_param(torture_type, charp, 0444);
MODULE_PARM_DESC(torture_type, "Type of RCU to torture (rcu, rcu_bh, srcu)");

Expand All @@ -91,6 +94,7 @@ static struct task_struct **fakewriter_tasks;
static struct task_struct **reader_tasks;
static struct task_struct *stats_task;
static struct task_struct *shuffler_task;
static struct task_struct *stutter_task;

#define RCU_TORTURE_PIPE_LEN 10

Expand Down Expand Up @@ -119,6 +123,8 @@ static atomic_t n_rcu_torture_mberror;
static atomic_t n_rcu_torture_error;
static struct list_head rcu_torture_removed;

static int stutter_pause_test = 0;

/*
* Allocate an element from the rcu_tortures pool.
*/
Expand Down Expand Up @@ -179,6 +185,13 @@ rcu_random(struct rcu_random_state *rrsp)
return swahw32(rrsp->rrs_state);
}

static void
rcu_stutter_wait(void)
{
while (stutter_pause_test)
schedule_timeout_interruptible(1);
}

/*
* Operations vector for selecting different types of tests.
*/
Expand Down Expand Up @@ -563,6 +576,7 @@ rcu_torture_writer(void *arg)
}
rcu_torture_current_version++;
oldbatch = cur_ops->completed();
rcu_stutter_wait();
} while (!kthread_should_stop() && !fullstop);
VERBOSE_PRINTK_STRING("rcu_torture_writer task stopping");
while (!kthread_should_stop())
Expand All @@ -586,6 +600,7 @@ rcu_torture_fakewriter(void *arg)
schedule_timeout_uninterruptible(1 + rcu_random(&rand)%10);
udelay(rcu_random(&rand) & 0x3ff);
cur_ops->sync();
rcu_stutter_wait();
} while (!kthread_should_stop() && !fullstop);

VERBOSE_PRINTK_STRING("rcu_torture_fakewriter task stopping");
Expand Down Expand Up @@ -641,6 +656,7 @@ rcu_torture_reader(void *arg)
preempt_enable();
cur_ops->readunlock(idx);
schedule();
rcu_stutter_wait();
} while (!kthread_should_stop() && !fullstop);
VERBOSE_PRINTK_STRING("rcu_torture_reader task stopping");
while (!kthread_should_stop())
Expand Down Expand Up @@ -812,15 +828,34 @@ rcu_torture_shuffle(void *arg)
return 0;
}

/* Cause the rcutorture test to "stutter", starting and stopping all
* threads periodically.
*/
static int
rcu_torture_stutter(void *arg)
{
VERBOSE_PRINTK_STRING("rcu_torture_stutter task started");
do {
schedule_timeout_interruptible(stutter * HZ);
stutter_pause_test = 1;
if (!kthread_should_stop())
schedule_timeout_interruptible(stutter * HZ);
stutter_pause_test = 0;
} while (!kthread_should_stop());
VERBOSE_PRINTK_STRING("rcu_torture_stutter task stopping");
return 0;
}

static inline void
rcu_torture_print_module_parms(char *tag)
{
printk(KERN_ALERT "%s" TORTURE_FLAG
"--- %s: nreaders=%d nfakewriters=%d "
"stat_interval=%d verbose=%d test_no_idle_hz=%d "
"shuffle_interval = %d\n",
"shuffle_interval=%d stutter=%d\n",
torture_type, tag, nrealreaders, nfakewriters,
stat_interval, verbose, test_no_idle_hz, shuffle_interval);
stat_interval, verbose, test_no_idle_hz, shuffle_interval,
stutter);
}

static void
Expand All @@ -829,6 +864,11 @@ rcu_torture_cleanup(void)
int i;

fullstop = 1;
if (stutter_task) {
VERBOSE_PRINTK_STRING("Stopping rcu_torture_stutter task");
kthread_stop(stutter_task);
}
stutter_task = NULL;
if (shuffler_task) {
VERBOSE_PRINTK_STRING("Stopping rcu_torture_shuffle task");
kthread_stop(shuffler_task);
Expand Down Expand Up @@ -1017,6 +1057,19 @@ rcu_torture_init(void)
goto unwind;
}
}
if (stutter < 0)
stutter = 0;
if (stutter) {
/* Create the stutter thread */
stutter_task = kthread_run(rcu_torture_stutter, NULL,
"rcu_torture_stutter");
if (IS_ERR(stutter_task)) {
firsterr = PTR_ERR(stutter_task);
VERBOSE_PRINTK_ERRSTRING("Failed to create stutter");
stutter_task = NULL;
goto unwind;
}
}
return 0;

unwind:
Expand Down

0 comments on commit 4815aca

Please sign in to comment.