Building kernel uImage using LOADADDR
Asked Answered
C

2

12

While building the kernel I am giving LOADADDR as "0x80008000":

make uImage LOADADDR=0x80008000

Can you please help to understand what is the use of this? Can I change the LOADADDR, is there any restriction on the length of the LOADADDR?

Claret answered 30/7, 2015 at 13:49 Comment(0)
S
18

(I'm assuming that you're using ARM based on the mention of U-Boot and the value of LOADADDR.)

Can you please help to understand what is the use of this?

LOADADDR specifies the address where the kernel image will be located by the linker. (This is true for a few architectures (e.g. Blackfin), but not for ARM.

LOADADDR specifies the address where the kernel image will be located by U-Boot and is stored in the U-Boot header by the mkimage utility. Typically the load address (for placement in memory) is also the start address (for execution). Note that the uImage file is typically just the (self-extracting, compressed) zImage file with the U-Boot wrapper.

Can I change the LOADADDR,

Yes, but according to (Vincent Sanders') Booting ARM Linux that would be contrary to ARM convention:

  • Despite the ability to place zImage anywhere within memory, convention has it that it is loaded at the base of physical RAM plus an offset of 0x8000 (32K). This leaves space for the parameter block usually placed at offset 0x100, zero page exception vectors and page tables. This convention is very common.

(The uImage mentioned in your question is probably just a zImage with the U-Boot wrapper, so the quotation does apply.)

is there any restriction on the length of the LOADADDR?

The "length"? If you're using a 32-bit processor, then the length of this address would be 32 bits.


ADDENDUM

arch/arm/boot/Makefile only uses LOADADDR for building the uImage from the zImage.

From (Russel King's) Booting ARM Linux the constraints on this LOADADDR are:

The kernel should be placed in the first 128MiB of RAM. It is recommended that it is loaded above 32MiB in order to avoid the need to relocate prior to decompression, which will make the boot process slightly faster.

When booting a raw (non-zImage) kernel the constraints are tighter. In this case the kernel must be loaded at an offset into system equal to TEXT_OFFSET - PAGE_OFFSET.

The expected locations for the Device Tree or ATAGs or an initramfs can add more constraints on this LOADADDR.

Stanstance answered 31/7, 2015 at 19:57 Comment(4)
Thanks for the reply. Yes, I am using ARM based board. I am not getting "LOADADDR specifies the address where the kernel image will be located by the linker.", could you please help. As per my understanding linker will link all the ".o "s and creates vmlinux.o. I think LOADADDR will not place any role while building uImage other than placing the same(LOADDR value) in the uImage header, please correct me if it is worng.Claret
The LOADADDR is virtual or physical? If we treat 0x80008000 as physical address(because MMU is not enable at this point) then 0x80008000 will point to a physical address which is more than 2GB. If we have 2GB RAM in our device then how it will treat?Claret
@Claret -- This is a physical memory address, since the bootloader does not enable the MMU as you mentioned. Typically the physical RAM does not start at address zero. I've seen ARM SoCs that have the RAM at 0x20000000, or at 0x70000000. Apparently on your board it starts at 0x80000000. Physical address zero typically has an internal boot ROM on ARM rather than read/writable RAM. Consult the datasheet or technical reference manual (TRM) of your SoC for a memory map.Stanstance
Thanks for the info, now I got idea about LOADADDR. I checked the uImage header using hexdump and could see loadaddr and entry point address. In my case both loadaddr and entry point addr are same. #hexdump uImage | head -2 0000000 0527 5619 5b20 01e4 bf55 da50 6000 a8d5 0000010 0080 0080 0080 0080 5f32 d5d4 0205 0002Claret
G
0

Putting this in other terms, kernel compilation can generate different images, compressed or not (i.e. needed for XIP). LOADADDR is the entry_point of the kernel, must be correct (match with where u-boot loads it in DDR) for certain architectures that compiles with absolute long jumps, and not important at all for ARM that can execute relative jumps.

Graphology answered 8/9, 2022 at 11:38 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.