[PATCH] [fixlet] mm/vmscan: increment pgreclaim_pageout_* and pgrotate_* for MGLRU
From: Usama Arif
Date: Tue Jul 14 2026 - 08:18:16 EST
/proc/vmstat and per-memcg memory.stat expose pgreclaim_pageout_*
and pgrotate_* directly (memcg_node_stat_items in memcontrol.c
forwards them per-memcg). Without this fix they stay at 0 whenever
reclaim runs through MGLRU, misreporting observability.
Under pure MGLRU the scan-balance signal itself is not consumed (both
prepare_scan_control() and get_scan_count() are short-circuited on the
MGLRU paths, and MGLRU's own type/tier selection comes from
read_ctrl_pos() on lrugen->{avg_refaulted,avg_total,refaulted,evicted},
not from anon_cost/file_cost), so this fix is about observability.
Signed-off-by: Usama Arif <usama.arif@xxxxxxxxx>
---
mm/vmscan.c | 13 ++++++++++++-
1 file changed, 12 insertions(+), 1 deletion(-)
diff --git a/mm/vmscan.c b/mm/vmscan.c
index 279f78b7a0e4..2da36374bb4a 100644
--- a/mm/vmscan.c
+++ b/mm/vmscan.c
@@ -4867,7 +4867,8 @@ static int evict_folios(unsigned long nr_to_scan, struct lruvec *lruvec,
struct reclaim_stat stat;
struct lru_gen_mm_walk *walk;
int scanned, reclaimed;
- int isolated = 0, type, type_scanned;
+ int isolated = 0, nr_isolated = 0, type, type_scanned;
+ unsigned long total_reclaimed = 0, total_pageout = 0;
bool skip_retry = false;
struct mem_cgroup *memcg = lruvec_memcg(lruvec);
struct pglist_data *pgdat = lruvec_pgdat(lruvec);
@@ -4879,6 +4880,7 @@ static int evict_folios(unsigned long nr_to_scan, struct lruvec *lruvec,
scanned = isolate_folios(nr_to_scan, lruvec, sc, swappiness,
&list, &isolated, &type, &type_scanned);
+ nr_isolated = isolated;
/* Scanning may have emptied the oldest gen, flush it */
if (scanned)
@@ -4891,6 +4893,8 @@ static int evict_folios(unsigned long nr_to_scan, struct lruvec *lruvec,
retry:
reclaimed = shrink_folio_list(&list, pgdat, sc, &stat, false, memcg);
sc->nr_reclaimed += reclaimed;
+ total_reclaimed += reclaimed;
+ total_pageout += stat.nr_pageout;
/* Retry pass is only meant for clean folios without new isolation */
if (isolated)
handle_reclaim_writeback(isolated, pgdat, sc, &stat);
@@ -4944,6 +4948,13 @@ static int evict_folios(unsigned long nr_to_scan, struct lruvec *lruvec,
goto retry;
}
+ if (total_pageout)
+ mod_lruvec_state(lruvec, PGRECLAIM_PAGEOUT_ANON + type,
+ total_pageout);
+ if (nr_isolated > total_reclaimed)
+ mod_lruvec_state(lruvec, PGROTATE_ANON + type,
+ nr_isolated - total_reclaimed);
+
return scanned;
}
--
2.53.0-Meta