[Devel] [PATCH rh7 1/3] mm/workingset: fix possible with memcg deletion.
Andrey Ryabinin
aryabinin at virtuozzo.com
Fri May 17 16:08:00 MSK 2019
workingset_refault() releases RCU lock too soon, before the
memcg_inc_ws_activate() which may result in crash if memcg deletion
runs in parallel with workingset_refault()
Fixes: f6a8b015027e ("ms/mm: workingset: per-cgroup cache thrash detection")
Signed-off-by: Andrey Ryabinin <aryabinin at virtuozzo.com>
---
mm/workingset.c | 7 ++++---
1 file changed, 4 insertions(+), 3 deletions(-)
diff --git a/mm/workingset.c b/mm/workingset.c
index 1168cc122828..1d7bdbf7a5d6 100644
--- a/mm/workingset.c
+++ b/mm/workingset.c
@@ -250,6 +250,7 @@ bool workingset_refault(void *shadow)
unsigned long refault;
struct zone *zone;
int memcgid;
+ bool ret = false;
unpack_shadow(shadow, &memcgid, &zone, &eviction);
@@ -278,7 +279,6 @@ bool workingset_refault(void *shadow)
lruvec = mem_cgroup_zone_lruvec(zone, memcg);
refault = atomic_long_read(&lruvec->inactive_age);
active_file = lruvec_lru_size(lruvec, LRU_ACTIVE_FILE);
- rcu_read_unlock();
/*
* The unsigned subtraction here gives an accurate distance
@@ -303,9 +303,10 @@ bool workingset_refault(void *shadow)
if (refault_distance <= active_file) {
memcg_inc_ws_activate(memcg);
inc_zone_state(zone, WORKINGSET_ACTIVATE);
- return true;
+ ret = true;
}
- return false;
+ rcu_read_unlock();
+ return ret;
}
/**
--
2.21.0
More information about the Devel
mailing list