mm-memory_hotplug-maintain-n_normal_memory-during-hotplug.patch removed from -mm tree
The quilt patch titled
Subject: mm/memory_hotplug: maintain N_NORMAL_MEMORY during hotplug
has been removed from the -mm tree. Its filename was
mm-memory_hotplug-maintain-n_normal_memory-during-hotplug.patch
This patch was dropped because it was merged into the mm-hotfixes-stable branch of git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm
------------------------------------------------------
From: Hao Li <[email protected]>
Subject: mm/memory_hotplug: maintain N_NORMAL_MEMORY during hotplug
Date: Mon, 30 Mar 2026 11:57:49 +0800
N_NORMAL_MEMORY is initialized from zone population at boot, but memory hotplug currently only updates N_MEMORY. As a result, a node that gains normal memory via hotplug can remain invisible to users iterating over N_NORMAL_MEMORY, while a node that loses its last normal memory can stay incorrectly marked as such.
The most visible effect is that /sys/devices/system/node/has_normal_memory does not report a node even after that node has gained normal memory via hotplug.
Also, list_lru-based shrinkers can undercount objects on such a node and may skip reclaim on that node entirely, which can lead to a higher memory footprint than expected.
Restore N_NORMAL_MEMORY maintenance directly in online_pages() and offline_pages(). Set the bit when a node that currently lacks normal memory onlines pages into a zone <= ZONE_NORMAL, and clear it when offlining removes the last present pages from zones <= ZONE_NORMAL.
This restores the intended semantics without bringing back the old status_change_nid_normal notifier plumbing which was removed in 8d2882a8edb8.
Current users that benefit include list_lru, zswap, nfsd filecache, hugetlb_cgroup, and has_normal_memory sysfs reporting.
---
mm/memory_hotplug.c | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+)
mm/memory_hotplug.c renamed from mm/memory_hotplug.c~mm-memory_hotplug-maintain-n_normal_memory-during-hotplug +20 -0
@@ -1209,6 +1209,13 @@ int online_pages(unsigned long pfn, unsiif (node_arg.nid >=0 )node_set_state (nid,N_MEMORY ); +/* +* Check whether we are adding normal memory to the node for the first +* time. +*/ +if (!node_state (nid,N_NORMAL_MEMORY ) &&zone_idx (zone) <=ZONE_NORMAL ) +node_set_state (nid,N_NORMAL_MEMORY ); +if (need_zonelists_rebuild)build_all_zonelists (NULL );
@@ -1908,6 +1915,8 @@ int offline_pages(unsigned long start_pfunsigned long flags;char *reason;int ret; +unsigned long normal_pages =0 ; +enum zone_type zt;/* * {on,off}lining is constrained to full memory sections (or more
@@ -2056,6 +2065,17 @@ int offline_pages(unsigned long start_pfinit_per_zone_wmark_min ();/* +* Check whether this operation removes the last normal memory from +* the node. We do this before clearing N_MEMORY to avoid the possible +* transient "!N_MEMORY && N_NORMAL_MEMORY" state. +*/ +if (zone_idx (zone) <=ZONE_NORMAL ) { +for (zt =0 ; zt <=ZONE_NORMAL ; zt++) + normal_pages += pgdat->node_zones[zt].present_pages; +if (!normal_pages) +node_clear_state (node,N_NORMAL_MEMORY ); + } +/* * Make sure to mark the node as memory-less before rebuilding the zone * list. Otherwise this node would still appear in the fallback lists. */
_
Patches currently in -mm which might be from [email protected] are