[PATCH] mm/memblock: Warn if used after slab is up and prevent memory corruption

From: Matt Fleming
Date: Mon Feb 27 2017 - 16:14:29 EST


Historically there have been many memory corruption bugs caused by
using the memblock API after its internal data structures have been
destroyed. The latest bug was fixed in commit,

20b1e22d01a4 ("x86/efi: Don't allocate memmap through memblock after mm_init()")

Instead of modifying the memblock data structures that no longer exist
and silently corrupting memory, WARN and return with an error.

Cc: Nicolai Stange <nicstange@xxxxxxxxx>
Cc: Dave Young <dyoung@xxxxxxxxxx>
Cc: Ard Biesheuvel <ard.biesheuvel@xxxxxxxxxx>
Cc: Mel Gorman <mgorman@xxxxxxxxxxxxxxxxxxx>
Cc: Andrew Morton <akpm@xxxxxxxxxxxxxxxxxxxx>
Cc: Vlastimil Babka <vbabka@xxxxxxx>
Cc: Michal Hocko <mhocko@xxxxxxx>
Signed-off-by: Matt Fleming <matt@xxxxxxxxxxxxxxxxxxx>
---
mm/memblock.c | 6 ++++++
1 file changed, 6 insertions(+)

diff --git a/mm/memblock.c b/mm/memblock.c
index 7608bc305936..4dbd86f2fddb 100644
--- a/mm/memblock.c
+++ b/mm/memblock.c
@@ -530,6 +530,9 @@ int __init_memblock memblock_add_range(struct memblock_type *type,
if (!size)
return 0;

+ if (WARN_ONCE(slab_is_available(), "memblock no longer available\n"))
+ return -EINVAL;
+
/* special case for empty array */
if (type->regions[0].size == 0) {
WARN_ON(type->cnt != 1 || type->total_size);
@@ -648,6 +651,9 @@ static int __init_memblock memblock_isolate_range(struct memblock_type *type,
if (!size)
return 0;

+ if (WARN_ONCE(slab_is_available(), "memblock no longer available\n"))
+ return -EINVAL;
+
/* we'll create at most two more regions */
while (type->cnt + 2 > type->max)
if (memblock_double_array(type, base, size) < 0)
--
2.10.0