2002-01-29 Chris Demetriou <cgd@broadcom.com>

* elf32-mips.c: Add additional comments about HI16 relocation
        processing.
        (_bfd_mips_elf_hi16_reloc): Don't subtract address here for
        pc-relative relocations.  (Reverts change made on 2001-10-31.)
        (_bfd_mips_elf_lo16_reloc): Subtract address of LO16 part here
        for pc-relative relocations.
        (mips_elf_calculate_relocation): Add a comment about a kludge
        in the R_MIPS_GNU_REL_HI16 handling.
        (_bfd_mips_elf_relocate_section): Implement that kludge;
        adjust pc-relative HI16 relocation for difference in HI16 and
        LO16 addresses, since it can't easily be done in
        mips_elf_calculate_relocation.
This commit is contained in:
Chris Demetriou 2002-01-30 02:13:20 +00:00
parent 977a303014
commit fcc76bea37
2 changed files with 45 additions and 5 deletions

View File

@ -1,3 +1,18 @@
2002-01-29 Chris Demetriou <cgd@broadcom.com>
* elf32-mips.c: Add additional comments about HI16 relocation
processing.
(_bfd_mips_elf_hi16_reloc): Don't subtract address here for
pc-relative relocations. (Reverts change made on 2001-10-31.)
(_bfd_mips_elf_lo16_reloc): Subtract address of LO16 part here
for pc-relative relocations.
(mips_elf_calculate_relocation): Add a comment about a kludge
in the R_MIPS_GNU_REL_HI16 handling.
(_bfd_mips_elf_relocate_section): Implement that kludge;
adjust pc-relative HI16 relocation for difference in HI16 and
LO16 addresses, since it can't easily be done in
mips_elf_calculate_relocation.
2002-01-29 Martin Schwidefsky <schwidefsky@de.ibm.com>
* elf32-i386 (elf_i386_adjust_dynamic_symbol): Do not replace PLT32

View File

@ -1640,11 +1640,17 @@ static reloc_howto_type elf_mips_gnu_vtentry_howto =
/* Do a R_MIPS_HI16 relocation. This has to be done in combination
with a R_MIPS_LO16 reloc, because there is a carry from the LO16 to
the HI16. Here we just save the information we need; we do the
actual relocation when we see the LO16. MIPS ELF requires that the
LO16 immediately follow the HI16. As a GNU extension, we permit an
actual relocation when we see the LO16.
MIPS ELF requires that the LO16 immediately follow the HI16. As a
GNU extension, for non-pc-relative relocations, we permit an
arbitrary number of HI16 relocs to be associated with a single LO16
reloc. This extension permits gcc to output the HI and LO relocs
itself. */
itself.
This cannot be done for PC-relative relocations because both the HI16
and LO16 parts of the relocations must be done relative to the LO16
part, and there can be carry to or borrow from the HI16 part. */
struct mips_hi16
{
@ -1727,8 +1733,6 @@ _bfd_mips_elf_hi16_reloc (abfd,
relocation += symbol->section->output_section->vma;
relocation += symbol->section->output_offset;
relocation += reloc_entry->addend;
if (reloc_entry->howto->pc_relative)
relocation -= reloc_entry->address;
if (reloc_entry->address > input_section->_cooked_size)
return bfd_reloc_outofrange;
@ -1794,6 +1798,12 @@ _bfd_mips_elf_lo16_reloc (abfd,
val = ((insn & 0xffff) << 16) + vallo;
val += l->addend;
/* If PC-relative, we need to subtract out the address of the LO
half of the HI/LO. (The actual relocation is relative
to that instruction.) */
if (reloc_entry->howto->pc_relative)
val -= reloc_entry->address;
/* At this point, "val" has the value of the combined HI/LO
pair. If the low order 16 bits (which will be used for
the LO16 insn) are negative, then we will need an
@ -6864,6 +6874,11 @@ mips_elf_calculate_relocation (abfd,
break;
case R_MIPS_GNU_REL_HI16:
/* Instead of subtracting 'p' here, we should be subtracting the
equivalent value for the LO part of the reloc, since the value
here is relative to that address. Because that's not easy to do,
we adjust 'addend' in _bfd_mips_elf_relocate_section(). See also
the comment there for more information. */
value = mips_elf_high (addend + symbol - p);
value &= howto->dst_mask;
break;
@ -7390,6 +7405,16 @@ _bfd_mips_elf_relocate_section (output_bfd, info, input_bfd, input_section,
/* Compute the combined addend. */
addend += l;
/* If PC-relative, subtract the difference between the
address of the LO part of the reloc and the address of
the HI part. The relocation is relative to the LO
part, but mips_elf_calculate_relocation() doesn't know
it address or the difference from the HI part, so
we subtract that difference here. See also the
comment in mips_elf_calculate_relocation(). */
if (r_type == R_MIPS_GNU_REL_HI16)
addend -= (lo16_relocation->r_offset - rel->r_offset);
}
else if (r_type == R_MIPS16_GPREL)
{