2011-11-10 Doug Kwan <dougkwan@google.com>
PR gold/13362 * arm.cc (Target_arm::Relocate::relocate_tls): Do unaligned accesses when processing data relocs. * reloc.h (Relocate_functions::rel_unaligned): New method. (Relocate_functions::pcrel_unaligned): Ditto. (Relocate_functions::rel32_unaligned): Ditto. (Relocate_functions::pcrel32_unaligned): Ditto.
This commit is contained in:
parent
50f182aa66
commit
29ab395d2b
@ -1,3 +1,13 @@
|
||||
2011-11-10 Doug Kwan <dougkwan@google.com>
|
||||
|
||||
PR gold/13362
|
||||
* arm.cc (Target_arm::Relocate::relocate_tls): Do unaligned accesses
|
||||
when processing data relocs.
|
||||
* reloc.h (Relocate_functions::rel_unaligned): New method.
|
||||
(Relocate_functions::pcrel_unaligned): Ditto.
|
||||
(Relocate_functions::rel32_unaligned): Ditto.
|
||||
(Relocate_functions::pcrel32_unaligned): Ditto.
|
||||
|
||||
2011-11-09 Doug Kwan <dougkwan@google.com>
|
||||
|
||||
PR gold/13362
|
||||
|
10
gold/arm.cc
10
gold/arm.cc
@ -9348,7 +9348,7 @@ Target_arm<big_endian>::Relocate::relocate_tls(
|
||||
|
||||
// Relocate the field with the PC relative offset of the pair of
|
||||
// GOT entries.
|
||||
RelocFuncs::pcrel32(view, got_entry, address);
|
||||
RelocFuncs::pcrel32_unaligned(view, got_entry, address);
|
||||
return ArmRelocFuncs::STATUS_OKAY;
|
||||
}
|
||||
}
|
||||
@ -9367,13 +9367,13 @@ Target_arm<big_endian>::Relocate::relocate_tls(
|
||||
|
||||
// Relocate the field with the PC relative offset of the pair of
|
||||
// GOT entries.
|
||||
RelocFuncs::pcrel32(view, got_entry, address);
|
||||
RelocFuncs::pcrel32_unaligned(view, got_entry, address);
|
||||
return ArmRelocFuncs::STATUS_OKAY;
|
||||
}
|
||||
break;
|
||||
|
||||
case elfcpp::R_ARM_TLS_LDO32: // Alternate local-dynamic
|
||||
RelocFuncs::rel32(view, value);
|
||||
RelocFuncs::rel32_unaligned(view, value);
|
||||
return ArmRelocFuncs::STATUS_OKAY;
|
||||
|
||||
case elfcpp::R_ARM_TLS_IE32: // Initial-exec
|
||||
@ -9402,7 +9402,7 @@ Target_arm<big_endian>::Relocate::relocate_tls(
|
||||
target->got_plt_section()->address() + got_offset;
|
||||
|
||||
// Relocate the field with the PC relative offset of the GOT entry.
|
||||
RelocFuncs::pcrel32(view, got_entry, address);
|
||||
RelocFuncs::pcrel32_unaligned(view, got_entry, address);
|
||||
return ArmRelocFuncs::STATUS_OKAY;
|
||||
}
|
||||
break;
|
||||
@ -9418,7 +9418,7 @@ Target_arm<big_endian>::Relocate::relocate_tls(
|
||||
// need to add TCB size to the offset.
|
||||
Arm_address aligned_tcb_size =
|
||||
align_address(ARM_TCB_SIZE, tls_segment->maximum_alignment());
|
||||
RelocFuncs::rel32(view, value + aligned_tcb_size);
|
||||
RelocFuncs::rel32_unaligned(view, value + aligned_tcb_size);
|
||||
|
||||
}
|
||||
return ArmRelocFuncs::STATUS_OKAY;
|
||||
|
36
gold/reloc.h
36
gold/reloc.h
@ -333,6 +333,18 @@ private:
|
||||
elfcpp::Swap<valsize, big_endian>::writeval(wv, x + value);
|
||||
}
|
||||
|
||||
// Like the above but for relocs at unaligned addresses.
|
||||
template<int valsize>
|
||||
static inline void
|
||||
rel_unaligned(unsigned char* view,
|
||||
typename elfcpp::Swap<valsize, big_endian>::Valtype value)
|
||||
{
|
||||
typedef typename elfcpp::Swap_unaligned<valsize, big_endian>::Valtype
|
||||
Valtype;
|
||||
Valtype x = elfcpp::Swap_unaligned<valsize, big_endian>::readval(view);
|
||||
elfcpp::Swap_unaligned<valsize, big_endian>::writeval(view, x + value);
|
||||
}
|
||||
|
||||
// Do a simple relocation using a Symbol_value with the addend in
|
||||
// the section contents. VALSIZE is the size of the value to
|
||||
// relocate.
|
||||
@ -405,6 +417,19 @@ private:
|
||||
elfcpp::Swap<valsize, big_endian>::writeval(wv, x + value - address);
|
||||
}
|
||||
|
||||
// Like the above but for relocs at unaligned addresses.
|
||||
template<int valsize>
|
||||
static inline void
|
||||
pcrel_unaligned(unsigned char* view,
|
||||
typename elfcpp::Swap<valsize, big_endian>::Valtype value,
|
||||
typename elfcpp::Elf_types<size>::Elf_Addr address)
|
||||
{
|
||||
typedef typename elfcpp::Swap<valsize, big_endian>::Valtype Valtype;
|
||||
Valtype x = elfcpp::Swap_unaligned<valsize, big_endian>::readval(view);
|
||||
elfcpp::Swap_unaligned<valsize, big_endian>::writeval(view,
|
||||
x + value - address);
|
||||
}
|
||||
|
||||
// Do a simple PC relative relocation with a Symbol_value with the
|
||||
// addend in the section contents. VALSIZE is the size of the
|
||||
// value.
|
||||
@ -568,6 +593,11 @@ public:
|
||||
rel32(unsigned char* view, elfcpp::Elf_Word value)
|
||||
{ This::template rel<32>(view, value); }
|
||||
|
||||
// Like above but for relocs at unaligned addresses.
|
||||
static inline void
|
||||
rel32_unaligned(unsigned char* view, elfcpp::Elf_Word value)
|
||||
{ This::template rel_unaligned<32>(view, value); }
|
||||
|
||||
static inline void
|
||||
rel32(unsigned char* view,
|
||||
const Sized_relobj_file<size, big_endian>* object,
|
||||
@ -600,6 +630,12 @@ public:
|
||||
typename elfcpp::Elf_types<size>::Elf_Addr address)
|
||||
{ This::template pcrel<32>(view, value, address); }
|
||||
|
||||
// Unaligned version of the above.
|
||||
static inline void
|
||||
pcrel32_unaligned(unsigned char* view, elfcpp::Elf_Word value,
|
||||
typename elfcpp::Elf_types<size>::Elf_Addr address)
|
||||
{ This::template pcrel_unaligned<32>(view, value, address); }
|
||||
|
||||
static inline void
|
||||
pcrel32(unsigned char* view,
|
||||
const Sized_relobj_file<size, big_endian>* object,
|
||||
|
Loading…
Reference in New Issue
Block a user