llext: arch_elf_relocate: pass opval unmodified

The opval argument of arch_elf_relocate() was modified by
adding the value stored at opaddr before passing it to
arch_elf_relocate(). This presumed that the addend would
always be stored as a raw value at opaddr, which is not the
case for all relocation types.

This PR modifies opval to be the absolute address of opval,
and moves the addition of the addend from llext_link_plt()
to the implementation of arch_elf_relocate().

Signed-off-by: Bjarki Arge Andreasen <bjarki@arge-andreasen.me>
This commit is contained in:
Bjarki Arge Andreasen 2024-03-12 16:48:18 +01:00 committed by Fabio Baltieri
parent 6c6495bb43
commit 5cac834bb6
2 changed files with 5 additions and 3 deletions

View file

@ -26,6 +26,9 @@ void arch_elf_relocate(elf_rela_t *rel, uintptr_t opaddr, uintptr_t opval)
switch (reloc_type) {
case R_ARM_ABS32:
/* Add the addend stored at opaddr to opval */
opval += *((uint32_t *)opaddr);
/* Update the absolute address of a load/store instruction */
*((uint32_t *)opaddr) = (uint32_t)opval;
break;

View file

@ -769,10 +769,9 @@ static int llext_link(struct llext_loader *ldr, struct llext *ext, bool do_local
}
} else if (ELF_ST_TYPE(sym.st_info) == STT_SECTION ||
ELF_ST_TYPE(sym.st_info) == STT_FUNC) {
/* Current relocation location holds an offset into the section */
/* Link address is relative to the start of the section */
link_addr = (uintptr_t)ext->mem[ldr->sect_map[sym.st_shndx]]
+ sym.st_value
+ *((uintptr_t *)op_loc);
+ sym.st_value;
LOG_INF("found section symbol %s addr 0x%lx", name, link_addr);
} else {