[PATCH] kho: fix signed shift UB in kho_preserved_memory_reserve()

Kiarash Azarnia <[email protected]>
Newsgroups org.kvack.linux-mm,org.infradead.lists.kexec,org.kernel.vger.linux-kernel,org.kernel.vger.stable
Message-ID <[email protected]>
kho_preserved_memory_reserve() computes the size of a preserved
reservation as:

	sz = 1 << (order + PAGE_SHIFT);

`1` is a signed int, so the shift is signed-int arithmetic. For order
19 (a 2 GiB region) it produces 1 << 31, which is unrepresentable in
int and is undefined behavior; in practice it yields 0x80000000,
sign-extended on the assignment to the u64 sz. For order >= 20 the
shift count exceeds the width of int, which is also undefined. The
return value of memblock_reserve() is ignored and memblock_cap_size()
clamps the bogus size, so the kernel silently reserves the wrong
amount of memory for the preserved region.

kho_alloc_preserve() caps order at MAX_PAGE_ORDER and cannot reach
order 19, but a boot-time reserve_mem= region of at least 2 GiB drives
kho_preserve_pages() to compute order 19, and kho_preserve_pages() is
EXPORT_SYMBOL_GPL(), so the path is reachable.

Cast the shift operand to u64 so the arithmetic is done in 64 bits:

	sz = (u64)1 << (order + PAGE_SHIFT);

Fixes: 3f2ad90060f6 ("kho: adopt radix tree for preserved memory tracking")
Cc: [email protected]
Signed-off-by: Kiarash Azarnia <[email protected]>
---
 kernel/liveupdate/kexec_handover.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/kernel/liveupdate/kexec_handover.c b/kernel/liveupdate/kexec_handover.c
index 175c08a6e41e..c79f48bd64ac 100644
--- a/kernel/liveupdate/kexec_handover.c
+++ b/kernel/liveupdate/kexec_handover.c
@@ -501,7 +501,7 @@ static int __init kho_preserved_memory_reserve(phys_addr_t phys,
 	struct page *page;
 	u64 sz;
 
-	sz = 1 << (order + PAGE_SHIFT);
+	sz = (u64)1 << (order + PAGE_SHIFT);
 	page = kho_get_preserved_page(phys, order);
 
 	/* Reserve the memory preserved in KHO in memblock */
-- 
2.53.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.