Run DCE after a LoopFlatten test to reduce spurious output [nfc]
[llvm-project.git] / llvm / lib / Target / RISCV / MCTargetDesc / RISCVELFObjectWriter.cpp
blob0799267eaf7c76986850ad9a9461d878f5ac62b8
1 //===-- RISCVELFObjectWriter.cpp - RISC-V ELF Writer ----------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
9 #include "MCTargetDesc/RISCVFixupKinds.h"
10 #include "MCTargetDesc/RISCVMCExpr.h"
11 #include "MCTargetDesc/RISCVMCTargetDesc.h"
12 #include "llvm/MC/MCContext.h"
13 #include "llvm/MC/MCELFObjectWriter.h"
14 #include "llvm/MC/MCFixup.h"
15 #include "llvm/MC/MCObjectWriter.h"
16 #include "llvm/MC/MCValue.h"
17 #include "llvm/Support/ErrorHandling.h"
19 using namespace llvm;
21 namespace {
22 class RISCVELFObjectWriter : public MCELFObjectTargetWriter {
23 public:
24 RISCVELFObjectWriter(uint8_t OSABI, bool Is64Bit);
26 ~RISCVELFObjectWriter() override;
28 // Return true if the given relocation must be with a symbol rather than
29 // section plus offset.
30 bool needsRelocateWithSymbol(const MCValue &Val, const MCSymbol &Sym,
31 unsigned Type) const override {
32 // TODO: this is very conservative, update once RISC-V psABI requirements
33 // are clarified.
34 return true;
37 protected:
38 unsigned getRelocType(MCContext &Ctx, const MCValue &Target,
39 const MCFixup &Fixup, bool IsPCRel) const override;
43 RISCVELFObjectWriter::RISCVELFObjectWriter(uint8_t OSABI, bool Is64Bit)
44 : MCELFObjectTargetWriter(Is64Bit, OSABI, ELF::EM_RISCV,
45 /*HasRelocationAddend*/ true) {}
47 RISCVELFObjectWriter::~RISCVELFObjectWriter() = default;
49 unsigned RISCVELFObjectWriter::getRelocType(MCContext &Ctx,
50 const MCValue &Target,
51 const MCFixup &Fixup,
52 bool IsPCRel) const {
53 const MCExpr *Expr = Fixup.getValue();
54 // Determine the type of the relocation
55 unsigned Kind = Fixup.getTargetKind();
56 if (Kind >= FirstLiteralRelocationKind)
57 return Kind - FirstLiteralRelocationKind;
58 if (IsPCRel) {
59 switch (Kind) {
60 default:
61 Ctx.reportError(Fixup.getLoc(), "unsupported relocation type");
62 return ELF::R_RISCV_NONE;
63 case FK_Data_4:
64 case FK_PCRel_4:
65 return Target.getAccessVariant() == MCSymbolRefExpr::VK_PLT
66 ? ELF::R_RISCV_PLT32
67 : ELF::R_RISCV_32_PCREL;
68 case RISCV::fixup_riscv_pcrel_hi20:
69 return ELF::R_RISCV_PCREL_HI20;
70 case RISCV::fixup_riscv_pcrel_lo12_i:
71 return ELF::R_RISCV_PCREL_LO12_I;
72 case RISCV::fixup_riscv_pcrel_lo12_s:
73 return ELF::R_RISCV_PCREL_LO12_S;
74 case RISCV::fixup_riscv_got_hi20:
75 return ELF::R_RISCV_GOT_HI20;
76 case RISCV::fixup_riscv_tls_got_hi20:
77 return ELF::R_RISCV_TLS_GOT_HI20;
78 case RISCV::fixup_riscv_tls_gd_hi20:
79 return ELF::R_RISCV_TLS_GD_HI20;
80 case RISCV::fixup_riscv_jal:
81 return ELF::R_RISCV_JAL;
82 case RISCV::fixup_riscv_branch:
83 return ELF::R_RISCV_BRANCH;
84 case RISCV::fixup_riscv_rvc_jump:
85 return ELF::R_RISCV_RVC_JUMP;
86 case RISCV::fixup_riscv_rvc_branch:
87 return ELF::R_RISCV_RVC_BRANCH;
88 case RISCV::fixup_riscv_call:
89 return ELF::R_RISCV_CALL_PLT;
90 case RISCV::fixup_riscv_call_plt:
91 return ELF::R_RISCV_CALL_PLT;
95 switch (Kind) {
96 default:
97 Ctx.reportError(Fixup.getLoc(), "unsupported relocation type");
98 return ELF::R_RISCV_NONE;
99 case FK_Data_1:
100 Ctx.reportError(Fixup.getLoc(), "1-byte data relocations not supported");
101 return ELF::R_RISCV_NONE;
102 case FK_Data_2:
103 Ctx.reportError(Fixup.getLoc(), "2-byte data relocations not supported");
104 return ELF::R_RISCV_NONE;
105 case FK_Data_4:
106 if (Expr->getKind() == MCExpr::Target &&
107 cast<RISCVMCExpr>(Expr)->getKind() == RISCVMCExpr::VK_RISCV_32_PCREL)
108 return ELF::R_RISCV_32_PCREL;
109 return ELF::R_RISCV_32;
110 case FK_Data_8:
111 return ELF::R_RISCV_64;
112 case RISCV::fixup_riscv_hi20:
113 return ELF::R_RISCV_HI20;
114 case RISCV::fixup_riscv_lo12_i:
115 return ELF::R_RISCV_LO12_I;
116 case RISCV::fixup_riscv_lo12_s:
117 return ELF::R_RISCV_LO12_S;
118 case RISCV::fixup_riscv_tprel_hi20:
119 return ELF::R_RISCV_TPREL_HI20;
120 case RISCV::fixup_riscv_tprel_lo12_i:
121 return ELF::R_RISCV_TPREL_LO12_I;
122 case RISCV::fixup_riscv_tprel_lo12_s:
123 return ELF::R_RISCV_TPREL_LO12_S;
124 case RISCV::fixup_riscv_tprel_add:
125 return ELF::R_RISCV_TPREL_ADD;
126 case RISCV::fixup_riscv_relax:
127 return ELF::R_RISCV_RELAX;
128 case RISCV::fixup_riscv_align:
129 return ELF::R_RISCV_ALIGN;
133 std::unique_ptr<MCObjectTargetWriter>
134 llvm::createRISCVELFObjectWriter(uint8_t OSABI, bool Is64Bit) {
135 return std::make_unique<RISCVELFObjectWriter>(OSABI, Is64Bit);