[PATCH, ARM] Fix handling of GOT and PLT access to IFUNC symbols
Richard Earnshaw
rearnsha@arm.com
Mon Apr 15 15:18:00 GMT 2013
On 12/04/13 17:42, Will Newton wrote:
>
> Hi all,
>
> The current ARM IFUNC code appears to have a bug when an access is made via
> the PLT and GOT in the same object. This results in two relocs being swapped
> out into the same slot so one R_ARM_IRELATIVE reloc goes missing.
>
> This patch changes the behaviour to use an incremented reloc count rather
> than the calculated PLT index to match the behaviour of elf32_arm_add_dynreloc
> and as a result requires the order of relocs in the ifunc tests to be adjusted.
>
> bfd/ChangeLog:
>
> 2013-04-12 Will Newton <will.newton@linaro.org>
>
> * elf32-arm.c (elf32_arm_populate_plt_entry): Increment reloc_count
> when emitting R_ARM_IRELATIVE relocs.
>
Hmm, it looks somewhat suspicious to me to be changing the reloc count
this late on.
Richard, do you know if this is safe? If not, can you recommend a
better approach?
R.
> ld/testsuite/ChangeLog:
>
> 2013-04-12 Will Newton <will.newton@linaro.org>
>
> * ld-arm/arm-elf.exp: Add IFUNC test 17.
> * ld-arm/ifunc-17.dd: New file.
> * ld-arm/ifunc-17.gd: Likewise.
> * ld-arm/ifunc-17.rd: Likewise.
> * ld-arm/ifunc-17.s: Likweise.
> * ld-arm/ifunc-1.rd: Reorder relocs to match linker output.
> * ld-arm/ifunc-2.rd: Likewise.
> * ld-arm/ifunc-5.rd: Likewise.
> * ld-arm/ifunc-6.rd: Likewise.
> ---
> bfd/elf32-arm.c | 5 ++++-
> ld/testsuite/ld-arm/arm-elf.exp | 5 +++++
> ld/testsuite/ld-arm/ifunc-1.rd | 2 +-
> ld/testsuite/ld-arm/ifunc-17.dd | 25 +++++++++++++++++++++++++
> ld/testsuite/ld-arm/ifunc-17.gd | 10 ++++++++++
> ld/testsuite/ld-arm/ifunc-17.rd | 5 +++++
> ld/testsuite/ld-arm/ifunc-17.s | 24 ++++++++++++++++++++++++
> ld/testsuite/ld-arm/ifunc-2.rd | 4 ++--
> ld/testsuite/ld-arm/ifunc-5.rd | 2 +-
> ld/testsuite/ld-arm/ifunc-6.rd | 4 ++--
> 10 files changed, 79 insertions(+), 7 deletions(-)
> create mode 100644 ld/testsuite/ld-arm/ifunc-17.dd
> create mode 100644 ld/testsuite/ld-arm/ifunc-17.gd
> create mode 100644 ld/testsuite/ld-arm/ifunc-17.rd
> create mode 100644 ld/testsuite/ld-arm/ifunc-17.s
>
> diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c
> index 78c2d1d..37690e9 100644
> --- a/bfd/elf32-arm.c
> +++ b/bfd/elf32-arm.c
> @@ -7695,7 +7695,10 @@ elf32_arm_populate_plt_entry (bfd *output_bfd, struct bfd_link_info *info,
> sgot->contents + got_offset);
> }
>
> - loc = srel->contents + plt_index * RELOC_SIZE (htab);
> + if (dynindx == -1)
> + loc = srel->contents + srel->reloc_count++ * RELOC_SIZE (htab);
> + else
> + loc = srel->contents + plt_index * RELOC_SIZE (htab);
> SWAP_RELOC_OUT (htab) (output_bfd, &rel, loc);
> }
>
> diff --git a/ld/testsuite/ld-arm/arm-elf.exp b/ld/testsuite/ld-arm/arm-elf.exp
> index f13fae5..c488e3c 100644
> --- a/ld/testsuite/ld-arm/arm-elf.exp
> +++ b/ld/testsuite/ld-arm/arm-elf.exp
> @@ -451,6 +451,11 @@ set armelftests_nonacl {
> {objdump {-s -j.data -j.got} ifunc-16.gd}
> {readelf -r ifunc-16.rd}}
> "ifunc-16"}
> + {"IFUNC test 17" "" "" "" {ifunc-17.s}
> + {{objdump -d ifunc-17.dd}
> + {objdump {-s -j.data -j.got} ifunc-17.gd}
> + {readelf -r ifunc-17.rd}}
> + "ifunc-17"}
> }
>
> run_ld_link_tests $armelftests_common
> diff --git a/ld/testsuite/ld-arm/ifunc-1.rd b/ld/testsuite/ld-arm/ifunc-1.rd
> index 75e6d70..2644123 100644
> --- a/ld/testsuite/ld-arm/ifunc-1.rd
> +++ b/ld/testsuite/ld-arm/ifunc-1.rd
> @@ -4,5 +4,5 @@ There is no dynamic section in this file\.
> Relocation section '\.rel\.dyn' at offset 0x8000 contains 3 entries:
> Offset Info Type Sym\.Value Sym\. Name
> 0001100c ......a0 R_ARM_IRELATIVE
> -00011010 ......a0 R_ARM_IRELATIVE
> 00011014 ......a0 R_ARM_IRELATIVE
> +00011010 ......a0 R_ARM_IRELATIVE
> diff --git a/ld/testsuite/ld-arm/ifunc-17.dd b/ld/testsuite/ld-arm/ifunc-17.dd
> new file mode 100644
> index 0000000..9d0e222
> --- /dev/null
> +++ b/ld/testsuite/ld-arm/ifunc-17.dd
> @@ -0,0 +1,25 @@
> +
> +.*
> +
> +
> +Disassembly of section \.iplt:
> +
> +00008084 <.iplt>:
> +#------------------------------------------------------------------------------
> +#------ libfunc1's .iplt entry
> +#------------------------------------------------------------------------------
> + 8084: e28fc600 add ip, pc, #0, 12
> + 8088: e28cca08 add ip, ip, #8, 20 ; 0x8000
> + 808c: e5bcf01c ldr pc, \[ip, #28\]!
> +
> +Disassembly of section \.text:
> +
> +00008090 <appfunc1>:
> + 8090: 46f7 mov pc, lr
> +
> +00008092 <appfunc2>:
> + 8092: 46f7 mov pc, lr
> +
> +00008094 <_start>:
> + 8094: f7ff eff6 blx 8084 <appfunc1-0xc>
> + 8098: 00000010 \.word 0x00000010
> diff --git a/ld/testsuite/ld-arm/ifunc-17.gd b/ld/testsuite/ld-arm/ifunc-17.gd
> new file mode 100644
> index 0000000..4a12eb8
> --- /dev/null
> +++ b/ld/testsuite/ld-arm/ifunc-17.gd
> @@ -0,0 +1,10 @@
> +
> +.*
> +
> +Contents of section \.got:
> +#------------------------------------------------------------------------------
> +#------ 000100a8: 0x8091 (appfunc1)
> +#------ 000100ac: 0x8093 (appfunc2)
> +#------------------------------------------------------------------------------
> + 1009c 00000000 00000000 00000000 91800000 .*
> + 100ac 93800000 .*
> diff --git a/ld/testsuite/ld-arm/ifunc-17.rd b/ld/testsuite/ld-arm/ifunc-17.rd
> new file mode 100644
> index 0000000..a93fd64
> --- /dev/null
> +++ b/ld/testsuite/ld-arm/ifunc-17.rd
> @@ -0,0 +1,5 @@
> +
> +Relocation section '\.rel\.dyn' at offset 0x74 contains 2 entries:
> + Offset Info Type Sym\.Value Sym\. Name
> +000100a8 ......a0 R_ARM_IRELATIVE
> +000100ac ......a0 R_ARM_IRELATIVE
> diff --git a/ld/testsuite/ld-arm/ifunc-17.s b/ld/testsuite/ld-arm/ifunc-17.s
> new file mode 100644
> index 0000000..75c4c56
> --- /dev/null
> +++ b/ld/testsuite/ld-arm/ifunc-17.s
> @@ -0,0 +1,24 @@
> + .syntax unified
> + .arch armv6t2
> +
> + .global appfunc1
> + .type appfunc1,%gnu_indirect_function
> + .thumb
> +appfunc1:
> + mov pc,lr
> + .size appfunc1,.-appfunc1
> +
> + .global appfunc2
> + .type appfunc2,%gnu_indirect_function
> + .thumb
> +appfunc2:
> + mov pc,lr
> + .size appfunc2,.-appfunc2
> +
> + .global _start
> + .type _start,%function
> + .thumb
> +_start:
> + bl appfunc1(PLT)
> + .word appfunc2(GOT)
> + .size _start,.-_start
> diff --git a/ld/testsuite/ld-arm/ifunc-2.rd b/ld/testsuite/ld-arm/ifunc-2.rd
> index 92b000a..7bbabf4 100644
> --- a/ld/testsuite/ld-arm/ifunc-2.rd
> +++ b/ld/testsuite/ld-arm/ifunc-2.rd
> @@ -5,9 +5,9 @@ Relocation section '\.rel\.dyn' at offset 0x8000 contains 8 entries:
> Offset Info Type Sym\.Value Sym\. Name
> 0001100c ......a0 R_ARM_IRELATIVE
> 00011010 ......a0 R_ARM_IRELATIVE
> +00011020 ......a0 R_ARM_IRELATIVE
> +00011028 ......a0 R_ARM_IRELATIVE
> 00011014 ......a0 R_ARM_IRELATIVE
> 00011018 ......a0 R_ARM_IRELATIVE
> 0001101c ......a0 R_ARM_IRELATIVE
> -00011020 ......a0 R_ARM_IRELATIVE
> 00011024 ......a0 R_ARM_IRELATIVE
> -00011028 ......a0 R_ARM_IRELATIVE
> diff --git a/ld/testsuite/ld-arm/ifunc-5.rd b/ld/testsuite/ld-arm/ifunc-5.rd
> index 75e6d70..2644123 100644
> --- a/ld/testsuite/ld-arm/ifunc-5.rd
> +++ b/ld/testsuite/ld-arm/ifunc-5.rd
> @@ -4,5 +4,5 @@ There is no dynamic section in this file\.
> Relocation section '\.rel\.dyn' at offset 0x8000 contains 3 entries:
> Offset Info Type Sym\.Value Sym\. Name
> 0001100c ......a0 R_ARM_IRELATIVE
> -00011010 ......a0 R_ARM_IRELATIVE
> 00011014 ......a0 R_ARM_IRELATIVE
> +00011010 ......a0 R_ARM_IRELATIVE
> diff --git a/ld/testsuite/ld-arm/ifunc-6.rd b/ld/testsuite/ld-arm/ifunc-6.rd
> index 0fbfec5..04c18a9 100644
> --- a/ld/testsuite/ld-arm/ifunc-6.rd
> +++ b/ld/testsuite/ld-arm/ifunc-6.rd
> @@ -3,7 +3,7 @@ There is no dynamic section in this file\.
>
> Relocation section '\.rel\.dyn' at offset 0x8000 contains 4 entries:
> Offset Info Type Sym\.Value Sym\. Name
> -0001100c ......a0 R_ARM_IRELATIVE
> +00011018 ......a0 R_ARM_IRELATIVE
> 00011010 ......a0 R_ARM_IRELATIVE
> +0001100c ......a0 R_ARM_IRELATIVE
> 00011014 ......a0 R_ARM_IRELATIVE
> -00011018 ......a0 R_ARM_IRELATIVE
>
More information about the Binutils
mailing list