From b6ebf270ebd2a202dae0e14d2f16a929cdfdd61c Mon Sep 17 00:00:00 2001 From: Alexander Motin Date: Fri, 2 Sep 2022 16:21:18 -0400 Subject: [PATCH] Apply arc_shrink_shift to ARC above arc_c_min It makes sense to free memory in smaller chunks when approaching arc_c_min to let other kernel subsystems to free more, since after that point we can't free anything. This also matches behavior on Linux, where to shrinker reported only the size above arc_c_min. Reviewed-by: Ryan Moeller Reviewed-by: Allan Jude Reviewed-by: Brian Behlendorf Signed-off-by: Alexander Motin Closes #13794 --- module/os/freebsd/zfs/arc_os.c | 5 ++++- module/zfs/arc.c | 9 +++++---- 2 files changed, 9 insertions(+), 5 deletions(-) diff --git a/module/os/freebsd/zfs/arc_os.c b/module/os/freebsd/zfs/arc_os.c index fddb1f0e87..77af092e1e 100644 --- a/module/os/freebsd/zfs/arc_os.c +++ b/module/os/freebsd/zfs/arc_os.c @@ -223,7 +223,10 @@ arc_lowmem(void *arg __unused, int howto __unused) arc_warm = B_TRUE; arc_growtime = gethrtime() + SEC2NSEC(arc_grow_retry); free_memory = arc_available_memory(); - to_free = (arc_c >> arc_shrink_shift) - MIN(free_memory, 0); + int64_t can_free = arc_c - arc_c_min; + if (can_free <= 0) + return; + to_free = (can_free >> arc_shrink_shift) - MIN(free_memory, 0); DTRACE_PROBE2(arc__needfree, int64_t, free_memory, int64_t, to_free); arc_reduce_target_size(to_free); diff --git a/module/zfs/arc.c b/module/zfs/arc.c index 8d38826947..215250ea6f 100644 --- a/module/zfs/arc.c +++ b/module/zfs/arc.c @@ -5036,10 +5036,11 @@ arc_reap_cb(void *arg, zthr_t *zthr) */ free_memory = arc_available_memory(); - int64_t to_free = - (arc_c >> arc_shrink_shift) - free_memory; - if (to_free > 0) { - arc_reduce_target_size(to_free); + int64_t can_free = arc_c - arc_c_min; + if (can_free > 0) { + int64_t to_free = (can_free >> arc_shrink_shift) - free_memory; + if (to_free > 0) + arc_reduce_target_size(to_free); } spl_fstrans_unmark(cookie); }