[PATCH 1/1] rcu: fix shrink budget underflow in lazy_rcu_shrink_scan
Longlong Xia <[email protected]>
| Newsgroups | org.kernel.vger.rcu,org.kernel.vger.linux-kernel |
|---|---|
| Message-ID | <[email protected]> |
From: Longlong Xia <[email protected]> The lazy RCU shrinker decremented sc->nr_to_scan (unsigned long) and then tested the result with <= 0. When a single CPU's lazy callback count exceeds the remaining budget, the subtraction wraps to a large positive value and the <= 0 comparison, which is equivalent to == 0 for an unsigned type, never fires again. The scan loop then iterates through every nocb CPU instead of honouring the reclaim budget. Reorder the logic to compare _count against nr_to_scan before subtracting, so the loop exits as soon as the budget is met. Fixes: c945b4da7a448 ("rcu: Shrinker for lazy rcu") Assisted-by: Zcode:GLM-5.2 Signed-off-by: Longlong Xia <[email protected]> --- kernel/rcu/tree_nocb.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/kernel/rcu/tree_nocb.h b/kernel/rcu/tree_nocb.h index 19bb42672baf..afc3ab84cc47 100644 --- a/kernel/rcu/tree_nocb.h +++ b/kernel/rcu/tree_nocb.h @@ -1332,10 +1332,11 @@ lazy_rcu_shrink_scan(struct shrinker *shrink, struct shrink_control *sc) rcu_nocb_try_flush_bypass(rdp, jiffies); rcu_nocb_unlock_irqrestore(rdp, flags); wake_nocb_gp(rdp); - sc->nr_to_scan -= _count; count += _count; - if (sc->nr_to_scan <= 0) + + if (_count >= sc->nr_to_scan) break; + sc->nr_to_scan -= _count; } mutex_unlock(&rcu_state.nocb_mutex); -- 2.43.0