lmb: make LMB memory map persistent and global
The current LMB API's for allocating and reserving memory use a
per-caller based memory view. Memory allocated by a caller can then be
overwritten by another caller. Make these allocations and reservations
persistent using the alloced list data structure.
Two alloced lists are declared -- one for the available(free) memory,
and one for the used memory. Once full, the list can then be extended
at runtime.
[sjg: Use a stack to store pointer of lmb struct when running lmb tests]
Signed-off-by: Sughosh Ganu <sughosh.ganu@linaro.org>
Signed-off-by: Simon Glass <sjg@chromium.org>
[sjg: Optimise the logic to add a region in lmb_add_region_flags()]
diff --git a/arch/arm/lib/stack.c b/arch/arm/lib/stack.c
index ea1b937..87d5c96 100644
--- a/arch/arm/lib/stack.c
+++ b/arch/arm/lib/stack.c
@@ -42,7 +42,7 @@
return ret;
}
-void arch_lmb_reserve(struct lmb *lmb)
+void arch_lmb_reserve(void)
{
- arch_lmb_reserve_generic(lmb, get_sp(), gd->ram_top, 16384);
+ arch_lmb_reserve_generic(get_sp(), gd->ram_top, 16384);
}
diff --git a/arch/arm/mach-apple/board.c b/arch/arm/mach-apple/board.c
index 8bace30..213390d 100644
--- a/arch/arm/mach-apple/board.c
+++ b/arch/arm/mach-apple/board.c
@@ -773,23 +773,22 @@
int board_late_init(void)
{
- struct lmb lmb;
u32 status = 0;
- lmb_init_and_reserve(&lmb, gd->bd, (void *)gd->fdt_blob);
+ lmb_init_and_reserve(gd->bd, (void *)gd->fdt_blob);
/* somewhat based on the Linux Kernel boot requirements:
* align by 2M and maximal FDT size 2M
*/
- status |= env_set_hex("loadaddr", lmb_alloc(&lmb, SZ_1G, SZ_2M));
- status |= env_set_hex("fdt_addr_r", lmb_alloc(&lmb, SZ_2M, SZ_2M));
- status |= env_set_hex("kernel_addr_r", lmb_alloc(&lmb, SZ_128M, SZ_2M));
- status |= env_set_hex("ramdisk_addr_r", lmb_alloc(&lmb, SZ_1G, SZ_2M));
+ status |= env_set_hex("loadaddr", lmb_alloc(SZ_1G, SZ_2M));
+ status |= env_set_hex("fdt_addr_r", lmb_alloc(SZ_2M, SZ_2M));
+ status |= env_set_hex("kernel_addr_r", lmb_alloc(SZ_128M, SZ_2M));
+ status |= env_set_hex("ramdisk_addr_r", lmb_alloc(SZ_1G, SZ_2M));
status |= env_set_hex("kernel_comp_addr_r",
- lmb_alloc(&lmb, KERNEL_COMP_SIZE, SZ_2M));
+ lmb_alloc(KERNEL_COMP_SIZE, SZ_2M));
status |= env_set_hex("kernel_comp_size", KERNEL_COMP_SIZE);
- status |= env_set_hex("scriptaddr", lmb_alloc(&lmb, SZ_4M, SZ_2M));
- status |= env_set_hex("pxefile_addr_r", lmb_alloc(&lmb, SZ_4M, SZ_2M));
+ status |= env_set_hex("scriptaddr", lmb_alloc(SZ_4M, SZ_2M));
+ status |= env_set_hex("pxefile_addr_r", lmb_alloc(SZ_4M, SZ_2M));
if (status)
log_warning("late_init: Failed to set run time variables\n");
diff --git a/arch/arm/mach-snapdragon/board.c b/arch/arm/mach-snapdragon/board.c
index b439a19..a63c8be 100644
--- a/arch/arm/mach-snapdragon/board.c
+++ b/arch/arm/mach-snapdragon/board.c
@@ -275,24 +275,23 @@
#define KERNEL_COMP_SIZE SZ_64M
-#define addr_alloc(lmb, size) lmb_alloc(lmb, size, SZ_2M)
+#define addr_alloc(size) lmb_alloc(size, SZ_2M)
/* Stolen from arch/arm/mach-apple/board.c */
int board_late_init(void)
{
- struct lmb lmb;
u32 status = 0;
- lmb_init_and_reserve(&lmb, gd->bd, (void *)gd->fdt_blob);
+ lmb_init_and_reserve(gd->bd, (void *)gd->fdt_blob);
/* We need to be fairly conservative here as we support boards with just 1G of TOTAL RAM */
- status |= env_set_hex("kernel_addr_r", addr_alloc(&lmb, SZ_128M));
- status |= env_set_hex("ramdisk_addr_r", addr_alloc(&lmb, SZ_128M));
- status |= env_set_hex("kernel_comp_addr_r", addr_alloc(&lmb, KERNEL_COMP_SIZE));
+ status |= env_set_hex("kernel_addr_r", addr_alloc(SZ_128M));
+ status |= env_set_hex("ramdisk_addr_r", addr_alloc(SZ_128M));
+ status |= env_set_hex("kernel_comp_addr_r", addr_alloc(KERNEL_COMP_SIZE));
status |= env_set_hex("kernel_comp_size", KERNEL_COMP_SIZE);
- status |= env_set_hex("scriptaddr", addr_alloc(&lmb, SZ_4M));
- status |= env_set_hex("pxefile_addr_r", addr_alloc(&lmb, SZ_4M));
- status |= env_set_hex("fdt_addr_r", addr_alloc(&lmb, SZ_2M));
+ status |= env_set_hex("scriptaddr", addr_alloc(SZ_4M));
+ status |= env_set_hex("pxefile_addr_r", addr_alloc(SZ_4M));
+ status |= env_set_hex("fdt_addr_r", addr_alloc(SZ_2M));
if (status)
log_warning("%s: Failed to set run time variables\n", __func__);
diff --git a/arch/arm/mach-stm32mp/dram_init.c b/arch/arm/mach-stm32mp/dram_init.c
index 6024959..e8b0a38 100644
--- a/arch/arm/mach-stm32mp/dram_init.c
+++ b/arch/arm/mach-stm32mp/dram_init.c
@@ -47,7 +47,6 @@
{
phys_size_t size;
phys_addr_t reg;
- struct lmb lmb;
if (!total_size)
return gd->ram_top;
@@ -59,12 +58,11 @@
gd->ram_top = clamp_val(gd->ram_top, 0, SZ_4G - 1);
/* found enough not-reserved memory to relocated U-Boot */
- lmb_init(&lmb);
- lmb_add(&lmb, gd->ram_base, gd->ram_top - gd->ram_base);
- boot_fdt_add_mem_rsv_regions(&lmb, (void *)gd->fdt_blob);
+ lmb_add(gd->ram_base, gd->ram_top - gd->ram_base);
+ boot_fdt_add_mem_rsv_regions((void *)gd->fdt_blob);
/* add 8M for reserved memory for display, fdt, gd,... */
size = ALIGN(SZ_8M + CONFIG_SYS_MALLOC_LEN + total_size, MMU_SECTION_SIZE),
- reg = lmb_alloc(&lmb, size, MMU_SECTION_SIZE);
+ reg = lmb_alloc(size, MMU_SECTION_SIZE);
if (!reg)
reg = gd->ram_top - size;
diff --git a/arch/arm/mach-stm32mp/stm32mp1/cpu.c b/arch/arm/mach-stm32mp/stm32mp1/cpu.c
index 478c3ef..a913737 100644
--- a/arch/arm/mach-stm32mp/stm32mp1/cpu.c
+++ b/arch/arm/mach-stm32mp/stm32mp1/cpu.c
@@ -30,8 +30,6 @@
*/
u8 early_tlb[PGTABLE_SIZE] __section(".data") __aligned(0x4000);
-struct lmb lmb;
-
u32 get_bootmode(void)
{
/* read bootmode from TAMP backup register */
@@ -80,7 +78,7 @@
i < (start >> MMU_SECTION_SHIFT) + (size >> MMU_SECTION_SHIFT);
i++) {
option = DCACHE_DEFAULT_OPTION;
- if (use_lmb && lmb_is_reserved_flags(&lmb, i << MMU_SECTION_SHIFT, LMB_NOMAP))
+ if (use_lmb && lmb_is_reserved_flags(i << MMU_SECTION_SHIFT, LMB_NOMAP))
option = 0; /* INVALID ENTRY in TLB */
set_section_dcache(i, option);
}
@@ -144,7 +142,7 @@
void enable_caches(void)
{
/* parse device tree when data cache is still activated */
- lmb_init_and_reserve(&lmb, gd->bd, (void *)gd->fdt_blob);
+ lmb_init_and_reserve(gd->bd, (void *)gd->fdt_blob);
/* I-cache is already enabled in start.S: icache_enable() not needed */