diff options
author | wanglei <wanglei@loongson.cn> | 2022-08-20 12:06:45 +0800 |
---|---|---|
committer | Weining Lu <luweining@loongson.cn> | 2022-08-20 12:07:07 +0800 |
commit | 1dbe8561e7b1190da33d2e248f171816ea9d108f (patch) | |
tree | 06c583a214d0df9815c6c045129f9ad42d0db797 | |
parent | c2ee21cf3f863dbe48bd6decf896b41891808647 (diff) | |
download | llvm-1dbe8561e7b1190da33d2e248f171816ea9d108f.zip llvm-1dbe8561e7b1190da33d2e248f171816ea9d108f.tar.gz llvm-1dbe8561e7b1190da33d2e248f171816ea9d108f.tar.bz2 |
[MC][LoongArch] Make .reloc support arbitrary relocation types
Similar to D76746 (ARM), D76754 (AArch64), D77018 (RISCV) and
llvmorg-11-init-6967-g152d14da64c (x86)
Differential Revision: https://reviews.llvm.org/D132119
4 files changed, 80 insertions, 1 deletions
diff --git a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.cpp b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.cpp index ea2c92b..dc98475 100644 --- a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.cpp +++ b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.cpp @@ -22,6 +22,22 @@ using namespace llvm; +Optional<MCFixupKind> LoongArchAsmBackend::getFixupKind(StringRef Name) const { + if (STI.getTargetTriple().isOSBinFormatELF()) { + auto Type = llvm::StringSwitch<unsigned>(Name) +#define ELF_RELOC(X, Y) .Case(#X, Y) +#include "llvm/BinaryFormat/ELFRelocs/LoongArch.def" +#undef ELF_RELOC + .Case("BFD_RELOC_NONE", ELF::R_LARCH_NONE) + .Case("BFD_RELOC_32", ELF::R_LARCH_32) + .Case("BFD_RELOC_64", ELF::R_LARCH_64) + .Default(-1u); + if (Type != -1u) + return static_cast<MCFixupKind>(FirstLiteralRelocationKind + Type); + } + return None; +} + const MCFixupKindInfo & LoongArchAsmBackend::getFixupKindInfo(MCFixupKind Kind) const { const static MCFixupKindInfo Infos[] = { @@ -38,6 +54,11 @@ LoongArchAsmBackend::getFixupKindInfo(MCFixupKind Kind) const { static_assert((array_lengthof(Infos)) == LoongArch::NumTargetFixupKinds, "Not all fixup kinds added to Infos array"); + // Fixup kinds from .reloc directive are like R_LARCH_NONE. They + // do not require any extra processing. + if (Kind >= FirstLiteralRelocationKind) + return MCAsmBackend::getFixupKindInfo(FK_NONE); + if (Kind < FirstTargetFixupKind) return MCAsmBackend::getFixupKindInfo(Kind); @@ -59,6 +80,8 @@ void LoongArchAsmBackend::applyFixup(const MCAssembler &Asm, bool LoongArchAsmBackend::shouldForceRelocation(const MCAssembler &Asm, const MCFixup &Fixup, const MCValue &Target) { + if (Fixup.getKind() >= FirstLiteralRelocationKind) + return true; // TODO: Determine which relocation require special processing at linking // time. return false; diff --git a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.h b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.h index 449554f..a69f8dc 100644 --- a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.h +++ b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchAsmBackend.h @@ -23,12 +23,14 @@ namespace llvm { class LoongArchAsmBackend : public MCAsmBackend { + const MCSubtargetInfo &STI; uint8_t OSABI; bool Is64Bit; public: LoongArchAsmBackend(const MCSubtargetInfo &STI, uint8_t OSABI, bool Is64Bit) - : MCAsmBackend(support::little), OSABI(OSABI), Is64Bit(Is64Bit) {} + : MCAsmBackend(support::little), STI(STI), OSABI(OSABI), + Is64Bit(Is64Bit) {} ~LoongArchAsmBackend() override {} void applyFixup(const MCAssembler &Asm, const MCFixup &Fixup, @@ -49,6 +51,8 @@ public: return LoongArch::NumTargetFixupKinds; } + Optional<MCFixupKind> getFixupKind(StringRef Name) const override; + const MCFixupKindInfo &getFixupKindInfo(MCFixupKind Kind) const override; void relaxInstruction(MCInst &Inst, diff --git a/llvm/test/MC/LoongArch/Relocations/reloc-directive-err.s b/llvm/test/MC/LoongArch/Relocations/reloc-directive-err.s new file mode 100644 index 0000000..e01209d --- /dev/null +++ b/llvm/test/MC/LoongArch/Relocations/reloc-directive-err.s @@ -0,0 +1,6 @@ +# RUN: llvm-mc --triple=loongarch64 %s |& FileCheck --check-prefix=PRINT %s +# RUN: not llvm-mc --filetype=obj --triple=loongarch64 %s -o /dev/null |& FileCheck %s + +# PRINT: .reloc 0, R_INVALID, 0 +# CHECK: {{.*}}.s:[[# @LINE+1]]:11: error: unknown relocation name +.reloc 0, R_INVALID, 0 diff --git a/llvm/test/MC/LoongArch/Relocations/reloc-directive.s b/llvm/test/MC/LoongArch/Relocations/reloc-directive.s new file mode 100644 index 0000000..f900f17c --- /dev/null +++ b/llvm/test/MC/LoongArch/Relocations/reloc-directive.s @@ -0,0 +1,46 @@ +# RUN: llvm-mc --triple=loongarch64 %s | FileCheck --check-prefix=PRINT %s +# RUN: llvm-mc --filetype=obj --triple=loongarch64 %s \ +# RUN: | llvm-readobj -r - | FileCheck %s + +# PRINT: .reloc 8, R_LARCH_NONE, .data +# PRINT: .reloc 4, R_LARCH_NONE, foo+4 +# PRINT: .reloc 0, R_LARCH_NONE, 8 +# PRINT: .reloc 0, R_LARCH_32, .data+2 +# PRINT: .reloc 0, R_LARCH_TLS_DTPMOD32, foo+3 +# PRINT: .reloc 0, R_LARCH_IRELATIVE, 5 +# PRINT: .reloc 0, BFD_RELOC_NONE, 9 +# PRINT-NEXT: .reloc 0, BFD_RELOC_32, 9 +# PRINT-NEXT: .reloc 0, BFD_RELOC_64, 9 + +.text + ret + nop + nop + .reloc 8, R_LARCH_NONE, .data + .reloc 4, R_LARCH_NONE, foo+4 + .reloc 0, R_LARCH_NONE, 8 + + .reloc 0, R_LARCH_32, .data+2 + .reloc 0, R_LARCH_TLS_DTPMOD32, foo+3 + .reloc 0, R_LARCH_IRELATIVE, 5 + + .reloc 0, BFD_RELOC_NONE, 9 + .reloc 0, BFD_RELOC_32, 9 + .reloc 0, BFD_RELOC_64, 9 + +.data +.globl foo +foo: + .word 0 + .word 0 + .word 0 + +# CHECK: 0x8 R_LARCH_NONE .data 0x0 +# CHECK-NEXT: 0x4 R_LARCH_NONE foo 0x4 +# CHECK-NEXT: 0x0 R_LARCH_NONE - 0x8 +# CHECK-NEXT: 0x0 R_LARCH_32 .data 0x2 +# CHECK-NEXT: 0x0 R_LARCH_TLS_DTPMOD32 foo 0x3 +# CHECK-NEXT: 0x0 R_LARCH_IRELATIVE - 0x5 +# CHECK-NEXT: 0x0 R_LARCH_NONE - 0x9 +# CHECK-NEXT: 0x0 R_LARCH_32 - 0x9 +# CHECK-NEXT: 0x0 R_LARCH_64 - 0x9 |