Skip to contentSkip to conversation

arm64: improved memory map handling for /dev/mem, ACPI etc

PATCH In review Ard Biesheuvel 4 participants 27 messages Dec 22, 2014 – Jan 12, 2015

Subsystems (5)
lore
Share & tools
lore
#0 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

 arch/arm64/Kconfig       |  1 +
 arch/arm64/kernel/efi.c  | 82 +++++++++++++++++++++++++++++++++++++++---------
 arch/arm64/mm/mmap.c     |  2 +-
 arch/arm64/mm/mmu.c      | 15 ++++++++-
 drivers/of/fdt.c         |  1 +
 include/linux/memblock.h | 10 ++++++
 mm/memblock.c            | 18 +++++++++++
 7 files changed, 113 insertions(+), 16 deletions(-)
Signature · 1 line
1.8.3.2
#1 lore raw

PATCH 1/8 arm64/efi: use UEFI memory map unconditionally if available

On systems that boot via UEFI, all memory nodes are deleted from the device tree, and instead, the size and location of system RAM is derived from the UEFI memory map. This is handled by reserve_regions, which not only reserves parts of memory that UEFI declares as reserved, but also installs the memblocks that cover the remaining usable memory.

Currently, reserve_regions() is only called if uefi_init() succeeds. However, it does not actually depend on anything that uefi_init() does, and not calling reserve_regions() results in a broken boot, so it is better to just call it unconditionally.

---
 arch/arm64/kernel/efi.c | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)
arch/arm64/kernel/efi.c +4 -7
index d7d2e818c856..d2f483a7cffe 100644
@@ -208,8 +208,7 @@ void __init efi_init(void)
 	memmap.desc_size = params.desc_size;
 	memmap.desc_version = params.desc_ver;
 
-	if (uefi_init() < 0)
-		return;
+	WARN_ON(uefi_init() < 0);
 
 	reserve_regions();
 }
@@ -218,15 +217,13 @@ static int __init arm64_enter_virtual_mode(void)
 {
 	u64 mapsize;
 
-	if (!efi_enabled(EFI_BOOT)) {
-		pr_info("EFI services will not be available.\n");
-		return -1;
-	}
+	if (!efi_enabled(EFI_MEMMAP))
+		return 0;
 
 	mapsize = memmap.map_end - memmap.map;
 	early_memunmap(memmap.map, mapsize);
 
-	if (efi_runtime_disabled()) {
+	if (!efi_enabled(EFI_BOOT) || efi_runtime_disabled()) {
 		pr_info("EFI runtime services will be disabled.\n");
 		return -1;
 	}
Signature · 1 line
1.8.3.2
#2 lore raw

PATCH 1/8 arm64/efi: use UEFI memory map unconditionally if available

Quoted 39 lines · Ard Biesheuvel

On systems that boot via UEFI, all memory nodes are deleted from the device tree, and instead, the size and location of system RAM is derived from the UEFI memory map. This is handled by reserve_regions, which not only reserves parts of memory that UEFI declares as reserved, but also installs the memblocks that cover the remaining usable memory.

Currently, reserve_regions() is only called if uefi_init() succeeds. However, it does not actually depend on anything that uefi_init() does, and not calling reserve_regions() results in a broken boot, so it is better to just call it unconditionally.

---
 arch/arm64/kernel/efi.c | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)
arch/arm64/kernel/efi.c +2 -6
index d7d2e818c856..d2f483a7cffe 100644
@@ -208,8 +208,7 @@ void __init efi_init(void)
 	memmap.desc_size = params.desc_size;
 	memmap.desc_version = params.desc_ver;
 
-	if (uefi_init() < 0)
-		return;
+	WARN_ON(uefi_init() < 0);
 
 	reserve_regions();
 }
@@ -218,15 +217,13 @@ static int __init arm64_enter_virtual_mode(void)
 {
 	u64 mapsize;
 
-	if (!efi_enabled(EFI_BOOT)) {
-		pr_info("EFI services will not be available.\n");
-		return -1;
-	}
+	if (!efi_enabled(EFI_MEMMAP))

arch/arm64/kernel/efi.c static int __init arm64_enter_virtual_mode(void) · line 229

Quoted 10 lines
arch/arm64/kernel/efi.c +2 -1
+		return 0;
 
 	mapsize = memmap.map_end - memmap.map;
 	early_memunmap(memmap.map, mapsize);
 
-	if (efi_runtime_disabled()) {
+	if (!efi_enabled(EFI_BOOT) || efi_runtime_disabled()) {
 		pr_info("EFI runtime services will be disabled.\n");
 		return -1;
 	}

Am I correct in thinking that it's possible to have EFI_MEMMAP set but not EFI_BOOT? That's not how things work on x86. EFI_BOOT means "I am an EFI-enabled platform and I was booted using EFI."

In other words, EFI_MEMMAP should imply EFI_BOOT (how did you get the memmap if you weren't booted using EFI?)

It looks like you should be setting EFI_BOOT (and EFI_64BIT) in efi_init() if efi_get_fdt_params() succeeds.

Signature · 1 line
Matt Fleming, Intel Open Source Technology Center
#3 lore raw

PATCH 1/8 arm64/efi: use UEFI memory map unconditionally if available

Quoted 55 lines · Matt Fleming
Quoted 39 lines · Ard Biesheuvel

On systems that boot via UEFI, all memory nodes are deleted from the device tree, and instead, the size and location of system RAM is derived from the UEFI memory map. This is handled by reserve_regions, which not only reserves parts of memory that UEFI declares as reserved, but also installs the memblocks that cover the remaining usable memory.

Currently, reserve_regions() is only called if uefi_init() succeeds. However, it does not actually depend on anything that uefi_init() does, and not calling reserve_regions() results in a broken boot, so it is better to just call it unconditionally.

---
 arch/arm64/kernel/efi.c | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)
arch/arm64/kernel/efi.c +2 -6
index d7d2e818c856..d2f483a7cffe 100644
@@ -208,8 +208,7 @@ void __init efi_init(void)
      memmap.desc_size = params.desc_size;
      memmap.desc_version = params.desc_ver;
 
-     if (uefi_init() < 0)
-             return;
+     WARN_ON(uefi_init() < 0);
 
      reserve_regions();
 }
@@ -218,15 +217,13 @@ static int __init arm64_enter_virtual_mode(void)
 {
      u64 mapsize;
 
-     if (!efi_enabled(EFI_BOOT)) {
-             pr_info("EFI services will not be available.\n");
-             return -1;
-     }
+     if (!efi_enabled(EFI_MEMMAP))

arch/arm64/kernel/efi.c static int __init arm64_enter_virtual_mode(void) · line 229

Quoted 10 lines
arch/arm64/kernel/efi.c +2 -1
+             return 0;
 
      mapsize = memmap.map_end - memmap.map;
      early_memunmap(memmap.map, mapsize);
 
-     if (efi_runtime_disabled()) {
+     if (!efi_enabled(EFI_BOOT) || efi_runtime_disabled()) {
              pr_info("EFI runtime services will be disabled.\n");
              return -1;
      }

Am I correct in thinking that it's possible to have EFI_MEMMAP set but not EFI_BOOT? That's not how things work on x86. EFI_BOOT means "I am an EFI-enabled platform and I was booted using EFI."

Quoted 3 lines

In other words, EFI_MEMMAP should imply EFI_BOOT (how did you get the memmap if you weren't booted using EFI?)

In the arm64 case, the memory map is retrieved by the stub, and its address is passed via the /chosen DT node, which also contains the address of the EFI system table. In the unlikely event that, for instance, the FEI system table signature is corrupted, we will not set EFI_BOOT (nor EFI_64BIT).

Quoted 3 lines

It looks like you should be setting EFI_BOOT (and EFI_64BIT) in efi_init() if efi_get_fdt_params() succeeds.

Yes, I agree. We should probably set EFI_SYSTEM_TABLES in uefi_init() then, and possibly unset it again if we fail to remap it.

Signature · 1 line
Ard.
#4 lore raw

PATCH 1/8 arm64/efi: use UEFI memory map unconditionally if available

Quoted 7 lines · Ard Biesheuvel
Quoted 3 lines · Matt Fleming

It looks like you should be setting EFI_BOOT (and EFI_64BIT) in efi_init() if efi_get_fdt_params() succeeds.

Yes, I agree. We should probably set EFI_SYSTEM_TABLES in uefi_init() then, and possibly unset it again if we fail to remap it.

Yeah, I think that would be more correct.

Signature · 1 line
Matt Fleming, Intel Open Source Technology Center
#5 lore raw

PATCH 1/8 arm64/efi: use UEFI memory map unconditionally if available

In reply to Ard Biesheuvel
Quoted 11 lines · Ard Biesheuvel

On systems that boot via UEFI, all memory nodes are deleted from the device tree, and instead, the size and location of system RAM is derived from the UEFI memory map. This is handled by reserve_regions, which not only reserves parts of memory that UEFI declares as reserved, but also installs the memblocks that cover the remaining usable memory.

Currently, reserve_regions() is only called if uefi_init() succeeds. However, it does not actually depend on anything that uefi_init() does, and not calling reserve_regions() results in a broken boot, so it is better to just call it unconditionally.

Quoted 4 lines
---
 arch/arm64/kernel/efi.c | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)

Will

Quoted 37 lines
arch/arm64/kernel/efi.c +4 -7
index d7d2e818c856..d2f483a7cffe 100644
@@ -208,8 +208,7 @@ void __init efi_init(void)
 	memmap.desc_size = params.desc_size;
 	memmap.desc_version = params.desc_ver;
 
-	if (uefi_init() < 0)
-		return;
+	WARN_ON(uefi_init() < 0);
 
 	reserve_regions();
 }
@@ -218,15 +217,13 @@ static int __init arm64_enter_virtual_mode(void)
 {
 	u64 mapsize;
 
-	if (!efi_enabled(EFI_BOOT)) {
-		pr_info("EFI services will not be available.\n");
-		return -1;
-	}
+	if (!efi_enabled(EFI_MEMMAP))
+		return 0;
 
 	mapsize = memmap.map_end - memmap.map;
 	early_memunmap(memmap.map, mapsize);
 
-	if (efi_runtime_disabled()) {
+	if (!efi_enabled(EFI_BOOT) || efi_runtime_disabled()) {
 		pr_info("EFI runtime services will be disabled.\n");
 		return -1;
 	}
Signature · 1 line
1.8.3.2
#6 lore raw

PATCH 2/8 arm64/efi: register UEFI reserved regions as iomem resources

In reply to Ard Biesheuvel

To prevent device drivers from attaching to device or memory regions owned by the firmware, register all UEFI reserved regions in the iomem resource table at init time.

---
 arch/arm64/kernel/efi.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 46 insertions(+)
arch/arm64/kernel/efi.c +46 -0
index d2f483a7cffe..ba5fe66c3634 100644
@@ -305,6 +305,50 @@ void efi_virtmap_unload(void)
 	efi_set_pgd(current->active_mm);
 }
 
+static __init void efi_reserve_iomem_resource(efi_memory_desc_t *md)
+{
+	struct resource *res;
+
+	res = alloc_bootmem_low(sizeof(*res));
+	res->start = md->phys_addr;
+	res->end = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) - 1;
+	res->flags = IORESOURCE_MEM | IORESOURCE_BUSY;
+
+	if (!is_reserve_region(md)) {
+		/*
+		 * Non-RAM regions with the EFI_MEMORY_RUNTIME attribute
+		 * are owned by the UEFI firmware, so make sure they are
+		 * tagged as exclusive: this will prevent device drivers
+		 * from binding to the memory region, and will also prevent
+		 * access via /dev/mem if CONFIG_STRICT_DEVMEM is in effect.
+		 */
+		res->name = "UEFI Runtime [MMIO]";
+		res->flags |= IORESOURCE_EXCLUSIVE;
+	} else if (md->type == EFI_RUNTIME_SERVICES_DATA) {
+		/*
+		 * UEFI Runtime Services Data regions may be used to store
+		 * configuration tables such as SMBIOS, which are often
+		 * accessed using userland tools such as 'dmidecode', that
+		 * are /dev/mem based. So don't set the exclusive flag in
+		 * this case.
+		 */
+		res->name = "UEFI Runtime [Data]";
+	} else {
+		/*
+		 * Register all remaining reserved RAM regions as both busy
+		 * and exclusive in the iomem resource table. This prevents
+		 * drivers from claiming the region, and also disallows
+		 * /dev/mem access.
+		 */
+		if (md->type == EFI_RUNTIME_SERVICES_CODE)
+			res->name = "UEFI Runtime [Code]";
+		else
+			res->name = "UEFI Reserved";
+		res->flags |= IORESOURCE_EXCLUSIVE;
+	}
+	request_resource(&iomem_resource, res);
+}
+
 void __init efi_virtmap_init(void)
 {
 	efi_memory_desc_t *md;
@@ -316,6 +360,8 @@ void __init efi_virtmap_init(void)
 		u64 paddr, npages, size;
 		pgprot_t prot;
 
+		if (is_reserve_region(md) || md->attribute & EFI_MEMORY_RUNTIME)
+			efi_reserve_iomem_resource(md);
 		if (!(md->attribute & EFI_MEMORY_RUNTIME))
 			continue;
 		if (WARN(md->virt_addr == 0,
Signature · 1 line
1.8.3.2
#7 lore raw

PATCH 2/8 arm64/efi: register UEFI reserved regions as iomem resources

Quoted 8 lines · Ard Biesheuvel

To prevent device drivers from attaching to device or memory regions owned by the firmware, register all UEFI reserved regions in the iomem resource table at init time.

---
 arch/arm64/kernel/efi.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 46 insertions(+)

Looks nice.

Just curious, have you actually seen drivers trying to claim these regions?

Signature · 1 line
Matt Fleming, Intel Open Source Technology Center
#8 lore raw

PATCH 2/8 arm64/efi: register UEFI reserved regions as iomem resources

Quoted 10 lines · Matt Fleming
Quoted 8 lines · Ard Biesheuvel

To prevent device drivers from attaching to device or memory regions owned by the firmware, register all UEFI reserved regions in the iomem resource table at init time.

---
 arch/arm64/kernel/efi.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 46 insertions(+)
Quoted 5 lines

Looks nice.

Just curious, have you actually seen drivers trying to claim these regions?

Yes. RTC and NOR flash in particular, which should not appear in the device tree in the first place if the firmware owns them, but let's not assume all firmware vendors will get that right first try,

#9 lore raw

PATCH 3/8 memblock: add physmem to memblock_dump_all() output

In reply to Ard Biesheuvel

If CONFIG_HAVE_MEMBLOCK_PHYS_MAP is set, there is a third memblock map called 'physmem'. Add it to the output of memblock_dump_all().

---
 mm/memblock.c | 3 +++
 1 file changed, 3 insertions(+)
mm/memblock.c +3 -0
index 252b77bdf65e..c27353beb260 100644
@@ -1522,6 +1522,9 @@ void __init_memblock __memblock_dump_all(void)
 
 	memblock_dump(&memblock.memory, "memory");
 	memblock_dump(&memblock.reserved, "reserved");
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+	memblock_dump(&memblock.physmem, "physmem");
+#endif
 }
 
 void __init memblock_allow_resize(void)
Signature · 1 line
1.8.3.2
#10 lore raw

Re: [PATCH 3/8] memblock: add physmem to memblock_dump_all() output

(Adding Andrew, linux-mm and lkml)

Quoted 25 lines · Ard Biesheuvel

If CONFIG_HAVE_MEMBLOCK_PHYS_MAP is set, there is a third memblock map called 'physmem'. Add it to the output of memblock_dump_all().

---
 mm/memblock.c | 3 +++
 1 file changed, 3 insertions(+)
mm/memblock.c +3 -0
index 252b77bdf65e..c27353beb260 100644
@@ -1522,6 +1522,9 @@ void __init_memblock __memblock_dump_all(void)
 
 	memblock_dump(&memblock.memory, "memory");
 	memblock_dump(&memblock.reserved, "reserved");
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+	memblock_dump(&memblock.physmem, "physmem");
+#endif
 }
 
 void __init memblock_allow_resize(void)
Signature · 1 line
1.8.3.2
Signature · 1 line
Matt Fleming, Intel Open Source Technology Center
#11 lore raw

PATCH 4/8 memblock: introduce memblock_add_phys() and memblock_is_physmem()

In reply to Ard Biesheuvel

This introduces the following functions:
- memblock_add_phys(), that registers regions in the 'physmem' memblock map if CONFIG_HAVE_MEMBLOCK_PHYS_MAP is set; otherwise, it is a nop
- memblock_is_physmem(), returns whether a physical address is classified as physical memory.

---
 include/linux/memblock.h | 10 ++++++++++
 mm/memblock.c            | 15 +++++++++++++++
 2 files changed, 25 insertions(+)
include/linux/memblock.h +10 -0
index e8cc45307f8f..d32fe838c6ca 100644
@@ -365,6 +365,16 @@ static inline unsigned long memblock_region_reserved_end_pfn(const struct memblo
 #define __initdata_memblock
 #endif
 
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+int memblock_add_phys(phys_addr_t base, phys_addr_t size);
+int memblock_is_physmem(phys_addr_t addr);
+#else
+static inline int memblock_add_phys(phys_addr_t base, phys_addr_t size)
+{
+	return 0;
+}
+#endif /* CONFIG_HAVE_MEMBLOCK_PHYS_MAP */
+
 #else
 static inline phys_addr_t memblock_alloc(phys_addr_t size, phys_addr_t align)
 {
mm/memblock.c +15 -0
index c27353beb260..107aa5ee2d7b 100644
@@ -586,6 +586,14 @@ int __init_memblock memblock_add(phys_addr_t base, phys_addr_t size)
 				   MAX_NUMNODES, 0);
 }
 
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+int __init_memblock memblock_add_phys(phys_addr_t base, phys_addr_t size)
+{
+	return memblock_add_range(&memblock.physmem, base, size,
+				  MAX_NUMNODES, 0);
+}
+#endif
+
 /**
  * memblock_isolate_range - isolate given range into disjoint memblocks
  * @type: memblock type to isolate range for
@@ -1398,6 +1406,13 @@ int __init_memblock memblock_is_memory(phys_addr_t addr)
 	return memblock_search(&memblock.memory, addr) != -1;
 }
 
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+int __init_memblock memblock_is_physmem(phys_addr_t addr)
+{
+	return memblock_search(&memblock.physmem, addr) != -1;
+}
+#endif
+
 #ifdef CONFIG_HAVE_MEMBLOCK_NODE_MAP
 int __init_memblock memblock_search_pfn_nid(unsigned long pfn,
 			 unsigned long *start_pfn, unsigned long *end_pfn)
Signature · 1 line
1.8.3.2
#12 lore raw

Re: [PATCH 4/8] memblock: introduce memblock_add_phys() and memblock_is_physmem()

(Moar reviewers)

Quoted 73 lines · Ard Biesheuvel

This introduces the following functions:
- memblock_add_phys(), that registers regions in the 'physmem' memblock map if CONFIG_HAVE_MEMBLOCK_PHYS_MAP is set; otherwise, it is a nop
- memblock_is_physmem(), returns whether a physical address is classified as physical memory.

---
 include/linux/memblock.h | 10 ++++++++++
 mm/memblock.c            | 15 +++++++++++++++
 2 files changed, 25 insertions(+)
include/linux/memblock.h +10 -0
index e8cc45307f8f..d32fe838c6ca 100644
@@ -365,6 +365,16 @@ static inline unsigned long memblock_region_reserved_end_pfn(const struct memblo
 #define __initdata_memblock
 #endif
 
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+int memblock_add_phys(phys_addr_t base, phys_addr_t size);
+int memblock_is_physmem(phys_addr_t addr);
+#else
+static inline int memblock_add_phys(phys_addr_t base, phys_addr_t size)
+{
+	return 0;
+}
+#endif /* CONFIG_HAVE_MEMBLOCK_PHYS_MAP */
+
 #else
 static inline phys_addr_t memblock_alloc(phys_addr_t size, phys_addr_t align)
 {
mm/memblock.c +15 -0
index c27353beb260..107aa5ee2d7b 100644
@@ -586,6 +586,14 @@ int __init_memblock memblock_add(phys_addr_t base, phys_addr_t size)
 				   MAX_NUMNODES, 0);
 }
 
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+int __init_memblock memblock_add_phys(phys_addr_t base, phys_addr_t size)
+{
+	return memblock_add_range(&memblock.physmem, base, size,
+				  MAX_NUMNODES, 0);
+}
+#endif
+
 /**
  * memblock_isolate_range - isolate given range into disjoint memblocks
  * @type: memblock type to isolate range for
@@ -1398,6 +1406,13 @@ int __init_memblock memblock_is_memory(phys_addr_t addr)
 	return memblock_search(&memblock.memory, addr) != -1;
 }
 
+#ifdef CONFIG_HAVE_MEMBLOCK_PHYS_MAP
+int __init_memblock memblock_is_physmem(phys_addr_t addr)
+{
+	return memblock_search(&memblock.physmem, addr) != -1;
+}
+#endif
+
 #ifdef CONFIG_HAVE_MEMBLOCK_NODE_MAP
 int __init_memblock memblock_search_pfn_nid(unsigned long pfn,
 			 unsigned long *start_pfn, unsigned long *end_pfn)
Signature · 6 lines
1.8.3.2

--
To unsubscribe from this list: send the line "unsubscribe linux-efi" in
the body of a message to majordomo at vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Signature · 1 line
Matt Fleming, Intel Open Source Technology Center
#13 lore raw

PATCH 5/8 of: fdt: register physmem in early_init_dt_scan_memory()

In reply to Ard Biesheuvel

This patch changes early_init_dt_scan_memory() so that all memory covered by DT memory nodes is registered in the 'physmem' memblock table if CONFIG_HAVE_MEMBLOCK_PHYS_MAP is enabled.

---
 drivers/of/fdt.c | 1 +
 1 file changed, 1 insertion(+)
drivers/of/fdt.c +1 -0
index 510074226d57..6e59c2168536 100644
@@ -894,6 +894,7 @@ int __init early_init_dt_scan_memory(unsigned long node, const char *uname,
 		    (unsigned long long)size);
 
 		early_init_dt_add_memory_arch(base, size);
+		memblock_add_phys(base, size);
 	}
 
 	return 0;
Signature · 1 line
1.8.3.2
#14 lore raw

PATCH 6/8 arm64/efi: register physmem in reserve_regions()

In reply to Ard Biesheuvel

After traversing the UEFI memory map to discover the regions that are backed by normal RAM, register the resulting minimal memory map into the physmem memblock table.

---
 arch/arm64/kernel/efi.c | 9 +++++++++
 1 file changed, 9 insertions(+)
arch/arm64/kernel/efi.c +9 -0
index ba5fe66c3634..b1b816ecf3b3 100644
@@ -155,6 +155,7 @@ static __init void reserve_regions(void)
 {
 	efi_memory_desc_t *md;
 	u64 paddr, npages, size;
+	struct memblock_region *r;
 
 	if (uefi_debug)
 		pr_info("Processing EFI memory map:\n");
@@ -187,6 +188,14 @@ static __init void reserve_regions(void)
 			pr_cont("\n");
 	}
 
+	/*
+	 * After memblock has stitched all the regions together, copy the
+	 * resulting map of physical memory from the memory memblock table into
+	 * the physmem memblock table.
+	 */
+	for_each_memblock(memory, r)
+		memblock_add_phys(r->base, r->size);
+
 	set_bit(EFI_MEMMAP, &efi.flags);
 }
 
Signature · 1 line
1.8.3.2
#15 lore raw

PATCH 7/8 arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling

In reply to Ard Biesheuvel

The 'physmem' memblock table allows us to classify memory as RAM even if it is not covered by the ordinary 'memory' memblock table.

Under CONFIG_STRICT_DEVMEM, we can use this to:
- allow read-only access to parts of RAM that are not considered memory by the kernel, this is mainly intended for exposing UEFI configuration tables such as SMBIOS to userland;
- avoid using non-cached mappings for those parts of RAM, as it may result in mismatched attributes.

---
 arch/arm64/Kconfig   |  1 +
 arch/arm64/mm/mmap.c |  2 +-
 arch/arm64/mm/mmu.c  | 15 ++++++++++++++-
 3 files changed, 16 insertions(+), 2 deletions(-)
arch/arm64/Kconfig +1 -0
index b1f9a20a3677..86902f8d8e36 100644
@@ -60,6 +60,7 @@ config ARM64
 	select HAVE_GENERIC_DMA_COHERENT
 	select HAVE_HW_BREAKPOINT if PERF_EVENTS
 	select HAVE_MEMBLOCK
+	select HAVE_MEMBLOCK_PHYS_MAP
 	select HAVE_PATA_PLATFORM
 	select HAVE_PERF_EVENTS
 	select HAVE_PERF_REGS
arch/arm64/mm/mmap.c +1 -1
index 54922d1275b8..9f558ab41f39 100644
@@ -126,7 +126,7 @@ int devmem_is_allowed(unsigned long pfn)
 {
 	if (iomem_is_exclusive(pfn << PAGE_SHIFT))
 		return 0;
-	if (!page_is_ram(pfn))
+	if (!pfn_valid(pfn))
 		return 1;
 	return 0;
 }
arch/arm64/mm/mmu.c +14 -1
index 328638548871..083be3de1a87 100644
@@ -122,7 +122,7 @@ early_param("cachepolicy", early_cachepolicy);
 pgprot_t phys_mem_access_prot(struct file *file, unsigned long pfn,
 			      unsigned long size, pgprot_t vma_prot)
 {
-	if (!pfn_valid(pfn))
+	if (!memblock_is_physmem(PFN_PHYS(pfn)))
 		return pgprot_noncached(vma_prot);
 	else if (file->f_flags & O_SYNC)
 		return pgprot_writecombine(vma_prot);
@@ -130,6 +130,19 @@ pgprot_t phys_mem_access_prot(struct file *file, unsigned long pfn,
 }
 EXPORT_SYMBOL(phys_mem_access_prot);
 
+/*
+ * This definition of phys_mem_access_prot_allowed() overrides
+ * the __weak definition in drivers/char/mem.c
+ */
+int phys_mem_access_prot_allowed(struct file *file, unsigned long pfn,
+				 unsigned long size, pgprot_t *prot)
+{
+	/* Disallow read-write access to system RAM */
+	if (memblock_is_physmem(PFN_PHYS(pfn)) && pgprot_val(*prot) & PTE_WRITE)
+		return 0;
+	return 1;
+}
+
 static void __init *early_alloc(unsigned long sz)
 {
 	void *ptr = __va(memblock_alloc(sz, sz));
Signature · 1 line
1.8.3.2
#16 lore raw

PATCH 7/8 arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling

Quoted 9 lines · Ard Biesheuvel

The 'physmem' memblock table allows us to classify memory as RAM even if it is not covered by the ordinary 'memory' memblock table.

Under CONFIG_STRICT_DEVMEM, we can use this to:
- allow read-only access to parts of RAM that are not considered memory by the kernel, this is mainly intended for exposing UEFI configuration tables such as SMBIOS to userland;
- avoid using non-cached mappings for those parts of RAM, as it may result in mismatched attributes.

Looks fine to me assuming that the rest of the series is ok:

Will

Quoted 69 lines
---
 arch/arm64/Kconfig   |  1 +
 arch/arm64/mm/mmap.c |  2 +-
 arch/arm64/mm/mmu.c  | 15 ++++++++++++++-
 3 files changed, 16 insertions(+), 2 deletions(-)
arch/arm64/Kconfig +1 -0
index b1f9a20a3677..86902f8d8e36 100644
@@ -60,6 +60,7 @@ config ARM64
 	select HAVE_GENERIC_DMA_COHERENT
 	select HAVE_HW_BREAKPOINT if PERF_EVENTS
 	select HAVE_MEMBLOCK
+	select HAVE_MEMBLOCK_PHYS_MAP
 	select HAVE_PATA_PLATFORM
 	select HAVE_PERF_EVENTS
 	select HAVE_PERF_REGS
arch/arm64/mm/mmap.c +1 -1
index 54922d1275b8..9f558ab41f39 100644
@@ -126,7 +126,7 @@ int devmem_is_allowed(unsigned long pfn)
 {
 	if (iomem_is_exclusive(pfn << PAGE_SHIFT))
 		return 0;
-	if (!page_is_ram(pfn))
+	if (!pfn_valid(pfn))
 		return 1;
 	return 0;
 }
arch/arm64/mm/mmu.c +14 -1
index 328638548871..083be3de1a87 100644
@@ -122,7 +122,7 @@ early_param("cachepolicy", early_cachepolicy);
 pgprot_t phys_mem_access_prot(struct file *file, unsigned long pfn,
 			      unsigned long size, pgprot_t vma_prot)
 {
-	if (!pfn_valid(pfn))
+	if (!memblock_is_physmem(PFN_PHYS(pfn)))
 		return pgprot_noncached(vma_prot);
 	else if (file->f_flags & O_SYNC)
 		return pgprot_writecombine(vma_prot);
@@ -130,6 +130,19 @@ pgprot_t phys_mem_access_prot(struct file *file, unsigned long pfn,
 }
 EXPORT_SYMBOL(phys_mem_access_prot);
 
+/*
+ * This definition of phys_mem_access_prot_allowed() overrides
+ * the __weak definition in drivers/char/mem.c
+ */
+int phys_mem_access_prot_allowed(struct file *file, unsigned long pfn,
+				 unsigned long size, pgprot_t *prot)
+{
+	/* Disallow read-write access to system RAM */
+	if (memblock_is_physmem(PFN_PHYS(pfn)) && pgprot_val(*prot) & PTE_WRITE)
+		return 0;
+	return 1;
+}
+
 static void __init *early_alloc(unsigned long sz)
 {
 	void *ptr = __va(memblock_alloc(sz, sz));
Signature · 1 line
1.8.3.2
#17 lore raw

PATCH 8/8 arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

In reply to Ard Biesheuvel

Now that we have the 'physmem' memblock table to keep track of physical RAM regions, we can start using memblock_remove() to eliminate UEFI reserved regions from the 'memory' memblock table and the kernel direct linear mapping entirely. This makes these regions inaccessible entirely, unless they are remapped explicitly by the UEFI Runtime Services layer, UEFI configuration table drivers or the ACPI layer.

---
 arch/arm64/kernel/efi.c | 22 ++++++++++++----------
 1 file changed, 12 insertions(+), 10 deletions(-)
arch/arm64/kernel/efi.c +12 -10
index b1b816ecf3b3..d0efd9df6216 100644
@@ -167,7 +167,7 @@ static __init void reserve_regions(void)
 		if (uefi_debug) {
 			char buf[64];
 
-			pr_info("  0x%012llx-0x%012llx %s",
+			pr_info("  0x%012llx-0x%012llx %s\n",
 				paddr, paddr + (npages << EFI_PAGE_SHIFT) - 1,
 				efi_md_typeattr_format(buf, sizeof(buf), md));
 		}
@@ -177,15 +177,6 @@ static __init void reserve_regions(void)
 
 		if (is_normal_ram(md))
 			early_init_dt_add_memory_arch(paddr, size);
-
-		if (is_reserve_region(md)) {
-			memblock_reserve(paddr, size);
-			if (uefi_debug)
-				pr_cont("*");
-		}
-
-		if (uefi_debug)
-			pr_cont("\n");
 	}
 
 	/*
@@ -196,7 +187,18 @@ static __init void reserve_regions(void)
 	for_each_memblock(memory, r)
 		memblock_add_phys(r->base, r->size);
 
+	for_each_efi_memory_desc(&memmap, md) {
+		if (is_reserve_region(md)) {
+			paddr = md->phys_addr;
+			npages = md->num_pages;
+			memrange_efi_to_native(&paddr, &npages);
+			memblock_remove(paddr, npages << PAGE_SHIFT);
+		}
+	}
+
 	set_bit(EFI_MEMMAP, &efi.flags);
+	if (uefi_debug)
+		__memblock_dump_all();
 }
 
 void __init efi_init(void)
Signature · 1 line
1.8.3.2
#18 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

In reply to Ard Biesheuvel
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Ard, It is much cleaner for this splitting.

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Thanks
Dave

#19 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

Thanks,
Ard.

#20 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 6 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

I will do some test later along with the stable mapping stuff.

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

Thanks
Dave

#21 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 70 lines · Dave Young
Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 1 line
Quoted 8 lines
Quoted 5 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

I will do some test later along with the stable mapping stuff.

Cheers.

Quoted 6 lines

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

No clues, unfortunately. The memory map is not used after early boot, so it may be getting clobbered at any point between the first boot and the second boot.

Signature · 1 line
Ard.
#22 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 71 lines · Ard Biesheuvel
Quoted 70 lines · Dave Young
Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 1 line
Quoted 7 lines
Quoted 7 lines
Quoted 5 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

I will do some test later along with the stable mapping stuff.

The whole patchset works well without the last patch.

I found that patch 8/8 caused system boot hangs very early. Just after stub print something about virtmap..

Any idea about it? I tested your patches upon 3.18.

Quoted 11 lines
Quoted 1 line

Cheers.

Quoted 6 lines

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

Quoted 3 lines

No clues, unfortunately. The memory map is not used after early boot, so it may be getting clobbered at any point between the first boot and the second boot.

It was caused by uefi sys table/mmap start addresses changes.
I generate dtb from acpi=off boot /proc/device-tree, and use the dtb for kexec boot, but seems mmap addresses changes sometimes.

Do you know have plan or status in Linaro for exporting dtb for acpi booting?

Thanks
Dave

#23 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 78 lines · Dave Young
Quoted 77 lines · Ard Biesheuvel
Quoted 76 lines · Dave Young
Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 6 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

Quoted 7 lines
Quoted 1 line
Quoted 1 line

I will do some test later along with the stable mapping stuff.

The whole patchset works well without the last patch.

I found that patch 8/8 caused system boot hangs very early. Just after stub print something about virtmap..

Which platform is this?
Do you have earlycon enabled?

Quoted 2 lines

Any idea about it? I tested your patches upon 3.18.

I suppose you tested both the virtmap series and this one, but did you also take the 3.19 changes we did for UEFI? Not sure it would make a difference, though.

Quoted 11 lines
Quoted 10 lines
Quoted 6 lines

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

No clues, unfortunately. The memory map is not used after early boot, so it may be getting clobbered at any point between the first boot and the second boot.

Quoted 6 lines

It was caused by uefi sys table/mmap start addresses changes.
I generate dtb from acpi=off boot /proc/device-tree, and use the dtb for kexec boot, but seems mmap addresses changes sometimes.

Do you know have plan or status in Linaro for exporting dtb for acpi booting?

We have this patch upstream now

08d53aa58cb1 of/fdt: export fdt blob as /sys/firmware/fdt

which exports whatever FDT the kernel received from the bootloader or the EFI stub, regardless of whether the kernel uses DT or not.

Signature · 1 line
Ard.
#24 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 81 lines · Ard Biesheuvel
Quoted 80 lines · Dave Young
Quoted 78 lines · Ard Biesheuvel
Quoted 77 lines · Dave Young
Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 6 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

I will do some test later along with the stable mapping stuff.

Quoted 8 lines
Quoted 5 lines

The whole patchset works well without the last patch.

I found that patch 8/8 caused system boot hangs very early. Just after stub print something about virtmap..

Which platform is this?
Do you have earlycon enabled?

It is apm mustang, earlycon was enabled.

Quoted 7 lines
Quoted 3 lines

Any idea about it? I tested your patches upon 3.18.

I suppose you tested both the virtmap series and this one, but did you also take the 3.19 changes we did for UEFI? Not sure it would make a difference, though.

Yes, both virtmap series and this one, I did not take UEFI 3.19 changes, Which patchset do you have in mind? If no clue I will try rebase to test 3.19

Quoted 19 lines
Quoted 12 lines
Quoted 11 lines
Quoted 7 lines

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

No clues, unfortunately. The memory map is not used after early boot, so it may be getting clobbered at any point between the first boot and the second boot.

Quoted 6 lines

It was caused by uefi sys table/mmap start addresses changes.
I generate dtb from acpi=off boot /proc/device-tree, and use the dtb for kexec boot, but seems mmap addresses changes sometimes.

Do you know have plan or status in Linaro for exporting dtb for acpi booting?

Quoted 6 lines

We have this patch upstream now

08d53aa58cb1 of/fdt: export fdt blob as /sys/firmware/fdt

which exports whatever FDT the kernel received from the bootloader or the EFI stub, regardless of whether the kernel uses DT or not.

Great, will try.

Thanks
Dave

#25 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 84 lines · Dave Young
Quoted 83 lines · Ard Biesheuvel
Quoted 82 lines · Dave Young
Quoted 71 lines · Ard Biesheuvel
Quoted 70 lines · Dave Young
Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 1 line
Quoted 7 lines
Quoted 7 lines
Quoted 5 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

I will do some test later along with the stable mapping stuff.

The whole patchset works well without the last patch.

Quoted 9 lines
Quoted 6 lines
Quoted 3 lines

I found that patch 8/8 caused system boot hangs very early. Just after stub print something about virtmap..

Which platform is this?
Do you have earlycon enabled?

It is apm mustang, earlycon was enabled.

That's odd. reserve_regions() is called after uefi_init(), and the latter prints the EFI: string, so I don't think the patch should affect anything else before that either. Could you please double check if you do see the console enabled/disabled messages?

Quoted 11 lines
Quoted 7 lines
Quoted 3 lines

Any idea about it? I tested your patches upon 3.18.

I suppose you tested both the virtmap series and this one, but did you also take the 3.19 changes we did for UEFI? Not sure it would make a difference, though.

Yes, both virtmap series and this one, I did not take UEFI 3.19 changes, Which patchset do you have in mind? If no clue I will try rebase to test 3.19

Well, there is patch 61139eb04056bba69aeef6c481802c4ea028bf4d that changes the definition of is_reserve_region(), which may or may not be relevant. Other than that, I don't think any of those patches could make a difference here.

Quoted 30 lines
Quoted 19 lines
Quoted 12 lines
Quoted 11 lines
Quoted 7 lines

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

No clues, unfortunately. The memory map is not used after early boot, so it may be getting clobbered at any point between the first boot and the second boot.

Quoted 6 lines

It was caused by uefi sys table/mmap start addresses changes.
I generate dtb from acpi=off boot /proc/device-tree, and use the dtb for kexec boot, but seems mmap addresses changes sometimes.

Do you know have plan or status in Linaro for exporting dtb for acpi booting?

Quoted 6 lines

We have this patch upstream now

08d53aa58cb1 of/fdt: export fdt blob as /sys/firmware/fdt

which exports whatever FDT the kernel received from the bootloader or the EFI stub, regardless of whether the kernel uses DT or not.

Great, will try.

Thanks
Dave

#26 lore raw

cover arm64: improved memory map handling for /dev/mem, ACPI etc

Quoted 92 lines · Ard Biesheuvel
Quoted 91 lines · Dave Young
Quoted 89 lines · Ard Biesheuvel
Quoted 78 lines · Dave Young
Quoted 77 lines · Ard Biesheuvel
Quoted 76 lines · Dave Young
Quoted 57 lines · Ard Biesheuvel
Quoted 47 lines · Dave Young
Quoted 36 lines · Ard Biesheuvel

This series was split off from the UEFI virtmap for kexec series that I posted earlier today. The main purpose is to deal with the need to classify memory ranges as RAM or non-RAM in a consistent and comprehensive manner. This series applies on top of the other series.

Patch #1 avoids an early panic if the UEFI memory map is available but UEFI support itself fails to initialize. In this case, there is no need to panic early, and we have a better chance of being able to inform the user if we deal with this error condition at a later time.

Patch #2 adds iomem resource registration of UEFI memory regions. This is necessary because otherwise, drivers could potentially claim regions that are in active use by the firmware. This applies to both MMIO (NOR flash, RTC) and RAM ranges (runtime services code and data).

Patch #3-6 adds support to UEFI and non-UEFI code paths to record all memory known to the system in the 'physmem' memblock table (if enabled). This fulfils a need in the /dev/mem and (upcoming) ACPI layers to be able to classify ranges as being backed by normal RAM even if they are not covered by the 'memory' memblock table, and are hence not covered by the linear direct mapping. The physmem code is pre-existing code that only needs minor tweaking to be made suitable for this purpose.

Patch #7 enables the 'physmem' memblock table for arm64, and wires it into the handling of /dev/mem mappings, both to decide whether it should be mapped as MT_NORMAL, and whether read-write access can be allowed. (Non-RAM regions can be mapped read-write as long as they are not claimed by a driver in the iomem resource table. RAM regions can only be mapped read-only, and only if they are not covered by the 'memory' memblock table, and hence not covered by the linear mapping)

Finally, patch #8 changes the way the virtual memory map is handled by the early UEFI code. Specifically, it memblock_remove()s rather than _reserves() UEFI reserved RAM regions, so that they are removed entirely from the linear mapping.

Quoted 9 lines

Ard Biesheuvel (8):
arm64/efi: use UEFI memory map unconditionally if available arm64/efi: register UEFI reserved regions as iomem resources
memblock: add physmem to memblock_dump_all() output
memblock: introduce memblock_add_phys() and memblock_is_physmem()
of: fdt: register physmem in early_init_dt_scan_memory() arm64/efi: register physmem in reserve_regions()
arm64: use 'physmem' memblock to improve CONFIG_STRICT_DEVMEM handling arm64/efi: memblock_remove rather than _reserve UEFI reserved RAM

Quoted 2 lines

Ard, It is much cleaner for this splitting.

Thanks for having a look.

Quoted 3 lines

I wonder if some of them can become general code such as register reserved regions as iomem resources?

Quoted 7 lines

AFAICT, the x86 code adds reservations for such regions to the E820 memory map, which in turn is used to memblock_reserve() the actual memory. Also, sharing of the RTC is handled with a dedicated mutex in the runtime services wrapper code (and x86 does not even use the time related runtime services as they are broken on many firmware implementations) so blindly applying the same logic to x86 or ia64 would likely break stuff.

Ok, I think bootloader will pass the E820 ranges though it can not tell which region is for what.

Quoted 6 lines

Do you (or Mark) have any feedback on the utility of this series in the ACPI context? I failed to mention in the cover letter that memblock_is_physmem() now serves the purpose of page_is_ram(), i.e., whether a physical region is backed by a slice of RAM that was left out of the kernel's linear mapping.

Quoted 7 lines
Quoted 1 line
Quoted 1 line

I will do some test later along with the stable mapping stuff.

The whole patchset works well without the last patch.

I found that patch 8/8 caused system boot hangs very early. Just after stub print something about virtmap..

Which platform is this?
Do you have earlycon enabled?

Quoted 7 lines
Quoted 2 lines

It is apm mustang, earlycon was enabled.

That's odd. reserve_regions() is called after uefi_init(), and the latter prints the EFI: string, so I don't think the patch should affect anything else before that either. Could you please double check if you do see the console enabled/disabled messages?

Will check, but I did not change the kernel params..

Quoted 9 lines
Quoted 9 lines
Quoted 8 lines
Quoted 4 lines

Any idea about it? I tested your patches upon 3.18.

I suppose you tested both the virtmap series and this one, but did you also take the 3.19 changes we did for UEFI? Not sure it would make a difference, though.

Quoted 8 lines
Quoted 3 lines

Yes, both virtmap series and this one, I did not take UEFI 3.19 changes, Which patchset do you have in mind? If no clue I will try rebase to test 3.19

Well, there is patch 61139eb04056bba69aeef6c481802c4ea028bf4d that changes the definition of is_reserve_region(), which may or may not be relevant. Other than that, I don't think any of those patches could make a difference here.

Ok, I have no machine on hand currently, will do some debugging once I have one.

Quoted 31 lines
Quoted 31 lines
Quoted 20 lines
Quoted 13 lines
Quoted 9 lines
Quoted 8 lines

BTW, with previous stable mapping patches on modified 3.18 tree kexec kernel panics because of damaged efi mempry map arrays. It contains some random value instead of right addresses so that virt_to_phys return same value for vendor field. Will do more debugging maybe I missed something. Any clue for debugging above issue will be appreciated.

Quoted 3 lines

No clues, unfortunately. The memory map is not used after early boot, so it may be getting clobbered at any point between the first boot and the second boot.

Quoted 6 lines

It was caused by uefi sys table/mmap start addresses changes.
I generate dtb from acpi=off boot /proc/device-tree, and use the dtb for kexec boot, but seems mmap addresses changes sometimes.

Do you know have plan or status in Linaro for exporting dtb for acpi booting?

Quoted 6 lines

We have this patch upstream now

08d53aa58cb1 of/fdt: export fdt blob as /sys/firmware/fdt

which exports whatever FDT the kernel received from the bootloader or the EFI stub, regardless of whether the kernel uses DT or not.

Great, will try.

Thanks
Dave