These patches were generated from: https://github.com/raspberrypi/linux/commits/rpi-6.12.y With the following command: git format-patch -N v6.12.27..HEAD (HEAD -> 8d3206ee456a5ecdf9ddbfd8e5e231e4f0cd716e) Exceptions: - (def)configs patches - github workflows patches - applied & reverted patches - readme patches - wireless patches Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
107 lines
2.8 KiB
Diff
107 lines
2.8 KiB
Diff
From 92719518d6336db632a00bcfb2ec28a8f82998a8 Mon Sep 17 00:00:00 2001
|
|
From: Tvrtko Ursulin <tvrtko.ursulin@igalia.com>
|
|
Date: Mon, 29 Jul 2024 16:53:18 +0100
|
|
Subject: [PATCH] numa/emulation: Check emulated zones around the CMA window
|
|
|
|
... Make sure CMA zones do not straddle the emulated NUMA nodes ...
|
|
|
|
Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@igalia.com>
|
|
---
|
|
include/linux/cma.h | 6 ++++++
|
|
mm/cma.c | 36 ++++++++++++++++++++++++++++++++++++
|
|
mm/numa_emulation.c | 6 ++++++
|
|
3 files changed, 48 insertions(+)
|
|
|
|
--- a/include/linux/cma.h
|
|
+++ b/include/linux/cma.h
|
|
@@ -56,6 +56,7 @@ extern void cma_reserve_pages_on_error(s
|
|
#ifdef CONFIG_CMA
|
|
struct folio *cma_alloc_folio(struct cma *cma, int order, gfp_t gfp);
|
|
bool cma_free_folio(struct cma *cma, const struct folio *folio);
|
|
+int cma_check_range(u64 *start, u64 *end);
|
|
#else
|
|
static inline struct folio *cma_alloc_folio(struct cma *cma, int order, gfp_t gfp)
|
|
{
|
|
@@ -66,6 +67,11 @@ static inline bool cma_free_folio(struct
|
|
{
|
|
return false;
|
|
}
|
|
+
|
|
+static inline int cma_check_range(u64 *start, u64 *end)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
#endif
|
|
|
|
#endif
|
|
--- a/mm/cma.c
|
|
+++ b/mm/cma.c
|
|
@@ -602,3 +602,39 @@ int cma_for_each_area(int (*it)(struct c
|
|
|
|
return 0;
|
|
}
|
|
+
|
|
+struct cma_check_range_data {
|
|
+ u64 start, end;
|
|
+};
|
|
+
|
|
+static int check_range(struct cma *cma_, void *data)
|
|
+{
|
|
+ struct cma_check_range_data *range = data;
|
|
+ struct cma_check_range_data cma;
|
|
+ bool starts_in_range;
|
|
+ bool ends_in_range;
|
|
+
|
|
+ cma.start = cma_get_base(cma_);
|
|
+ cma.end = cma.start + cma_get_size(cma_) - 1;
|
|
+
|
|
+ starts_in_range = cma.start >= range->start && cma.start <= range->end;
|
|
+ ends_in_range = cma.end >= range->start && cma.end <= range->end;
|
|
+
|
|
+ if (starts_in_range == ends_in_range)
|
|
+ return 0;
|
|
+
|
|
+ pr_notice("CMA %s [%llx-%llx] straddles range [%llx-%llx]\n",
|
|
+ cma_->name, cma.start, cma.end, range->start, range->end);
|
|
+
|
|
+ return -EINVAL;
|
|
+}
|
|
+
|
|
+int cma_check_range(u64 *start, u64 *end)
|
|
+{
|
|
+ struct cma_check_range_data range = {
|
|
+ .start = *start,
|
|
+ .end = *end,
|
|
+ };
|
|
+
|
|
+ return cma_for_each_area(check_range, &range);
|
|
+}
|
|
--- a/mm/numa_emulation.c
|
|
+++ b/mm/numa_emulation.c
|
|
@@ -7,6 +7,7 @@
|
|
#include <linux/topology.h>
|
|
#include <linux/memblock.h>
|
|
#include <linux/numa_memblks.h>
|
|
+#include <linux/cma.h>
|
|
#include <asm/numa.h>
|
|
|
|
#define FAKE_NODE_MIN_SIZE ((u64)32 << 20)
|
|
@@ -51,6 +52,7 @@ static int __init emu_setup_memblk(struc
|
|
{
|
|
struct numa_memblk *eb = &ei->blk[ei->nr_blks];
|
|
struct numa_memblk *pb = &pi->blk[phys_blk];
|
|
+ int ret;
|
|
|
|
if (ei->nr_blks >= NR_NODE_MEMBLKS) {
|
|
pr_err("NUMA: Too many emulated memblks, failing emulation\n");
|
|
@@ -62,6 +64,10 @@ static int __init emu_setup_memblk(struc
|
|
eb->end = pb->start + size;
|
|
eb->nid = nid;
|
|
|
|
+ ret = cma_check_range(&eb->start, &eb->end);
|
|
+ if (ret)
|
|
+ return ret;
|
|
+
|
|
if (emu_nid_to_phys[nid] == NUMA_NO_NODE)
|
|
emu_nid_to_phys[nid] = pb->nid;
|
|
|