mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-08-23 17:30:02 +00:00
perf bench futex: Fix hung wakeup tasks after requeueing
The futex-requeue benchmark can hang because of missing wakeups once the benchmark is done, ie: [Run 1]: Requeued 1024 of 1024 threads in 0.3290 ms perf: couldn't wakeup all tasks (135/1024) This bug, while perhaps suggesting missing wakeups in kernel futex code, is merely a consequence of the crappy FUTEX_CMP_REQUEUE man page, incorrectly mentioning that the number of requeued tasks is in fact returned, not the wakeups. This patch acknowledges this and updates the corresponding futex_wake code around it. Signed-off-by: Davidlohr Bueso <dbueso@suse.de> Cc: Mel Gorman <mgorman@suse.de> Link: http://lkml.kernel.org/r/1429894848.10273.44.camel@stgolabs.net Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
This commit is contained in:
parent
d13855ef18
commit
052b0f6eaf
1 changed files with 8 additions and 7 deletions
|
@ -132,6 +132,9 @@ int bench_futex_requeue(int argc, const char **argv,
|
|||
if (!fshared)
|
||||
futex_flag = FUTEX_PRIVATE_FLAG;
|
||||
|
||||
if (nrequeue > nthreads)
|
||||
nrequeue = nthreads;
|
||||
|
||||
printf("Run summary [PID %d]: Requeuing %d threads (from [%s] %p to %p), "
|
||||
"%d at a time.\n\n", getpid(), nthreads,
|
||||
fshared ? "shared":"private", &futex1, &futex2, nrequeue);
|
||||
|
@ -161,20 +164,18 @@ int bench_futex_requeue(int argc, const char **argv,
|
|||
|
||||
/* Ok, all threads are patiently blocked, start requeueing */
|
||||
gettimeofday(&start, NULL);
|
||||
for (nrequeued = 0; nrequeued < nthreads; nrequeued += nrequeue) {
|
||||
while (nrequeued < nthreads) {
|
||||
/*
|
||||
* Do not wakeup any tasks blocked on futex1, allowing
|
||||
* us to really measure futex_wait functionality.
|
||||
*/
|
||||
futex_cmp_requeue(&futex1, 0, &futex2, 0,
|
||||
nrequeue, futex_flag);
|
||||
nrequeued += futex_cmp_requeue(&futex1, 0, &futex2, 0,
|
||||
nrequeue, futex_flag);
|
||||
}
|
||||
|
||||
gettimeofday(&end, NULL);
|
||||
timersub(&end, &start, &runtime);
|
||||
|
||||
if (nrequeued > nthreads)
|
||||
nrequeued = nthreads;
|
||||
|
||||
update_stats(&requeued_stats, nrequeued);
|
||||
update_stats(&requeuetime_stats, runtime.tv_usec);
|
||||
|
||||
|
@ -184,7 +185,7 @@ int bench_futex_requeue(int argc, const char **argv,
|
|||
}
|
||||
|
||||
/* everybody should be blocked on futex2, wake'em up */
|
||||
nrequeued = futex_wake(&futex2, nthreads, futex_flag);
|
||||
nrequeued = futex_wake(&futex2, nrequeued, futex_flag);
|
||||
if (nthreads != nrequeued)
|
||||
warnx("couldn't wakeup all tasks (%d/%d)", nrequeued, nthreads);
|
||||
|
||||
|
|
Loading…
Reference in a new issue