From: Peng Liu liupeng256@huawei.com
hulk inclusion category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I59AN8 CVE: NA backport: openEuler-22.03-LTS
--------------------------------
The user specificed memmap-reserve range may overlap in-use memory region, and users are hard to avoid this due to KASLR. Thus, the reduplicative memmap-reserve range should be ignored. Furthermore, to be consistent with INITRD, the range that not in a memory region will also be ignored.
Fixes: d05cfbd95ab2 ("arm64: Add support for memmap kernel parameters") Signed-off-by: Peng Liu liupeng256@huawei.com Reviewed-by: Kefeng Wang wangkefeng.wang@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- .../admin-guide/kernel-parameters.txt | 3 ++- arch/arm64/mm/init.c | 22 ++++++++++++++++++- 2 files changed, 23 insertions(+), 2 deletions(-)
diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 98199d3ae741..e67e9dbb26bc 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2848,7 +2848,8 @@ [KNL,ACPI] Mark specific memory as reserved. Region of memory to be reserved is from ss to ss+nn. For ARM64, reserved memory must be in the range of - existed memory. + existed memory and do not overlap in-use memory region, + otherwise request will be ignored. Example: Exclude memory from 0x18690000-0x1869ffff memmap=64K$0x18690000 or diff --git a/arch/arm64/mm/init.c b/arch/arm64/mm/init.c index b19bdd48cc43..f5bd046f9e19 100644 --- a/arch/arm64/mm/init.c +++ b/arch/arm64/mm/init.c @@ -298,7 +298,27 @@ static void __init reserve_memmap_regions(void) for (i = 0; i < mbk_memmap_cnt; i++) { base = mbk_memmap_regions[i].base; size = mbk_memmap_regions[i].size; - memblock_reserve(base, size); + + if (!memblock_is_region_memory(base, size)) { + pr_warn("memmap reserve: 0x%08llx - 0x%08llx is not a memory region - ignore\n", + base, base + size); + continue; + } + + if (memblock_is_region_reserved(base, size)) { + pr_warn("memmap reserve: 0x%08llx - 0x%08llx overlaps in-use memory region - ignore\n", + base, base + size); + continue; + } + + if (memblock_reserve(base, size)) { + pr_warn("memmap reserve: 0x%08llx - 0x%08llx failed\n", + base, base + size); + continue; + } + + pr_info("memmap reserved: 0x%08llx - 0x%08llx (%lld MB)", + base, base + size, size >> 20); memblock_mark_memmap(base, size); } }