This is the mail archive of the
binutils@sourceware.org
mailing list for the binutils project.
Re: powepc64le gold linking problem
- From: Jay Foad <jay dot foad at gmail dot com>
- To: Jay Foad <jay dot foad at gmail dot com>, binutils at sourceware dot org
- Date: Mon, 24 Nov 2014 13:35:08 +0000
- Subject: Re: powepc64le gold linking problem
- Authentication-results: sourceware.org; auth=none
- References: <CANd1uZ==OJpGtmpYh3=kNSirC8SJ2YCVRzo+onipoh7OBSiDdA at mail dot gmail dot com> <20141124121555 dot GJ4477 at bubble dot grove dot modra dot org>
On 24 November 2014 at 12:15, Alan Modra <amodra@gmail.com> wrote:
> On Mon, Nov 24, 2014 at 11:02:41AM +0000, Jay Foad wrote:
>> Hi,
>>
>> I'm trying to investigate a problem with gold on powerpc64le linux. I
>> have a large test program which I can link and run successfully with
>> ld.bfd, but if I link with ld.gold the test segfaults in a plt stub
>> because r2 is not set up correctly. I have tracked it down to a call
>> to _ZN7testing8internal2RED1Ev, where it looks like r2 was not set up
>> correctly.
>>
>> The calling code looks like:
>>
>> 2cc: 01 00 00 48 bl 2cc
>> <_ZN45AddressSanitizer_InternalSimpleDeathTest_Test8TestBodyEv+0x2cc>
>> 2cc: R_PPC64_REL24 _ZN7testing8internal2RED1Ev
>>
>> The callee, in a different module, has:
>>
>> 0000000000000000 g F .text._ZN7testing8internal2RED2Ev
>> 0000000000000080 _ZN7testing8internal2RED1Ev
>> 0000000000000000 g F .text._ZN7testing8internal2RED2Ev
>> 0000000000000080 0x60 _ZN7testing8internal2RED2Ev
>>
>> Disassembly of section .text._ZN7testing8internal2RED2Ev:
>>
>> 0000000000000000 <_ZN7testing8internal2RED1Ev>:
>> 0: 00 00 4c 3c addis r2,r12,0
>> 0: R_PPC64_REL16_HA .TOC.
>> 4: 00 00 42 38 addi r2,r2,0
>> 4: R_PPC64_REL16_LO .TOC.+0x4
>> 8: a6 02 08 7c mflr r0
>> c: f8 ff e1 fb std r31,-8(r1)
>> ...
>>
>> After linking with gold, I can see that the call is a bl directly to
>> the global entry point, which is wrong, isn't it?
>
> Yes.
>
>> 000000001002de34 g F .text 0000000000000080
>> _ZN7testing8internal2RED1Ev
>> 000000001002de34 g F .text 0000000000000080 0x60
>> _ZN7testing8internal2RED2Ev
>> ...
>> 000000001002de34 <_ZN7testing8internal2RED1Ev>:
>> 1002de34: 13 00 4c 3c addis r2,r12,19
>> 1002de38: 84 aa 42 38 addi r2,r2,-21884
>> 1002de3c: a6 02 08 7c mflr r0
>> 1002de40: f8 ff e1 fb std r31,-8(r1)
>> ...
>> 100425f8: 3d b8 fe 4b bl 1002de34 <_ZN7testing8internal2RED1Ev>
>>
>> It seems a bit suspicious that there are two symbols
>> (_ZN7testing8internal2RED1Ev and _ZN7testing8internal2RED2Ev) with the
>> same address, but only one of them has st_other set to indicate that
>> the local entry point is two instructions past the global antry point.
>
> According to http://www.codesourcery.com/cxx-abi/abi.html#mangling the
> D1 symbol is a complete object destructor and the D2 symbol is a base
> object destructor. If they happen to be the same function, then they
> should have the same st_other bits. So how did that occur?
Ah. The .o file containing those desctructors was generated by Clang,
and it only has that problem (differening st_other bits) when it's
using its integrated assembler. I shall report this to the LLVM
people.
> You say
> ld.bfd links the project OK, so presumably the object defining the
> callee was linked with a ld -r stage. Is that correct?
No, it was generated by clang -c.
> (If not, I
> don't see how ld.bfd would link the object OK.)
Well somehow it manages to. Maybe it's something to do with this code
in ppc64_elf_branch_reloc (in bfd/elf64-ppc.c):
elf_symbol_type *elfsym = (elf_symbol_type *) symbol;
if (symbol->section->owner != abfd
&& abiversion (symbol->section->owner) >= 2)
{
unsigned int i;
for (i = 0; i < symbol->section->owner->symcount; ++i)
{
asymbol *symdef = symbol->section->owner->outsymbols[i];
if (strcmp (symdef->name, symbol->name) == 0)
{
elfsym = (elf_symbol_type *) symdef;
break;
}
}
}
reloc_entry->addend
+= PPC64_LOCAL_ENTRY_OFFSET (elfsym->internal_elf_sym.st_other);
I don't understand the purpose of this code, but it looks like it
might be intentionally using the st_other bits from a different
symbol.
Thanks for your help!
Jay.