[RFC 0/1] use lmb to calculate ram left for the kernel
Sughosh Ganu
sughosh.ganu at linaro.org
Tue Aug 5 14:48:52 CEST 2025
On Tue, 5 Aug 2025 at 17:57, Tomas Alvarez Vanoli
<tomas.alvarez-vanoli at hitachienergy.com> wrote:
>
> >Okay, I see. Given that we now have a global memory map for lmb, I don't think that using lmb functionality is the best way of computing the amount of memory that would be available for the kernel to use.
> >Please note that with a global and persistent memory map of lmb, there is no guarantee as to where the first chunk of used memory lie above your rootfs memory. Earlier, I think this was fine as the lmb memory map was local, so you could copy the ramfs to some low memory region, and then show the rest of memory as available in the lmb memory map.
>
> I am not sure I understand what you mean with "there is no guarantee as to where the first chunk of used memory lie above your rootfs memory".
> How is it different to when it was local?
Earlier, with a local lmb map, one could define a map inside a
function, with available memory and used memory which could be
controlled inside some function. This is no longer possible. There
could be an allocation that could have happened above the rootfs
memory, which would mean that the free memory computation would be
non-deterministic. So with a global and persistent lmb memory map,
this is no longer a robust way to compute memory available for the
kernel.
As an aside, I am not sure if you have considered using the UEFI
interfaces for booting the kernel. The EFI firmware (U-Boot in this
case) passes a memory map to the kernel which specifies which memory
the kernel can use, and which is reserved. Booting the kernel with EFI
interfaces, the memory occupied by the ramfs can then be marked as
EfiReservedMemoryType, and this would not be used by the kernel. This
definitely can be done on armv8 platforms -- I have not booted a
kernel with EFI interfaces on armv7 boards though. Something to
consider for your solution.
-sughosh
>
>
> >That might no longer be the case. So this computation of memory available for the kernel will have to be re-designed. I think instead of relying on the lmb memory map for your computations, there should be some fixed memory region where the ramfs would have to be copied, and then the rest of the memory can be considered as safe for the kernel to use.
>
> >Btw, I tried looking for the function that you are changing in your board file in the patch, but I do not see it in the upstream U-Boot.
>
> It's not mainlined yet, here's the full function with the patch applied:
>
> ```c
> static int do_calc_ramfs_addr(struct cmd_tbl *cmdtp, int flag, int argc,
> char *const argv[]) {
> ulong size = 0;
> if(strict_strtoul(argv[1], 16, &size) != 0) {
> printf("%s: failed to parse size arg\n", __func__);
> return CMD_RET_FAILURE;
> }
>
> phys_addr_t addr = lmb_alloc(size, SZ_16K);
>
> if (addr == 0) {
> printf("%s: failed to find space for rootfs in ram\n", __func__);
> return CMD_RET_FAILURE;
> }
>
> // calculate how much ram we can give the kernel
> phys_size_t free = lmb_get_reservable_size(CFG_SYS_SDRAM_BASE) & ~(SZ_16K - 1);
> if (free <= 0) {
> printf("%s: failed to calculate free memory for kernel\n", __func__);
> return CMD_RET_FAILURE;
> }
>
> /* We dont reserve the memory for the rootfs, because tftp needs to write it.
> * because of that, we check here if the kernel memory overlaps it or not.
> */
> if (CFG_SYS_SDRAM_BASE + free > addr) {
> free = (addr - CFG_SYS_SDRAM_BASE) & ~(SZ_16K - 1);
> }
>
> char envval[20];
> sprintf(envval, "%pa", &addr);
> env_set("rootfsaddr", envval);
> sprintf(envval, "%pa", &free);
> env_set("kernelmem", envval);
>
> return 0;
> }
> ```
More information about the U-Boot
mailing list