Commit ba4877b9 authored by Michal Hocko's avatar Michal Hocko Committed by Linus Torvalds

vmstat: do not use deferrable delayed work for vmstat_update

Vinayak Menon has reported that an excessive number of tasks was throttled
in the direct reclaim inside too_many_isolated() because NR_ISOLATED_FILE
was relatively high compared to NR_INACTIVE_FILE.  However it turned out
that the real number of NR_ISOLATED_FILE was 0 and the per-cpu
vm_stat_diff wasn't transferred into the global counter.

vmstat_work which is responsible for the sync is defined as deferrable
delayed work which means that the defined timeout doesn't wake up an idle
CPU.  A CPU might stay in an idle state for a long time and general effort
is to keep such a CPU in this state as long as possible which might lead
to all sorts of troubles for vmstat consumers as can be seen with the
excessive direct reclaim throttling.

This patch basically reverts 39bf6270 ("VM statistics: Make timer
deferrable") but it shouldn't cause any problems for idle CPUs because
only CPUs with an active per-cpu drift are woken up since 7cc36bbd
("vmstat: on-demand vmstat workers v8") and CPUs which are idle for a
longer time shouldn't have per-cpu drift.

Fixes: 39bf6270 (VM statistics: Make timer deferrable)
Signed-off-by: default avatarMichal Hocko <mhocko@suse.cz>
Reported-by: default avatarVinayak Menon <vinmenon@codeaurora.org>
Acked-by: default avatarChristoph Lameter <cl@linux.com>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: Vladimir Davydov <vdavydov@parallels.com>
Cc: Mel Gorman <mgorman@suse.de>
Cc: Minchan Kim <minchan@kernel.org>
Cc: David Rientjes <rientjes@google.com>
Signed-off-by: default avatarAndrew Morton <akpm@linux-foundation.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@linux-foundation.org>
parent 9c0415eb
...@@ -1452,7 +1452,7 @@ static void __init start_shepherd_timer(void) ...@@ -1452,7 +1452,7 @@ static void __init start_shepherd_timer(void)
int cpu; int cpu;
for_each_possible_cpu(cpu) for_each_possible_cpu(cpu)
INIT_DEFERRABLE_WORK(per_cpu_ptr(&vmstat_work, cpu), INIT_DELAYED_WORK(per_cpu_ptr(&vmstat_work, cpu),
vmstat_update); vmstat_update);
if (!alloc_cpumask_var(&cpu_stat_off, GFP_KERNEL)) if (!alloc_cpumask_var(&cpu_stat_off, GFP_KERNEL))
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment