summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPratyush Yadav (Google) <pratyush@kernel.org>2026-03-09 12:34:06 +0000
committerAndrew Morton <akpm@linux-foundation.org>2026-04-05 13:53:24 -0700
commit91e74fa8b1bc1e44612cb677a710edce2061b6a7 (patch)
tree8810271485919304a32f640fe9fe354c5f758c2f
parent396042fb2b834a8fbcea9c850dbbd4ae7c7b75a9 (diff)
kho: make sure preservations do not span multiple NUMA nodes
The KHO restoration machinery is not capable of dealing with preservations that span multiple NUMA nodes. kho_preserve_folio() guarantees the preservation will only span one NUMA node since folios can't span multiple nodes. This leaves kho_preserve_pages(). While semantically kho_preserve_pages() only deals with 0-order pages, so all preservations should be single page only, in practice it combines preservations to higher orders for efficiency. This can result in a preservation spanning multiple nodes. Break up the preservations into a smaller order if that happens. Link: https://lkml.kernel.org/r/20260309123410.382308-1-pratyush@kernel.org Signed-off-by: Pratyush Yadav (Google) <pratyush@kernel.org> Suggested-by: Pasha Tatashin <pasha.tatashin@soleen.com> Reviewed-by: Samiullah Khawaja <skhawaja@google.com> Reviewed-by: Mike Rapoport (Microsoft) <rppt@kernel.org> Cc: Alexander Graf <graf@amazon.com> Cc: Pasha Tatashin <pasha.tatashin@soleen.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
-rw-r--r--kernel/liveupdate/kexec_handover.c10
1 files changed, 9 insertions, 1 deletions
diff --git a/kernel/liveupdate/kexec_handover.c b/kernel/liveupdate/kexec_handover.c
index 747a35107c84..3586490f7487 100644
--- a/kernel/liveupdate/kexec_handover.c
+++ b/kernel/liveupdate/kexec_handover.c
@@ -870,9 +870,17 @@ int kho_preserve_pages(struct page *page, unsigned long nr_pages)
}
while (pfn < end_pfn) {
- const unsigned int order =
+ unsigned int order =
min(count_trailing_zeros(pfn), ilog2(end_pfn - pfn));
+ /*
+ * Make sure all the pages in a single preservation are in the
+ * same NUMA node. The restore machinery can not cope with a
+ * preservation spanning multiple NUMA nodes.
+ */
+ while (pfn_to_nid(pfn) != pfn_to_nid(pfn + (1UL << order) - 1))
+ order--;
+
err = kho_radix_add_page(tree, pfn, order);
if (err) {
failed_pfn = pfn;