aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/task_work.c
diff options
context:
space:
mode:
authorEric Dumazet <edumazet@google.com>2015-08-28 22:42:30 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2015-09-05 16:46:58 -0400
commitc82199061009d1561e31e17fca5e47a87cb7ff4c (patch)
tree547ec8ef61b4d70c57ff478d9d1de4853c373d92 /kernel/task_work.c
parentf377ea88b862bf7151be96d276f4cb740f8e1c41 (diff)
task_work: remove fifo ordering guarantee
In commit f341861fb0b ("task_work: add a scheduling point in task_work_run()") I fixed a latency problem adding a cond_resched() call. Later, commit ac3d0da8f329 added yet another loop to reverse a list, bringing back the latency spike : I've seen in some cases this loop taking 275 ms, if for example a process with 2,000,000 files is killed. We could add yet another cond_resched() in the reverse loop, or we can simply remove the reversal, as I do not think anything would depend on order of task_work_add() submitted works. Fixes: ac3d0da8f329 ("task_work: Make task_work_add() lockless") Signed-off-by: Eric Dumazet <edumazet@google.com> Reported-by: Maciej Żenczykowski <maze@google.com> Acked-by: Al Viro <viro@zeniv.linux.org.uk> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'kernel/task_work.c')
-rw-r--r--kernel/task_work.c12
1 files changed, 2 insertions, 10 deletions
diff --git a/kernel/task_work.c b/kernel/task_work.c
index 8727032e3a6f..53fa971d000d 100644
--- a/kernel/task_work.c
+++ b/kernel/task_work.c
@@ -18,6 +18,8 @@ static struct callback_head work_exited; /* all we need is ->next == NULL */
18 * This is like the signal handler which runs in kernel mode, but it doesn't 18 * This is like the signal handler which runs in kernel mode, but it doesn't
19 * try to wake up the @task. 19 * try to wake up the @task.
20 * 20 *
21 * Note: there is no ordering guarantee on works queued here.
22 *
21 * RETURNS: 23 * RETURNS:
22 * 0 if succeeds or -ESRCH. 24 * 0 if succeeds or -ESRCH.
23 */ 25 */
@@ -108,16 +110,6 @@ void task_work_run(void)
108 raw_spin_unlock_wait(&task->pi_lock); 110 raw_spin_unlock_wait(&task->pi_lock);
109 smp_mb(); 111 smp_mb();
110 112
111 /* Reverse the list to run the works in fifo order */
112 head = NULL;
113 do {
114 next = work->next;
115 work->next = head;
116 head = work;
117 work = next;
118 } while (work);
119
120 work = head;
121 do { 113 do {
122 next = work->next; 114 next = work->next;
123 work->func(work); 115 work->func(work);