diff options
| author | Tom Rini <[email protected]> | 2026-06-24 15:39:29 -0600 |
|---|---|---|
| committer | Tom Rini <[email protected]> | 2026-06-24 18:13:25 -0600 |
| commit | 19eafbadf20f56c1a24abe6b5e8774e776894261 (patch) | |
| tree | 1ece0528f796fb129f2a7d6b18cf14db130b1150 /drivers | |
| parent | 47e9c542ee032e89f556adc73c2aeff3acb0e5a9 (diff) | |
| parent | fb537c85bca0e3d29a62fe119181bf1744b8c91a (diff) | |
Merge patch series "Relocate U-Boot in the last bank"
Ilias Apalodimas <[email protected]> says:
There was a discussion recently on the mailing lists regarding our
management of memory above ram_top [0]. The tl;dr is that we have two problems.
The first one is that U-Boot always relocates to the top of the first available
bank unless there's special board code to sidestep that. The second is we don't
successfully deal with devices that can only do 32-bit DMA.
This patch series deals with the first problem by adding a Kconfig option
allowing platforms to relocate to the top of the last discovered bank.
It's worth noting that this is easily testable with QEMU
qemu-system-aarch64 -m 8192 -smp 2 -nographic -cpu cortex-a57 \
-machine virt,secure=off \
-bios u-boot.bin \
-device virtio-rng-pci \
-drive id=os,if=none,file="$image" \
-device virtio-blk-device,drive=os \
-object memory-backend-ram,id=ram0,size=4G \
-object memory-backend-ram,id=ram1,size=4G \
-numa node,memdev=ram0 \
-numa node,memdev=ram1
# RELOC_ADDR_TOP not set
Hit any key to stop autoboot: 0
=> bdinfo
[...]
relocaddr = 0x000000013f66c000
reloc off = 0x000000013f66c000
[...]
lmb_dump_all:
memory.count = 0x1
memory[0] [0x40000000-0x23fffffff], 0x200000000 bytes, flags: none
reserved.count = 0x2
reserved[0] [0x13d507000-0x13d509fff], 0x3000 bytes, flags: no-notify, no-overwrite
reserved[1] [0x13d50aff0-0x23fffffff], 0x102af5010 bytes, flags: no-overwrite
devicetree = board
[...]
TLB addr = 0x000000013ffe0000
irq_sp = 0x000000013e50aff0
sp start = 0x000000013e50aff0
Early malloc usage: e88 / 2000
=>
# RELOC_ADDR_TOP enabled
=> bdinfo
[...]
relocaddr = 0x000000023f66c000
reloc off = 0x000000023f66c000
[...]
lmb_dump_all:
memory.count = 0x1
memory[0] [0x40000000-0x23fffffff], 0x200000000 bytes, flags: none
reserved.count = 0x2
reserved[0] [0x23d507000-0x23d509fff], 0x3000 bytes, flags: no-notify, no-overwrite
reserved[1] [0x23d50aff0-0x23fffffff], 0x2af5010 bytes, flags: no-overwrite
devicetree = board
[...]
TLB addr = 0x000000023ffe0000
irq_sp = 0x000000023e50aff0
sp start = 0x000000023e50aff0
Early malloc usage: e88 / 2000
=>
[0] https://lore.kernel.org/u-boot/CAC_iWjKFAzpj3B_MEW7-dnOrcAV-rfkhXXo8Bv0KgLNP2VJxRA@mail.gmail.com/
Link: https://lore.kernel.org/r/[email protected]
Diffstat (limited to 'drivers')
| -rw-r--r-- | drivers/bootcount/bootcount_ram.c | 4 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_agilex.c | 4 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_agilex5.c | 18 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_agilex7m.c | 4 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_arria10.c | 12 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_n5x.c | 4 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_s10.c | 4 | ||||
| -rw-r--r-- | drivers/ddr/altera/sdram_soc64.c | 28 | ||||
| -rw-r--r-- | drivers/mmc/mvebu_mmc.c | 4 | ||||
| -rw-r--r-- | drivers/net/mvgbe.c | 4 | ||||
| -rw-r--r-- | drivers/pci/pci-uclass.c | 8 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-marvell.c | 4 | ||||
| -rw-r--r-- | drivers/video/meson/meson_vpu.c | 8 | ||||
| -rw-r--r-- | drivers/video/sunxi/sunxi_de2.c | 2 | ||||
| -rw-r--r-- | drivers/video/sunxi/sunxi_display.c | 2 |
15 files changed, 55 insertions, 55 deletions
diff --git a/drivers/bootcount/bootcount_ram.c b/drivers/bootcount/bootcount_ram.c index 33e157b865a..f726d9ab016 100644 --- a/drivers/bootcount/bootcount_ram.c +++ b/drivers/bootcount/bootcount_ram.c @@ -27,7 +27,7 @@ void bootcount_store(ulong a) int i; for (i = 0; i < CONFIG_NR_DRAM_BANKS; i++) - size += gd->bd->bi_dram[i].size; + size += gd->dram[i].size; save_addr = (ulong *)(size - BOOTCOUNT_ADDR); writel(a, save_addr); writel(CONFIG_SYS_BOOTCOUNT_MAGIC, &save_addr[1]); @@ -50,7 +50,7 @@ ulong bootcount_load(void) int i, tmp; for (i = 0; i < CONFIG_NR_DRAM_BANKS; i++) - size += gd->bd->bi_dram[i].size; + size += gd->dram[i].size; save_addr = (ulong *)(size - BOOTCOUNT_ADDR); counter = readl(&save_addr[0]); diff --git a/drivers/ddr/altera/sdram_agilex.c b/drivers/ddr/altera/sdram_agilex.c index b36a765a5de..2d2b72cf766 100644 --- a/drivers/ddr/altera/sdram_agilex.c +++ b/drivers/ddr/altera/sdram_agilex.c @@ -104,7 +104,7 @@ int sdram_mmr_init_full(struct udevice *dev) /* Get bank configuration from devicetree */ ret = fdtdec_decode_ram_size(gd->fdt_blob, NULL, 0, NULL, - (phys_size_t *)&gd->ram_size, &bd); + (phys_size_t *)&gd->ram_size, gd); if (ret) { puts("DDR: Failed to decode memory node\n"); return -ENXIO; @@ -158,7 +158,7 @@ int sdram_mmr_init_full(struct udevice *dev) sdram_set_firewall(&bd); - priv->info.base = bd.bi_dram[0].start; + priv->info.base = gd->dram[0].start; priv->info.size = gd->ram_size; debug("DDR: HMC init success\n"); diff --git a/drivers/ddr/altera/sdram_agilex5.c b/drivers/ddr/altera/sdram_agilex5.c index ee66c72157a..d14e4bc5dcc 100644 --- a/drivers/ddr/altera/sdram_agilex5.c +++ b/drivers/ddr/altera/sdram_agilex5.c @@ -302,7 +302,7 @@ int sdram_mmr_init_full(struct udevice *dev) /* Get bank configuration from devicetree */ ret = fdtdec_decode_ram_size(gd->fdt_blob, NULL, 0, NULL, - (phys_size_t *)&gd->ram_size, gd->bd); + (phys_size_t *)&gd->ram_size, gd); if (ret) { puts("DDR: Failed to decode memory node\n"); ret = -ENXIO; @@ -345,19 +345,19 @@ int sdram_mmr_init_full(struct udevice *dev) for (i = 0; i < config_dram_banks; i++) { remaining_size = hw_size - size_counter; if (remaining_size <= dram_bank_info[i].max_size) { - gd->bd->bi_dram[i].start = dram_bank_info[i].start; - gd->bd->bi_dram[i].size = remaining_size; + gd->dram[i].start = dram_bank_info[i].start; + gd->dram[i].size = remaining_size; debug("Memory bank[%d] Starting address: 0x%llx size: 0x%llx\n", - i, gd->bd->bi_dram[i].start, gd->bd->bi_dram[i].size); + i, gd->dram[i].start, gd->dram[i].size); break; } - gd->bd->bi_dram[i].start = dram_bank_info[i].start; - gd->bd->bi_dram[i].size = dram_bank_info[i].max_size; + gd->dram[i].start = dram_bank_info[i].start; + gd->dram[i].size = dram_bank_info[i].max_size; debug("Memory bank[%d] Starting address: 0x%llx size: 0x%llx\n", - i, gd->bd->bi_dram[i].start, gd->bd->bi_dram[i].size); - size_counter += gd->bd->bi_dram[i].size; + i, gd->dram[i].start, gd->dram[i].size); + size_counter += gd->dram[i].size; } gd->ram_size = hw_size; @@ -408,7 +408,7 @@ int sdram_mmr_init_full(struct udevice *dev) printf("DDR: firewall init success\n"); - priv->info.base = gd->bd->bi_dram[0].start; + priv->info.base = gd->dram[0].start; priv->info.size = gd->ram_size; /* Ending DDR driver initialization success tracking */ diff --git a/drivers/ddr/altera/sdram_agilex7m.c b/drivers/ddr/altera/sdram_agilex7m.c index 9b3cc5c7b86..e4d522202d8 100644 --- a/drivers/ddr/altera/sdram_agilex7m.c +++ b/drivers/ddr/altera/sdram_agilex7m.c @@ -375,7 +375,7 @@ int sdram_mmr_init_full(struct udevice *dev) /* Get bank configuration from devicetree */ ret = fdtdec_decode_ram_size(gd->fdt_blob, NULL, 0, NULL, - (phys_size_t *)&gd->ram_size, &bd); + (phys_size_t *)&gd->ram_size, gd); if (ret) { printf("%s: Failed to decode memory node\n", memory_type_in_use(dev)); @@ -484,7 +484,7 @@ int sdram_mmr_init_full(struct udevice *dev) printf("%s: firewall init success\n", (is_ddr_in_use(dev) ? io96b_ctrl->ddr_type : "HBM")); - priv->info.base = bd.bi_dram[0].start; + priv->info.base = gd->dram[0].start; priv->info.size = gd->ram_size; /* Ending DDR driver initialization success tracking */ diff --git a/drivers/ddr/altera/sdram_arria10.c b/drivers/ddr/altera/sdram_arria10.c index c281f711fdf..9cc809b8001 100644 --- a/drivers/ddr/altera/sdram_arria10.c +++ b/drivers/ddr/altera/sdram_arria10.c @@ -674,9 +674,9 @@ static void sdram_size_check(void) debug("DDR: Running SDRAM size sanity check\n"); - ram_check = get_ram_size((long *)gd->bd->bi_dram[0].start, - gd->bd->bi_dram[0].size); - if (ram_check != gd->bd->bi_dram[0].size) { + ram_check = get_ram_size((long *)gd->dram[0].start, + gd->dram[0].size); + if (ram_check != gd->dram[0].size) { puts("DDR: SDRAM size check failed!\n"); hang(); } @@ -719,14 +719,14 @@ int ddr_calibration_sequence(void) /* setup the dram info within bd */ dram_init_banksize(); - if (gd->ram_size != gd->bd->bi_dram[0].size) { + if (gd->ram_size != gd->dram[0].size) { printf("DDR: Warning: DRAM size from device tree (%ld MiB)\n", - gd->bd->bi_dram[0].size >> 20); + gd->dram[0].size >> 20); printf(" mismatch with hardware (%ld MiB).\n", gd->ram_size >> 20); } - if (gd->bd->bi_dram[0].size > gd->ram_size) { + if (gd->dram[0].size > gd->ram_size) { printf("DDR: Error: DRAM size from device tree is greater\n"); printf(" than hardware size.\n"); hang(); diff --git a/drivers/ddr/altera/sdram_n5x.c b/drivers/ddr/altera/sdram_n5x.c index 17ec6afa82b..900d4f59989 100644 --- a/drivers/ddr/altera/sdram_n5x.c +++ b/drivers/ddr/altera/sdram_n5x.c @@ -2279,7 +2279,7 @@ int sdram_mmr_init_full(struct udevice *dev) /* Get bank configuration from devicetree */ ret = fdtdec_decode_ram_size(gd->fdt_blob, NULL, 0, NULL, - (phys_size_t *)&gd->ram_size, &bd); + (phys_size_t *)&gd->ram_size, gd); if (ret) { debug("%s: Failed to decode memory node\n", __func__); return -1; @@ -2287,7 +2287,7 @@ int sdram_mmr_init_full(struct udevice *dev) printf("DDR: %lld MiB\n", gd->ram_size >> 20); - priv->info.base = bd.bi_dram[0].start; + priv->info.base = gd->dram[0].start; priv->info.size = gd->ram_size; sdram_size_check(&bd); diff --git a/drivers/ddr/altera/sdram_s10.c b/drivers/ddr/altera/sdram_s10.c index 4ac4c79e0ac..6664090f86a 100644 --- a/drivers/ddr/altera/sdram_s10.c +++ b/drivers/ddr/altera/sdram_s10.c @@ -285,7 +285,7 @@ int sdram_mmr_init_full(struct udevice *dev) /* Get bank configuration from devicetree */ ret = fdtdec_decode_ram_size(gd->fdt_blob, NULL, 0, NULL, - (phys_size_t *)&gd->ram_size, &bd); + (phys_size_t *)&gd->ram_size, gd); if (ret) { puts("DDR: Failed to decode memory node\n"); return -1; @@ -328,7 +328,7 @@ int sdram_mmr_init_full(struct udevice *dev) sdram_size_check(&bd); - priv->info.base = bd.bi_dram[0].start; + priv->info.base = gd->dram[0].start; priv->info.size = gd->ram_size; debug("DDR: HMC init success\n"); diff --git a/drivers/ddr/altera/sdram_soc64.c b/drivers/ddr/altera/sdram_soc64.c index 8ee7049b164..93df3d1812a 100644 --- a/drivers/ddr/altera/sdram_soc64.c +++ b/drivers/ddr/altera/sdram_soc64.c @@ -150,8 +150,8 @@ void sdram_init_ecc_bits(struct bd_info *bd) icache_enable(); - start_addr = bd->bi_dram[0].start; - size = bd->bi_dram[0].size; + start_addr = gd->dram[0].start; + size = gd->dram[0].size; /* Initialize small block for page table */ memset((void *)start_addr, 0, PGTABLE_SIZE + PGTABLE_OFF); @@ -174,8 +174,8 @@ void sdram_init_ecc_bits(struct bd_info *bd) if (bank >= CONFIG_NR_DRAM_BANKS) break; - start_addr = bd->bi_dram[bank].start; - size = bd->bi_dram[bank].size; + start_addr = gd->dram[bank].start; + size = gd->dram[bank].size; } dcache_disable(); @@ -198,12 +198,12 @@ void sdram_size_check(struct bd_info *bd) phys_addr_t start = 0; phys_size_t remaining_size; - start = bd->bi_dram[bank].start; - remaining_size = bd->bi_dram[bank].size; + start = gd->dram[bank].start; + remaining_size = gd->dram[bank].size; debug("Checking bank %d: start=0x%llx, size=0x%llx\n", bank, start, remaining_size); - while (ram_check < bd->bi_dram[bank].size) { + while (ram_check < gd->dram[bank].size) { phys_size_t size, test_size, detected_size; size = min((phys_addr_t)SZ_1G, (phys_addr_t)remaining_size); @@ -232,7 +232,7 @@ void sdram_size_check(struct bd_info *bd) } ram_check += detected_size; - remaining_size = bd->bi_dram[bank].size - ram_check; + remaining_size = gd->dram[bank].size - ram_check; } total_ram_check += ram_check; @@ -292,10 +292,10 @@ static void sdram_set_firewall_non_f2sdram(struct bd_info *bd) u32 lower, upper; for (i = 0; i < CONFIG_NR_DRAM_BANKS; i++) { - if (!bd->bi_dram[i].size) + if (!gd->dram[i].size) continue; - value = bd->bi_dram[i].start; + value = gd->dram[i].start; /* Keep first 1MB of SDRAM memory region as secure region when * using ATF flow, where the ATF code is located. @@ -322,7 +322,7 @@ static void sdram_set_firewall_non_f2sdram(struct bd_info *bd) (i * 4 * sizeof(u32))); /* Setting non-secure MPU limit and limit extended */ - value = bd->bi_dram[i].start + bd->bi_dram[i].size - 1; + value = gd->dram[i].start + gd->dram[i].size - 1; lower = lower_32_bits(value); upper = upper_32_bits(value); @@ -354,10 +354,10 @@ static void sdram_set_firewall_f2sdram(struct bd_info *bd) phys_size_t value; for (i = 0; i < CONFIG_NR_DRAM_BANKS; i++) { - if (!bd->bi_dram[i].size) + if (!gd->dram[i].size) continue; - value = bd->bi_dram[i].start; + value = gd->dram[i].start; /* Keep first 1MB of SDRAM memory region as secure region when * using ATF flow, where the ATF code is located. @@ -376,7 +376,7 @@ static void sdram_set_firewall_f2sdram(struct bd_info *bd) (i * 4 * sizeof(u32))); /* Setting limit and limit extended */ - value = bd->bi_dram[i].start + bd->bi_dram[i].size - 1; + value = gd->dram[i].start + gd->dram[i].size - 1; lower = lower_32_bits(value); upper = upper_32_bits(value); diff --git a/drivers/mmc/mvebu_mmc.c b/drivers/mmc/mvebu_mmc.c index 5af1953cd14..89d511c1a6f 100644 --- a/drivers/mmc/mvebu_mmc.c +++ b/drivers/mmc/mvebu_mmc.c @@ -375,8 +375,8 @@ static void mvebu_window_setup(const struct mmc *mmc) break; } - size = gd->bd->bi_dram[i].size; - base = gd->bd->bi_dram[i].start; + size = gd->dram[i].size; + base = gd->dram[i].start; if (size && attrib) { mvebu_mmc_write(mmc, WINDOW_CTRL(i), MVCPU_WIN_CTRL_DATA(size, diff --git a/drivers/net/mvgbe.c b/drivers/net/mvgbe.c index 107a33aa9f5..4dc738980cb 100644 --- a/drivers/net/mvgbe.c +++ b/drivers/net/mvgbe.c @@ -256,8 +256,8 @@ static void set_dram_access(struct mvgbe_registers *regs) win_param.access_ctrl = EWIN_ACCESS_FULL; win_param.high_addr = 0; /* Get bank base and size */ - win_param.base_addr = gd->bd->bi_dram[i].start; - win_param.size = gd->bd->bi_dram[i].size; + win_param.base_addr = gd->dram[i].start; + win_param.size = gd->dram[i].size; if (win_param.size == 0) win_param.enable = 0; else diff --git a/drivers/pci/pci-uclass.c b/drivers/pci/pci-uclass.c index f58d542ef75..4bdd1f7477f 100644 --- a/drivers/pci/pci-uclass.c +++ b/drivers/pci/pci-uclass.c @@ -1126,14 +1126,14 @@ static int decode_regions(struct pci_controller *hose, ofnode parent_node, return 0; for (i = 0; i < CONFIG_NR_DRAM_BANKS; ++i) { - if (bd->bi_dram[i].size) { - phys_addr_t start = bd->bi_dram[i].start; + if (gd->dram[i].size) { + phys_addr_t start = gd->dram[i].start; if (IS_ENABLED(CONFIG_PCI_MAP_SYSTEM_MEMORY)) - start = virt_to_phys((void *)(uintptr_t)bd->bi_dram[i].start); + start = virt_to_phys((void *)(uintptr_t)gd->dram[i].start); pci_set_region(hose->regions + hose->region_count++, - start, start, bd->bi_dram[i].size, + start, start, gd->dram[i].size, PCI_REGION_MEM | PCI_REGION_SYS_MEMORY); } } diff --git a/drivers/usb/host/ehci-marvell.c b/drivers/usb/host/ehci-marvell.c index 794a4168913..38ee17f063d 100644 --- a/drivers/usb/host/ehci-marvell.c +++ b/drivers/usb/host/ehci-marvell.c @@ -222,8 +222,8 @@ static void usb_brg_adrdec_setup(int index) break; } - size = gd->bd->bi_dram[i].size; - base = gd->bd->bi_dram[i].start; + size = gd->dram[i].size; + base = gd->dram[i].start; if ((size) && (attrib)) writel(MVCPU_WIN_CTRL_DATA(size, USB_TARGET_DRAM, attrib, MVCPU_WIN_ENABLE), diff --git a/drivers/video/meson/meson_vpu.c b/drivers/video/meson/meson_vpu.c index ca627728743..a686faf9f58 100644 --- a/drivers/video/meson/meson_vpu.c +++ b/drivers/video/meson/meson_vpu.c @@ -81,8 +81,8 @@ cvbs: meson_fb.fb_size = ALIGN(meson_fb.xsize * meson_fb.ysize * ((1 << VPU_MAX_LOG2_BPP) / 8) + MESON_VPU_OVERSCAN, EFI_PAGE_SIZE); - meson_fb.base = gd->bd->bi_dram[0].start + - gd->bd->bi_dram[0].size - meson_fb.fb_size; + meson_fb.base = gd->dram[0].start + + gd->dram[0].size - meson_fb.fb_size; /* Override the framebuffer address */ uc_plat->base = meson_fb.base; @@ -175,8 +175,8 @@ static void meson_vpu_setup_simplefb(void *fdt) * at the end of the RAM and we strip this portion from the kernel * allowed region */ - mem_start = gd->bd->bi_dram[0].start; - mem_size = gd->bd->bi_dram[0].size - meson_fb.fb_size; + mem_start = gd->dram[0].start; + mem_size = gd->dram[0].size - meson_fb.fb_size; ret = fdt_fixup_memory_banks(fdt, &mem_start, &mem_size, 1); if (ret) { eprintf("Cannot setup simplefb: Error reserving memory\n"); diff --git a/drivers/video/sunxi/sunxi_de2.c b/drivers/video/sunxi/sunxi_de2.c index 154641b9a69..ab36ee1595b 100644 --- a/drivers/video/sunxi/sunxi_de2.c +++ b/drivers/video/sunxi/sunxi_de2.c @@ -368,7 +368,7 @@ int sunxi_simplefb_setup(void *blob) return 0; /* Keep older kernels working */ } - start = gd->bd->bi_dram[0].start; + start = gd->dram[0].start; size = de2_plat->base - start; ret = fdt_fixup_memory_banks(blob, &start, &size, 1); if (ret) { diff --git a/drivers/video/sunxi/sunxi_display.c b/drivers/video/sunxi/sunxi_display.c index 4a6a89ef9d2..fa492c661db 100644 --- a/drivers/video/sunxi/sunxi_display.c +++ b/drivers/video/sunxi/sunxi_display.c @@ -1336,7 +1336,7 @@ int sunxi_simplefb_setup(void *blob) * and e.g. Linux refuses to iomap RAM on ARM, see: * linux/arch/arm/mm/ioremap.c around line 301. */ - start = gd->bd->bi_dram[0].start; + start = gd->dram[0].start; size = sunxi_display->fb_addr - start; ret = fdt_fixup_memory_banks(blob, &start, &size, 1); if (ret) { |
