[PATCH v2 1/2] sunxi: restore modified memory

Andrey Skvortsov andrej.skvortzov at gmail.com
Wed Dec 6 20:06:32 CET 2023


On A64 with 2G of RAM words at following addresses were modified with
'aa55aa55' value:
 - 50000000
 - 60000000
 - 84000000
 - 88000000
 - 90000000
 - A0000000
 - A0000200

That made harder to pick memory range for persistent storage in RAM.

Signed-off-by: Andrey Skvortsov <andrej.skvortzov at gmail.com>
---
 arch/arm/mach-sunxi/dram_helpers.c  | 16 ++++++++++++++--
 arch/arm/mach-sunxi/dram_sunxi_dw.c | 16 ++++++++++++++--
 2 files changed, 28 insertions(+), 4 deletions(-)

diff --git a/arch/arm/mach-sunxi/dram_helpers.c b/arch/arm/mach-sunxi/dram_helpers.c
index cdf2750f1c..61a6da84e3 100644
--- a/arch/arm/mach-sunxi/dram_helpers.c
+++ b/arch/arm/mach-sunxi/dram_helpers.c
@@ -32,12 +32,24 @@ void mctl_await_completion(u32 *reg, u32 mask, u32 val)
 #ifndef CONFIG_MACH_SUNIV
 bool mctl_mem_matches(u32 offset)
 {
+	u32 val_base;
+	u32 val_offset;
+	bool ret;
+
+	/* Save original values */
+	val_base = readl(CFG_SYS_SDRAM_BASE);
+	val_offset = readl((ulong)CFG_SYS_SDRAM_BASE + offset);
+
 	/* Try to write different values to RAM at two addresses */
 	writel(0, CFG_SYS_SDRAM_BASE);
 	writel(0xaa55aa55, (ulong)CFG_SYS_SDRAM_BASE + offset);
 	dsb();
 	/* Check if the same value is actually observed when reading back */
-	return readl(CFG_SYS_SDRAM_BASE) ==
-	       readl((ulong)CFG_SYS_SDRAM_BASE + offset);
+	ret = readl(CFG_SYS_SDRAM_BASE) == readl((ulong)CFG_SYS_SDRAM_BASE + offset);
+
+	/* Restore original values */
+	writel(val_base, CFG_SYS_SDRAM_BASE);
+	writel(val_offset, (ulong)CFG_SYS_SDRAM_BASE + offset);
+	return ret;
 }
 #endif
diff --git a/arch/arm/mach-sunxi/dram_sunxi_dw.c b/arch/arm/mach-sunxi/dram_sunxi_dw.c
index 9382d3d0be..905a43c918 100644
--- a/arch/arm/mach-sunxi/dram_sunxi_dw.c
+++ b/arch/arm/mach-sunxi/dram_sunxi_dw.c
@@ -657,13 +657,25 @@ static int mctl_channel_init(uint16_t socid, struct dram_para *para)
  */
 static bool mctl_mem_matches_base(u32 offset, ulong base)
 {
+	u32 val_base;
+	u32 val_offset;
+	bool ret;
+
+	/* Save original values */
+	val_base = readl(base);
+	val_offset = readl((ulong)base + offset);
+
 	/* Try to write different values to RAM at two addresses */
 	writel(0, base);
 	writel(0xaa55aa55, base + offset);
 	dsb();
 	/* Check if the same value is actually observed when reading back */
-	return readl(base) ==
-	       readl(base + offset);
+	ret = readl(base) == readl(base + offset);
+
+	/* Restore original values */
+	writel(val_base, base);
+	writel(val_offset, (ulong)base + offset);
+	return ret;
 }
 
 static void mctl_auto_detect_dram_size_rank(uint16_t socid, struct dram_para *para, ulong base, struct rank_para *rank)
-- 
2.42.0



More information about the U-Boot mailing list