-
Notifications
You must be signed in to change notification settings - Fork 13.5k
[llvm][lld] Support R_AARCH64_GOTPCREL32 #72584
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
@llvm/pr-subscribers-lld-elf @llvm/pr-subscribers-mc Author: None (PiJoules) ChangesThis is the follopw implementation to Full diff: https://github.com/llvm/llvm-project/pull/72584.diff 5 Files Affected:
diff --git a/lld/ELF/Arch/AArch64.cpp b/lld/ELF/Arch/AArch64.cpp
index 048f0ec30ebd283..32cff73955028e4 100644
--- a/lld/ELF/Arch/AArch64.cpp
+++ b/lld/ELF/Arch/AArch64.cpp
@@ -165,6 +165,8 @@ RelExpr AArch64::getRelExpr(RelType type, const Symbol &s,
case R_AARCH64_ADR_GOT_PAGE:
case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
return R_AARCH64_GOT_PAGE_PC;
+ case R_AARCH64_GOTPCREL32:
+ return R_GOT_PC;
case R_AARCH64_NONE:
return R_NONE;
default:
@@ -374,6 +376,7 @@ void AArch64::relocate(uint8_t *loc, const Relocation &rel,
write32(loc, val);
break;
case R_AARCH64_PLT32:
+ case R_AARCH64_GOTPCREL32:
checkInt(loc, val, 32, rel);
write32(loc, val);
break;
diff --git a/lld/test/ELF/aarch64-reloc-gotpcrel32.s b/lld/test/ELF/aarch64-reloc-gotpcrel32.s
new file mode 100644
index 000000000000000..7ea55bfc5b00aad
--- /dev/null
+++ b/lld/test/ELF/aarch64-reloc-gotpcrel32.s
@@ -0,0 +1,36 @@
+// REQUIRES: aarch64
+// RUN: llvm-mc -filetype=obj -triple=aarch64 %s -o %t.o
+// RUN: llvm-mc -filetype=obj -triple=aarch64 %S/Inputs/abs255.s -o %t255.o
+// RUN: ld.lld %t.o -o %t.so -shared
+// RUN: llvm-readobj -S %t.so | FileCheck --check-prefix=SEC %s
+// RUN: llvm-objdump --no-print-imm-hex -s -d %t.so | FileCheck %s
+
+
+// SEC: Name: .got (58)
+// SEC-NEXT: Type: SHT_PROGBITS (0x1)
+// SEC-NEXT: Flags [ (0x3)
+// SEC-NEXT: SHF_ALLOC (0x2)
+// SEC-NEXT: SHF_WRITE (0x1)
+// SEC-NEXT: ]
+// SEC-NEXT: Address: 0x20350
+// SEC-NEXT: Offset: 0x350
+// SEC-NEXT: Size: 8
+// SEC-NEXT: Link: 0
+// SEC-NEXT: Info: 0
+// SEC-NEXT: AddressAlignment: 8
+// SEC-NEXT: EntrySize: 0
+
+ .section .data
+ .globl bar
+bar:
+
+ .globl _start
+_start:
+// bar@GOTPCREL = 0x20350 (got entry for `bar`) - 0x30358 (.) = 0xfffefff8
+// bar@GOTPCREL+4 = 0x20350 (got entry for `bar`) - 0x3035c (.) + 4 = 0xfffefff8
+// bar@GOTPCREL-4 = 0x20350 (got entry for `bar`) - 0x30360 (.) + 4 = 0xfffeffec
+// CHECK: Contents of section .data:
+// CHECK: 30358 f8fffeff f8fffeff ecfffeff
+ .word bar@GOTPCREL
+ .word bar@GOTPCREL+4
+ .word bar@GOTPCREL-4
diff --git a/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def b/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def
index b507109b19e1b90..fcaea2aceed5209 100644
--- a/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def
+++ b/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def
@@ -59,6 +59,7 @@ ELF_RELOC(R_AARCH64_ADR_GOT_PAGE, 0x137)
ELF_RELOC(R_AARCH64_LD64_GOT_LO12_NC, 0x138)
ELF_RELOC(R_AARCH64_LD64_GOTPAGE_LO15, 0x139)
ELF_RELOC(R_AARCH64_PLT32, 0x13a)
+ELF_RELOC(R_AARCH64_GOTPCREL32, 0x13b)
ELF_RELOC(R_AARCH64_TLSGD_ADR_PREL21, 0x200)
ELF_RELOC(R_AARCH64_TLSGD_ADR_PAGE21, 0x201)
ELF_RELOC(R_AARCH64_TLSGD_ADD_LO12_NC, 0x202)
@@ -166,6 +167,7 @@ ELF_RELOC(R_AARCH64_P32_ADR_GOT_PAGE, 0x01a)
ELF_RELOC(R_AARCH64_P32_LD32_GOT_LO12_NC, 0x01b)
ELF_RELOC(R_AARCH64_P32_LD32_GOTPAGE_LO14, 0x01c)
ELF_RELOC(R_AARCH64_P32_PLT32, 0x01d)
+ELF_RELOC(R_AARCH64_P32_GOTPCREL32, 0x01e)
ELF_RELOC(R_AARCH64_P32_TLSGD_ADR_PREL21, 0x050)
ELF_RELOC(R_AARCH64_P32_TLSGD_ADR_PAGE21, 0x051)
ELF_RELOC(R_AARCH64_P32_TLSGD_ADD_LO12_NC, 0x052)
diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp
index 9de40661298ccad..996fd1614d19f57 100644
--- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp
+++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp
@@ -120,7 +120,8 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx,
assert((!Target.getSymA() ||
Target.getSymA()->getKind() == MCSymbolRefExpr::VK_None ||
- Target.getSymA()->getKind() == MCSymbolRefExpr::VK_PLT) &&
+ Target.getSymA()->getKind() == MCSymbolRefExpr::VK_PLT ||
+ Target.getSymA()->getKind() == MCSymbolRefExpr::VK_GOTPCREL) &&
"Should only be expression-level modifiers here");
assert((!Target.getSymB() ||
@@ -202,7 +203,9 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx,
case FK_Data_2:
return R_CLS(ABS16);
case FK_Data_4:
- return R_CLS(ABS32);
+ return Target.getAccessVariant() == MCSymbolRefExpr::VK_GOTPCREL
+ ? R_CLS(GOTPCREL32)
+ : R_CLS(ABS32);
case FK_Data_8:
if (IsILP32) {
Ctx.reportError(Fixup.getLoc(),
diff --git a/llvm/test/MC/AArch64/elf-reloc-gotpcrel32.s b/llvm/test/MC/AArch64/elf-reloc-gotpcrel32.s
new file mode 100644
index 000000000000000..afbcaad9e1dfdcc
--- /dev/null
+++ b/llvm/test/MC/AArch64/elf-reloc-gotpcrel32.s
@@ -0,0 +1,14 @@
+// RUN: llvm-mc -triple=aarch64 -filetype=obj %s -o - | \
+// RUN: llvm-readobj -r - | FileCheck %s
+
+ .section .data
+this:
+ .word this@GOTPCREL
+ .word extern_sym@GOTPCREL+4
+ .word negative_offset@GOTPCREL-4
+
+// CHECK: Section ({{.*}}) .rela.data
+// CHECK-NEXT: 0x0 R_AARCH64_GOTPCREL32 this 0x0
+// CHECK-NEXT: 0x4 R_AARCH64_GOTPCREL32 extern_sym 0x4
+// CHECK-NEXT: 0x8 R_AARCH64_GOTPCREL32 negative_offset 0xFFFFFFFFFFFFFFFC
+// CHECK-NEXT: }
|
@llvm/pr-subscribers-backend-aarch64 Author: None (PiJoules) ChangesThis is the follopw implementation to Full diff: https://github.com/llvm/llvm-project/pull/72584.diff 5 Files Affected:
diff --git a/lld/ELF/Arch/AArch64.cpp b/lld/ELF/Arch/AArch64.cpp
index 048f0ec30ebd283..32cff73955028e4 100644
--- a/lld/ELF/Arch/AArch64.cpp
+++ b/lld/ELF/Arch/AArch64.cpp
@@ -165,6 +165,8 @@ RelExpr AArch64::getRelExpr(RelType type, const Symbol &s,
case R_AARCH64_ADR_GOT_PAGE:
case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
return R_AARCH64_GOT_PAGE_PC;
+ case R_AARCH64_GOTPCREL32:
+ return R_GOT_PC;
case R_AARCH64_NONE:
return R_NONE;
default:
@@ -374,6 +376,7 @@ void AArch64::relocate(uint8_t *loc, const Relocation &rel,
write32(loc, val);
break;
case R_AARCH64_PLT32:
+ case R_AARCH64_GOTPCREL32:
checkInt(loc, val, 32, rel);
write32(loc, val);
break;
diff --git a/lld/test/ELF/aarch64-reloc-gotpcrel32.s b/lld/test/ELF/aarch64-reloc-gotpcrel32.s
new file mode 100644
index 000000000000000..7ea55bfc5b00aad
--- /dev/null
+++ b/lld/test/ELF/aarch64-reloc-gotpcrel32.s
@@ -0,0 +1,36 @@
+// REQUIRES: aarch64
+// RUN: llvm-mc -filetype=obj -triple=aarch64 %s -o %t.o
+// RUN: llvm-mc -filetype=obj -triple=aarch64 %S/Inputs/abs255.s -o %t255.o
+// RUN: ld.lld %t.o -o %t.so -shared
+// RUN: llvm-readobj -S %t.so | FileCheck --check-prefix=SEC %s
+// RUN: llvm-objdump --no-print-imm-hex -s -d %t.so | FileCheck %s
+
+
+// SEC: Name: .got (58)
+// SEC-NEXT: Type: SHT_PROGBITS (0x1)
+// SEC-NEXT: Flags [ (0x3)
+// SEC-NEXT: SHF_ALLOC (0x2)
+// SEC-NEXT: SHF_WRITE (0x1)
+// SEC-NEXT: ]
+// SEC-NEXT: Address: 0x20350
+// SEC-NEXT: Offset: 0x350
+// SEC-NEXT: Size: 8
+// SEC-NEXT: Link: 0
+// SEC-NEXT: Info: 0
+// SEC-NEXT: AddressAlignment: 8
+// SEC-NEXT: EntrySize: 0
+
+ .section .data
+ .globl bar
+bar:
+
+ .globl _start
+_start:
+// bar@GOTPCREL = 0x20350 (got entry for `bar`) - 0x30358 (.) = 0xfffefff8
+// bar@GOTPCREL+4 = 0x20350 (got entry for `bar`) - 0x3035c (.) + 4 = 0xfffefff8
+// bar@GOTPCREL-4 = 0x20350 (got entry for `bar`) - 0x30360 (.) + 4 = 0xfffeffec
+// CHECK: Contents of section .data:
+// CHECK: 30358 f8fffeff f8fffeff ecfffeff
+ .word bar@GOTPCREL
+ .word bar@GOTPCREL+4
+ .word bar@GOTPCREL-4
diff --git a/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def b/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def
index b507109b19e1b90..fcaea2aceed5209 100644
--- a/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def
+++ b/llvm/include/llvm/BinaryFormat/ELFRelocs/AArch64.def
@@ -59,6 +59,7 @@ ELF_RELOC(R_AARCH64_ADR_GOT_PAGE, 0x137)
ELF_RELOC(R_AARCH64_LD64_GOT_LO12_NC, 0x138)
ELF_RELOC(R_AARCH64_LD64_GOTPAGE_LO15, 0x139)
ELF_RELOC(R_AARCH64_PLT32, 0x13a)
+ELF_RELOC(R_AARCH64_GOTPCREL32, 0x13b)
ELF_RELOC(R_AARCH64_TLSGD_ADR_PREL21, 0x200)
ELF_RELOC(R_AARCH64_TLSGD_ADR_PAGE21, 0x201)
ELF_RELOC(R_AARCH64_TLSGD_ADD_LO12_NC, 0x202)
@@ -166,6 +167,7 @@ ELF_RELOC(R_AARCH64_P32_ADR_GOT_PAGE, 0x01a)
ELF_RELOC(R_AARCH64_P32_LD32_GOT_LO12_NC, 0x01b)
ELF_RELOC(R_AARCH64_P32_LD32_GOTPAGE_LO14, 0x01c)
ELF_RELOC(R_AARCH64_P32_PLT32, 0x01d)
+ELF_RELOC(R_AARCH64_P32_GOTPCREL32, 0x01e)
ELF_RELOC(R_AARCH64_P32_TLSGD_ADR_PREL21, 0x050)
ELF_RELOC(R_AARCH64_P32_TLSGD_ADR_PAGE21, 0x051)
ELF_RELOC(R_AARCH64_P32_TLSGD_ADD_LO12_NC, 0x052)
diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp
index 9de40661298ccad..996fd1614d19f57 100644
--- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp
+++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp
@@ -120,7 +120,8 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx,
assert((!Target.getSymA() ||
Target.getSymA()->getKind() == MCSymbolRefExpr::VK_None ||
- Target.getSymA()->getKind() == MCSymbolRefExpr::VK_PLT) &&
+ Target.getSymA()->getKind() == MCSymbolRefExpr::VK_PLT ||
+ Target.getSymA()->getKind() == MCSymbolRefExpr::VK_GOTPCREL) &&
"Should only be expression-level modifiers here");
assert((!Target.getSymB() ||
@@ -202,7 +203,9 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx,
case FK_Data_2:
return R_CLS(ABS16);
case FK_Data_4:
- return R_CLS(ABS32);
+ return Target.getAccessVariant() == MCSymbolRefExpr::VK_GOTPCREL
+ ? R_CLS(GOTPCREL32)
+ : R_CLS(ABS32);
case FK_Data_8:
if (IsILP32) {
Ctx.reportError(Fixup.getLoc(),
diff --git a/llvm/test/MC/AArch64/elf-reloc-gotpcrel32.s b/llvm/test/MC/AArch64/elf-reloc-gotpcrel32.s
new file mode 100644
index 000000000000000..afbcaad9e1dfdcc
--- /dev/null
+++ b/llvm/test/MC/AArch64/elf-reloc-gotpcrel32.s
@@ -0,0 +1,14 @@
+// RUN: llvm-mc -triple=aarch64 -filetype=obj %s -o - | \
+// RUN: llvm-readobj -r - | FileCheck %s
+
+ .section .data
+this:
+ .word this@GOTPCREL
+ .word extern_sym@GOTPCREL+4
+ .word negative_offset@GOTPCREL-4
+
+// CHECK: Section ({{.*}}) .rela.data
+// CHECK-NEXT: 0x0 R_AARCH64_GOTPCREL32 this 0x0
+// CHECK-NEXT: 0x4 R_AARCH64_GOTPCREL32 extern_sym 0x4
+// CHECK-NEXT: 0x8 R_AARCH64_GOTPCREL32 negative_offset 0xFFFFFFFFFFFFFFFC
+// CHECK-NEXT: }
|
I only discovered the |
a0b6255
to
958ec66
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Other than one line about the ILP32 code LGTM.
Please do tell us if you need ILP32 support and we can add the code to the ABI.
958ec66
to
718b1c5
Compare
@@ -0,0 +1,11 @@ | |||
// REQUIRES: aarch64 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Newer tests place overflow tests (RUN: not ld.lld ...
) and regular tests (RUN: ld.lld ...
) in one file so that the boundary is clearer.
aarch64-reloc-plt32.s
is a good example
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For PLT32 I can put all the tests in one file since foo@PLT
can be relaxed to foo
if it's defined in one of the other input files, but I don't think the same can work for foo@GOTPCREL
since this can't be relaxed to anything that could be defined in a separate input file.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you perhaps have another example I can follow?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Perhaps you can use more than one symbol in a test.
Since the error message contains the bounds (in [-2147483648, 2147483647]
), I think we don't need to make an extreme test.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Updated tests
I don't have any more comments, thanks for making the earlier changes. Happy for MaskRay to approve when his comments have been addressed. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is mostly good, just needing some test changes.
718b1c5
to
2353935
Compare
This is the follopw implementation to ARM-software/abi-aa#223 that supports this relocation in llvm and lld.
2353935
to
43a19d6
Compare
This is the follopw implementation to ARM-software/abi-aa#223 that supports this relocation in llvm and lld.
This reverts the MC changes from commit 04a906e, which cause failures when linking with gold on arm64.
Partially revert "[llvm][lld] Support R_AARCH64_GOTPCREL32 (llvm#72584)"
…lvm#72584)"" This reverts commit f1cbfe9, which ended up causing other failures.
Revert "Partially revert "[llvm][lld] Support R_AARCH64_GOTPCREL32 (llvm#72584)""
This is the follopw implementation to
ARM-software/abi-aa#223 that supports this relocation in llvm and lld.