[llvm] r349799 - [MC] [AArch64] Support resolving fixups for abs_g0 etc.
Eli Friedman via llvm-commits
llvm-commits at lists.llvm.org
Thu Dec 20 11:38:07 PST 2018
Author: efriedma
Date: Thu Dec 20 11:38:07 2018
New Revision: 349799
URL: http://llvm.org/viewvc/llvm-project?rev=349799&view=rev
Log:
[MC] [AArch64] Support resolving fixups for abs_g0 etc.
This requires a bit more code than other fixups, to distingush between
abs_g0/abs_g1/etc. Actually, I think some of the other fixups are
missing some checks, but I won't try to address that here.
I haven't seen any real-world code that uses a construct like this, but
it clearly should work, and we're considering using it in the
implementation of localescape/localrecover on Windows (see
https://reviews.llvm.org/D53540). I've verified that binutils produces
the same code as llvm-mc for the testcase.
This currently doesn't include support for the *_s variants (that
requires a bit more work to set the opcode).
Differential Revision: https://reviews.llvm.org/D55896
Added:
llvm/trunk/test/MC/AArch64/fixup-absolute.s
Modified:
llvm/trunk/lib/Target/AArch64/MCTargetDesc/AArch64AsmBackend.cpp
llvm/trunk/test/MC/AArch64/fixup-out-of-range.s
Modified: llvm/trunk/lib/Target/AArch64/MCTargetDesc/AArch64AsmBackend.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/AArch64/MCTargetDesc/AArch64AsmBackend.cpp?rev=349799&r1=349798&r2=349799&view=diff
==============================================================================
--- llvm/trunk/lib/Target/AArch64/MCTargetDesc/AArch64AsmBackend.cpp (original)
+++ llvm/trunk/lib/Target/AArch64/MCTargetDesc/AArch64AsmBackend.cpp Thu Dec 20 11:38:07 2018
@@ -110,11 +110,11 @@ static unsigned getFixupKindNumBytes(uns
case FK_Data_1:
return 1;
- case AArch64::fixup_aarch64_movw:
case FK_Data_2:
case FK_SecRel_2:
return 2;
+ case AArch64::fixup_aarch64_movw:
case AArch64::fixup_aarch64_pcrel_branch14:
case AArch64::fixup_aarch64_add_imm12:
case AArch64::fixup_aarch64_ldst_imm12_scale1:
@@ -145,9 +145,9 @@ static unsigned AdrImmBits(unsigned Valu
return (hi19 << 5) | (lo2 << 29);
}
-static uint64_t adjustFixupValue(const MCFixup &Fixup, uint64_t Value,
- MCContext &Ctx, const Triple &TheTriple,
- bool IsResolved) {
+static uint64_t adjustFixupValue(const MCFixup &Fixup, const MCValue &Target,
+ uint64_t Value, MCContext &Ctx,
+ const Triple &TheTriple, bool IsResolved) {
unsigned Kind = Fixup.getKind();
int64_t SignedValue = static_cast<int64_t>(Value);
switch (Kind) {
@@ -215,10 +215,51 @@ static uint64_t adjustFixupValue(const M
if (Value & 0xf)
Ctx.reportError(Fixup.getLoc(), "fixup must be 16-byte aligned");
return Value >> 4;
- case AArch64::fixup_aarch64_movw:
- Ctx.reportError(Fixup.getLoc(),
- "no resolvable MOVZ/MOVK fixups supported yet");
+ case AArch64::fixup_aarch64_movw: {
+ AArch64MCExpr::VariantKind RefKind =
+ static_cast<AArch64MCExpr::VariantKind>(Target.getRefKind());
+ if (AArch64MCExpr::getSymbolLoc(RefKind) != AArch64MCExpr::VK_ABS) {
+ if (AArch64MCExpr::getSymbolLoc(RefKind) != AArch64MCExpr::VK_SABS) {
+ // VK_GOTTPREL, VK_TPREL, VK_DTPREL are movw fixups, but they can't
+ // ever be resolved in the assembler.
+ Ctx.reportError(Fixup.getLoc(),
+ "relocation for a thread-local variable points to an "
+ "absolute symbol");
+ return Value;
+ }
+ Ctx.reportError(Fixup.getLoc(),
+ "resolvable R_AARCH64_MOVW_SABS_G* fixups are not "
+ "yet implemented");
+ return Value;
+ }
+ if (!IsResolved) {
+ // FIXME: Figure out when this can actually happen, and verify our
+ // behavior.
+ Ctx.reportError(Fixup.getLoc(), "unresolved movw fixup not yet "
+ "implemented");
+ return Value;
+ }
+ switch (AArch64MCExpr::getAddressFrag(RefKind)) {
+ case AArch64MCExpr::VK_G0:
+ break;
+ case AArch64MCExpr::VK_G1:
+ Value = Value >> 16;
+ break;
+ case AArch64MCExpr::VK_G2:
+ Value = Value >> 32;
+ break;
+ case AArch64MCExpr::VK_G3:
+ Value = Value >> 48;
+ break;
+ default:
+ llvm_unreachable("Variant kind doesn't correspond to fixup");
+ }
+ if (RefKind & AArch64MCExpr::VK_NC)
+ Value &= 0xFFFF;
+ else if (Value > 0xFFFF)
+ Ctx.reportError(Fixup.getLoc(), "fixup value out of range");
return Value;
+ }
case AArch64::fixup_aarch64_pcrel_branch14:
// Signed 16-bit immediate
if (SignedValue > 32767 || SignedValue < -32768)
@@ -296,7 +337,7 @@ void AArch64AsmBackend::applyFixup(const
MCFixupKindInfo Info = getFixupKindInfo(Fixup.getKind());
MCContext &Ctx = Asm.getContext();
// Apply any target-specific value adjustments.
- Value = adjustFixupValue(Fixup, Value, Ctx, TheTriple, IsResolved);
+ Value = adjustFixupValue(Fixup, Target, Value, Ctx, TheTriple, IsResolved);
// Shift the value into position.
Value <<= Info.TargetOffset;
Added: llvm/trunk/test/MC/AArch64/fixup-absolute.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/AArch64/fixup-absolute.s?rev=349799&view=auto
==============================================================================
--- llvm/trunk/test/MC/AArch64/fixup-absolute.s (added)
+++ llvm/trunk/test/MC/AArch64/fixup-absolute.s Thu Dec 20 11:38:07 2018
@@ -0,0 +1,21 @@
+// RUN: llvm-mc -triple aarch64--none-eabi -filetype obj < %s -o - | llvm-objdump -d - | FileCheck %s
+
+// CHECK: mov x0, #1311673391471656960
+movz x0, #:abs_g3:fourpart
+// CHECK: mov x0, #20014547599360
+movz x0, #:abs_g2:threepart
+// CHECK: movk x0, #22136, lsl #32
+movk x0, #:abs_g2_nc:fourpart
+// CHECK: mov x0, #305397760
+movz x0, #:abs_g1:twopart
+// CHECK: movk x0, #37035, lsl #16
+movk x0, #:abs_g1_nc:fourpart
+// CHECK: mov x0, #4660
+movz x0, #:abs_g0:onepart
+// CHECK: movk x0, #52719
+movk x0, #:abs_g0_nc:fourpart
+
+onepart = 0x1234
+twopart = 0x12345678
+threepart = 0x1234567890AB
+fourpart = 0x1234567890ABCDEF
Modified: llvm/trunk/test/MC/AArch64/fixup-out-of-range.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/AArch64/fixup-out-of-range.s?rev=349799&r1=349798&r2=349799&view=diff
==============================================================================
--- llvm/trunk/test/MC/AArch64/fixup-out-of-range.s (original)
+++ llvm/trunk/test/MC/AArch64/fixup-out-of-range.s Thu Dec 20 11:38:07 2018
@@ -55,6 +55,19 @@
// CHECK: :[[@LINE+1]]:{{[0-9]+}}: error: fixup not sufficiently aligned
b unaligned
+// CHECK: :[[@LINE+1]]:{{[0-9]+}}: error: fixup value out of range
+ movz x0, #:abs_g0:value1
+
+// CHECK: :[[@LINE+1]]:{{[0-9]+}}: error: fixup value out of range
+ movz x0, #:abs_g1:value2
+
+// CHECK: :[[@LINE+1]]:{{[0-9]+}}: error: resolvable R_AARCH64_MOVW_SABS_G* fixups are not yet implemented
+ movz x0, #:abs_g0_s:value1
+
+// CHECK: :[[@LINE+1]]:{{[0-9]+}}: error: relocation for a thread-local variable points to an absolute symbol
+ movz x0, #:tprel_g0:value1
+
+
.byte 0
unaligned:
.byte 0
@@ -63,3 +76,5 @@ unaligned:
.balign 8
distant:
.word 0
+value1 = 0x12345678
+value2 = 0x123456789
More information about the llvm-commits
mailing list