summaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorAhmad Fatoum <a.fatoum@pengutronix.de>2023-05-22 07:28:29 +0200
committerSascha Hauer <s.hauer@pengutronix.de>2023-05-23 09:26:09 +0200
commit417611441df1780cde77d837e65900c7b14d3164 (patch)
tree623c3552160a4fc8cb03c938ecdd07c2ff48934e /drivers
parent4ad24201d89a4497c156ba4982ab24d7f4bcf4b4 (diff)
downloadbarebox-417611441df1780cde77d837e65900c7b14d3164.tar.gz
barebox-417611441df1780cde77d837e65900c7b14d3164.tar.xz
of: platform: remap memory when encountering virtual-reg property
Quoting the Device Tree specification v0.4-rc1[1]: The virtual-reg property specifies an effective address that maps to the first physical address specified in the reg property of the device node. This property enables boot programs to provide client programs with virtual- to-physical mappings that have been set up. The only upstream use of this device tree property are some PowerPC device trees that use it to find the virtual address of the early UART. Let's start handling this property in barebox as well by remapping the device to start at virtual-reg. [1]: https://github.com/devicetree-org/devicetree-specification/releases/tag/v0.4-rc1 Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de> Link: https://lore.barebox.org/20230522052835.1039143-6-a.fatoum@pengutronix.de Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/mtd/nor/cfi_flash.c5
-rw-r--r--drivers/of/platform.c20
2 files changed, 24 insertions, 1 deletions
diff --git a/drivers/mtd/nor/cfi_flash.c b/drivers/mtd/nor/cfi_flash.c
index 8b5302d7a7..f1555a72a4 100644
--- a/drivers/mtd/nor/cfi_flash.c
+++ b/drivers/mtd/nor/cfi_flash.c
@@ -965,7 +965,10 @@ static int cfi_probe_one(struct flash_info *info, int num)
return PTR_ERR(iores);
info->base = IOMEM(iores->start);
- /* TODO: either remap memory region or disable NULL pointer page */
+ /*
+ * Platforms hitting this should remap memory region, e.g. via virtual-reg
+ * device tree property or disable MMU.
+ */
if (IS_ENABLED(CONFIG_MMU) && iores->start == 0)
return -EPERM;
diff --git a/drivers/of/platform.c b/drivers/of/platform.c
index 23b8fa7934..ab73762932 100644
--- a/drivers/of/platform.c
+++ b/drivers/of/platform.c
@@ -12,6 +12,7 @@
#include <of.h>
#include <of_address.h>
#include <linux/amba/bus.h>
+#include <mmu.h>
/**
* of_find_device_by_node - Find the platform_device associated with a node
@@ -145,6 +146,7 @@ struct device *of_platform_device_create(struct device_node *np,
struct resource *res = NULL, temp_res;
resource_size_t resinval;
int i, ret, num_reg = 0;
+ u32 virt;
if (!of_device_is_available(np))
return NULL;
@@ -186,6 +188,24 @@ struct device *of_platform_device_create(struct device_node *np,
of_dma_configure(dev, np);
+ if (num_reg && !of_property_read_u32(np, "virtual-reg", &virt)) {
+ resource_size_t remap_offset = virt - res[0].start;
+
+ for (i = 0; i < num_reg; i++) {
+ void *new_virt = (void *)res[i].start + remap_offset;
+ resource_size_t size = resource_size(&res[i]);
+
+ ret = arch_remap_range(new_virt, res[i].start, size, MAP_UNCACHED);
+ if (!ret) {
+ debug("%s: remap device %s resource %d: %pa -> 0x%p\n",
+ __func__, dev_name(dev), i, &res[i].start, new_virt);
+
+ res[i].start = (resource_size_t)new_virt;
+ res[i].end = res[i].start + size - 1;
+ }
+ }
+ }
+
resinval = (-1);
debug("%s: register device %s, io=%pa\n",