1 From: Tobias Wolf <dev-NTEO@vplace.de>
2 Subject: mm: Fix alloc_node_mem_map with ARCH_PFN_OFFSET calculation
4 An rt288x (ralink) based router (Belkin F5D8235 v1) does not boot with any
5 kernel beyond version 4.3 resulting in:
7 BUG: Bad page state in process swapper pfn:086ac
11 a1c34a3bf00af2cede839879502e12dc68491ad5 is the first bad commit
12 commit a1c34a3bf00af2cede839879502e12dc68491ad5
13 Author: Laura Abbott <laura@labbott.name>
14 Date: Thu Nov 5 18:48:46 2015 -0800
16 mm: Don't offset memmap for flatmem
18 Srinivas Kandagatla reported bad page messages when trying to remove the
19 bottom 2MB on an ARM based IFC6410 board
21 BUG: Bad page state in process swapper pfn:fffa8
22 page:ef7fb500 count:0 mapcount:0 mapping: (null) index:0x0
23 flags: 0x96640253(locked|error|dirty|active|arch_1|reclaim|mlocked)
24 page dumped because: PAGE_FLAGS_CHECK_AT_FREE flag(s) set
26 flags: 0x200041(locked|active|mlocked)
28 CPU: 0 PID: 0 Comm: swapper Not tainted 3.19.0-rc3-00007-g412f9ba-dirty
30 Hardware name: Qualcomm (Flattened Device Tree)
41 Disabling lock debugging due to kernel taint
43 :040000 040000 2de013c372345fd471cd58f0553c9b38b0ef1cc4
44 0a8156f848733dfa21e16c196dfb6c0a76290709 M mm
46 This fix for ARM does not account ARCH_PFN_OFFSET for mem_map as later used by
49 The following output was generated with two hacked in printk statements:
51 printk("before %p vs. %p or %p\n", mem_map, mem_map - offset, mem_map -
52 (pgdat->node_start_pfn - ARCH_PFN_OFFSET));
53 if (page_to_pfn(mem_map) != pgdat->node_start_pfn)
54 mem_map -= offset + (pgdat->node_start_pfn - ARCH_PFN_OFFSET);
55 printk("after %p\n", mem_map);
59 [ 0.000000] before 8861b280 vs. 8861b280 or 8851b280
60 [ 0.000000] after 8851b280
62 As seen in the first line mem_map with subtraction of offset does not equal the
63 mem_map after subtraction of ARCH_PFN_OFFSET.
65 After adding the offset of ARCH_PFN_OFFSET as well to mem_map as the
66 previously calculated offset is zero for the named platform it is able to boot
67 4.4 and 4.9-rc7 again.
69 Signed-off-by: Tobias Wolf <dev-NTEO@vplace.de>
74 @@ -6884,7 +6884,7 @@ static void __ref alloc_node_mem_map(str
75 mem_map = NODE_DATA(0)->node_mem_map;
76 #if defined(CONFIG_HAVE_MEMBLOCK_NODE_MAP) || defined(CONFIG_FLATMEM)
77 if (page_to_pfn(mem_map) != pgdat->node_start_pfn)
79 + mem_map -= offset + (pgdat->node_start_pfn - ARCH_PFN_OFFSET);
80 #endif /* CONFIG_HAVE_MEMBLOCK_NODE_MAP */