diff options
author | Adhemerval Zanella <adhemerval.zanella@linaro.org> | 2016-04-08 14:10:41 +0000 |
---|---|---|
committer | Adhemerval Zanella <adhemerval.zanella@linaro.org> | 2016-04-08 14:10:41 +0000 |
commit | 15cba9e7e543ae1593f2e62ed4166c446cabbeb7 (patch) | |
tree | 46926b683ee892f8d8e7f5359dea887056d06d20 | |
parent | 954ba21f852534c24dc1caf023d957adc06eef20 (diff) | |
download | bcm5719-llvm-15cba9e7e543ae1593f2e62ed4166c446cabbeb7.tar.gz bcm5719-llvm-15cba9e7e543ae1593f2e62ed4166c446cabbeb7.zip |
[lld] [ELF/AARCH64] Fix dynamic relocation from PIC GOT access
This patch fixes dynamic relocation creation from GOT access in dynamic
objects on aarch64. Current code creates a plt relative one
(R_AARCH64_JUMP_SLOT) instead of a got relative (R_AARCH64_GLOB_DAT).
It leads the programs fails with:
$ cat t.cc
std::string test = "hello...\n";
int main ()
{
printf ("%s\n", test.c_str());
return 0;
}
$ clang++ t.cc -fpic -o t
$ ./t
hello...
Segmentation fault (core dumped)
Due the fact it will try to access the plt instead of the got for
__cxa_atexit registration for the std::string destruction. It will
lead in a bogus function address in atexit.
llvm-svn: 265784
-rw-r--r-- | lld/ELF/Target.cpp | 5 | ||||
-rw-r--r-- | lld/test/ELF/aarch64-fpic-got.s | 18 |
2 files changed, 23 insertions, 0 deletions
diff --git a/lld/ELF/Target.cpp b/lld/ELF/Target.cpp index b5f5dd18745..5c92fbc93a7 100644 --- a/lld/ELF/Target.cpp +++ b/lld/ELF/Target.cpp @@ -170,6 +170,7 @@ public: bool isRelRelative(uint32_t Type) const override; bool needsCopyRelImpl(uint32_t Type) const override; bool needsGot(uint32_t Type, const SymbolBody &S) const override; + bool refersToGotEntry(uint32_t Type) const override; bool needsPltImpl(uint32_t Type) const override; void relocateOne(uint8_t *Loc, uint8_t *BufEnd, uint32_t Type, uint64_t P, uint64_t SA) const override; @@ -1381,6 +1382,10 @@ bool AArch64TargetInfo::needsGot(uint32_t Type, const SymbolBody &S) const { } } +bool AArch64TargetInfo::refersToGotEntry(uint32_t Type) const { + return Type == R_AARCH64_ADR_GOT_PAGE || Type == R_AARCH64_LD64_GOT_LO12_NC; +} + bool AArch64TargetInfo::needsPltImpl(uint32_t Type) const { switch (Type) { default: diff --git a/lld/test/ELF/aarch64-fpic-got.s b/lld/test/ELF/aarch64-fpic-got.s new file mode 100644 index 00000000000..70b2a7a76f8 --- /dev/null +++ b/lld/test/ELF/aarch64-fpic-got.s @@ -0,0 +1,18 @@ +# REQUIRES: aarch64 + +# RUN: llvm-mc -filetype=obj -triple=aarch64-none-linux %s -o %t.o +# RUN: llvm-mc -filetype=obj -triple=aarch64-none-linux %p/Inputs/shared.s -o %t-lib.o +# RUN: ld.lld -shared %t-lib.o -o %t-lib.so +# RUN: ld.lld %t-lib.so %t.o -o %t.exe +# RUN: llvm-readobj -dyn-relocations %t.exe | FileCheck %s + +## Checks if got access to dynamic objects is done through a got relative +## dynamic relocation and not using plt relative (R_AARCH64_JUMP_SLOT). +# CHECK: Dynamic Relocations { +# CHECK-NEXT: 0x{{[0-9A-F]+}} R_AARCH64_GLOB_DAT bar 0x0 +# CHECK-NEXT: } + +.globl _start +_start: + adrp x0, :got:bar + ldr x0, [x0, :got_lo12:bar] |