From: Maciej W. Rozycki Date: Wed, 14 Jan 2026 22:28:44 +0000 (+0000) Subject: MIPS/BFD: Fix ELF link orphan REL HI16 relocation addend processing X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=a85a420984db83a33be4af777f0b94ed94c1b9f2;p=thirdparty%2Fbinutils-gdb.git MIPS/BFD: Fix ELF link orphan REL HI16 relocation addend processing Correct the addend being ignored for orphan REL HI16 relocations. For ELF links `_bfd_mips_elf_relocate_section' handles relocation and uses `mips_elf_add_lo16_rel_addend' to shift the incoming HI16 in-place addend into its intended [31:16] bit positions and combine it with the LO16 part. If no matching LO16 reloc has been found, then the function returns early and consequently the incoming HI16 addend is not shifted and remains in bits [0:15]. For final links any value of the symbol referred is then added. Then the final value is shifted back into bits [0:15] for installation into the field relocated. It is obviously wrong as the original HI16 in-place addend has now been lost. Fix the issue by shifting the incoming HI16 in-place addend before using `mips_elf_next_relocation' to find the matching LO16 relocation. Then upon early return from `mips_elf_add_lo16_rel_addend' the addend is in the intended [31:16] bit positions already. Test cases will be added with a separate change. --- diff --git a/bfd/elfxx-mips.c b/bfd/elfxx-mips.c index f4424aca504..d3d989eae82 100644 --- a/bfd/elfxx-mips.c +++ b/bfd/elfxx-mips.c @@ -8370,9 +8370,10 @@ mips_elf_add_lo16_rel_addend (bfd *abfd, /* The combined value is the sum of the HI16 addend, left-shifted by sixteen bits, and the LO16 addend, sign extended. (Usually, the code does a `lui' of the HI16 value, and then an `addiu' of the - LO16 value.) + LO16 value.) */ + *addend <<= 16; - Scan ahead to find a matching LO16 relocation. + /* Scan ahead to find a matching LO16 relocation. According to the MIPS ELF ABI, the R_MIPS_LO16 relocation must be immediately following. However, for the IRIX6 ABI, the next @@ -8400,7 +8401,6 @@ mips_elf_add_lo16_rel_addend (bfd *abfd, l = (l - (lo16_relocation->r_offset - rel->r_offset)) & 0xffff; l = _bfd_mips_elf_sign_extend (l, 16); - *addend <<= 16; *addend += l; return true; }