1 //===-- HexagonELFObjectWriter.cpp - Hexagon Target Descriptions ----------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #include "Hexagon.h"
11 #include "MCTargetDesc/HexagonFixupKinds.h"
12 #include "llvm/MC/MCAssembler.h"
13 #include "llvm/MC/MCELFObjectWriter.h"
14 #include "llvm/Support/Debug.h"
15 #include "llvm/Support/raw_ostream.h"
16 
17 #define DEBUG_TYPE "hexagon-elf-writer"
18 
19 using namespace llvm;
20 using namespace Hexagon;
21 
22 namespace {
23 
24 class HexagonELFObjectWriter : public MCELFObjectTargetWriter {
25 private:
26   StringRef CPU;
27 
28 public:
29   HexagonELFObjectWriter(uint8_t OSABI, StringRef C);
30 
31   unsigned GetRelocType(MCValue const &Target, MCFixup const &Fixup,
32                         bool IsPCRel) const override;
33 };
34 }
35 
HexagonELFObjectWriter(uint8_t OSABI,StringRef C)36 HexagonELFObjectWriter::HexagonELFObjectWriter(uint8_t OSABI, StringRef C)
37     : MCELFObjectTargetWriter(/*Is64bit*/ false, OSABI, ELF::EM_HEXAGON,
38                               /*HasRelocationAddend*/ true),
39       CPU(C) {}
40 
GetRelocType(MCValue const &,MCFixup const & Fixup,bool IsPCRel) const41 unsigned HexagonELFObjectWriter::GetRelocType(MCValue const & /*Target*/,
42                                               MCFixup const &Fixup,
43                                               bool IsPCRel) const {
44   switch ((unsigned)Fixup.getKind()) {
45   default:
46     DEBUG(dbgs() << "unrecognized relocation " << Fixup.getKind() << "\n");
47     llvm_unreachable("Unimplemented Fixup kind!");
48     return ELF::R_HEX_NONE;
49   case FK_Data_4:
50     return (IsPCRel) ? ELF::R_HEX_32_PCREL : ELF::R_HEX_32;
51   case FK_PCRel_4:
52     return ELF::R_HEX_32_PCREL;
53   case FK_Data_2:
54     return ELF::R_HEX_16;
55   case FK_Data_1:
56     return ELF::R_HEX_8;
57   case fixup_Hexagon_B22_PCREL:
58     return ELF::R_HEX_B22_PCREL;
59   case fixup_Hexagon_B15_PCREL:
60     return ELF::R_HEX_B15_PCREL;
61   case fixup_Hexagon_B7_PCREL:
62     return ELF::R_HEX_B7_PCREL;
63   case fixup_Hexagon_LO16:
64     return ELF::R_HEX_LO16;
65   case fixup_Hexagon_HI16:
66     return ELF::R_HEX_HI16;
67   case fixup_Hexagon_32:
68     return ELF::R_HEX_32;
69   case fixup_Hexagon_16:
70     return ELF::R_HEX_16;
71   case fixup_Hexagon_8:
72     return ELF::R_HEX_8;
73   case fixup_Hexagon_GPREL16_0:
74     return ELF::R_HEX_GPREL16_0;
75   case fixup_Hexagon_GPREL16_1:
76     return ELF::R_HEX_GPREL16_1;
77   case fixup_Hexagon_GPREL16_2:
78     return ELF::R_HEX_GPREL16_2;
79   case fixup_Hexagon_GPREL16_3:
80     return ELF::R_HEX_GPREL16_3;
81   case fixup_Hexagon_HL16:
82     return ELF::R_HEX_HL16;
83   case fixup_Hexagon_B13_PCREL:
84     return ELF::R_HEX_B13_PCREL;
85   case fixup_Hexagon_B9_PCREL:
86     return ELF::R_HEX_B9_PCREL;
87   case fixup_Hexagon_B32_PCREL_X:
88     return ELF::R_HEX_B32_PCREL_X;
89   case fixup_Hexagon_32_6_X:
90     return ELF::R_HEX_32_6_X;
91   case fixup_Hexagon_B22_PCREL_X:
92     return ELF::R_HEX_B22_PCREL_X;
93   case fixup_Hexagon_B15_PCREL_X:
94     return ELF::R_HEX_B15_PCREL_X;
95   case fixup_Hexagon_B13_PCREL_X:
96     return ELF::R_HEX_B13_PCREL_X;
97   case fixup_Hexagon_B9_PCREL_X:
98     return ELF::R_HEX_B9_PCREL_X;
99   case fixup_Hexagon_B7_PCREL_X:
100     return ELF::R_HEX_B7_PCREL_X;
101   case fixup_Hexagon_16_X:
102     return ELF::R_HEX_16_X;
103   case fixup_Hexagon_12_X:
104     return ELF::R_HEX_12_X;
105   case fixup_Hexagon_11_X:
106     return ELF::R_HEX_11_X;
107   case fixup_Hexagon_10_X:
108     return ELF::R_HEX_10_X;
109   case fixup_Hexagon_9_X:
110     return ELF::R_HEX_9_X;
111   case fixup_Hexagon_8_X:
112     return ELF::R_HEX_8_X;
113   case fixup_Hexagon_7_X:
114     return ELF::R_HEX_7_X;
115   case fixup_Hexagon_6_X:
116     return ELF::R_HEX_6_X;
117   case fixup_Hexagon_32_PCREL:
118     return ELF::R_HEX_32_PCREL;
119   case fixup_Hexagon_COPY:
120     return ELF::R_HEX_COPY;
121   case fixup_Hexagon_GLOB_DAT:
122     return ELF::R_HEX_GLOB_DAT;
123   case fixup_Hexagon_JMP_SLOT:
124     return ELF::R_HEX_JMP_SLOT;
125   case fixup_Hexagon_RELATIVE:
126     return ELF::R_HEX_RELATIVE;
127   case fixup_Hexagon_PLT_B22_PCREL:
128     return ELF::R_HEX_PLT_B22_PCREL;
129   case fixup_Hexagon_GOTREL_LO16:
130     return ELF::R_HEX_GOTREL_LO16;
131   case fixup_Hexagon_GOTREL_HI16:
132     return ELF::R_HEX_GOTREL_HI16;
133   case fixup_Hexagon_GOTREL_32:
134     return ELF::R_HEX_GOTREL_32;
135   case fixup_Hexagon_GOT_LO16:
136     return ELF::R_HEX_GOT_LO16;
137   case fixup_Hexagon_GOT_HI16:
138     return ELF::R_HEX_GOT_HI16;
139   case fixup_Hexagon_GOT_32:
140     return ELF::R_HEX_GOT_32;
141   case fixup_Hexagon_GOT_16:
142     return ELF::R_HEX_GOT_16;
143   case fixup_Hexagon_DTPMOD_32:
144     return ELF::R_HEX_DTPMOD_32;
145   case fixup_Hexagon_DTPREL_LO16:
146     return ELF::R_HEX_DTPREL_LO16;
147   case fixup_Hexagon_DTPREL_HI16:
148     return ELF::R_HEX_DTPREL_HI16;
149   case fixup_Hexagon_DTPREL_32:
150     return ELF::R_HEX_DTPREL_32;
151   case fixup_Hexagon_DTPREL_16:
152     return ELF::R_HEX_DTPREL_16;
153   case fixup_Hexagon_GD_PLT_B22_PCREL:
154     return ELF::R_HEX_GD_PLT_B22_PCREL;
155   case fixup_Hexagon_LD_PLT_B22_PCREL:
156     return ELF::R_HEX_LD_PLT_B22_PCREL;
157   case fixup_Hexagon_GD_GOT_LO16:
158     return ELF::R_HEX_GD_GOT_LO16;
159   case fixup_Hexagon_GD_GOT_HI16:
160     return ELF::R_HEX_GD_GOT_HI16;
161   case fixup_Hexagon_GD_GOT_32:
162     return ELF::R_HEX_GD_GOT_32;
163   case fixup_Hexagon_GD_GOT_16:
164     return ELF::R_HEX_GD_GOT_16;
165   case fixup_Hexagon_LD_GOT_LO16:
166     return ELF::R_HEX_LD_GOT_LO16;
167   case fixup_Hexagon_LD_GOT_HI16:
168     return ELF::R_HEX_LD_GOT_HI16;
169   case fixup_Hexagon_LD_GOT_32:
170     return ELF::R_HEX_LD_GOT_32;
171   case fixup_Hexagon_LD_GOT_16:
172     return ELF::R_HEX_LD_GOT_16;
173   case fixup_Hexagon_IE_LO16:
174     return ELF::R_HEX_IE_LO16;
175   case fixup_Hexagon_IE_HI16:
176     return ELF::R_HEX_IE_HI16;
177   case fixup_Hexagon_IE_32:
178     return ELF::R_HEX_IE_32;
179   case fixup_Hexagon_IE_GOT_LO16:
180     return ELF::R_HEX_IE_GOT_LO16;
181   case fixup_Hexagon_IE_GOT_HI16:
182     return ELF::R_HEX_IE_GOT_HI16;
183   case fixup_Hexagon_IE_GOT_32:
184     return ELF::R_HEX_IE_GOT_32;
185   case fixup_Hexagon_IE_GOT_16:
186     return ELF::R_HEX_IE_GOT_16;
187   case fixup_Hexagon_TPREL_LO16:
188     return ELF::R_HEX_TPREL_LO16;
189   case fixup_Hexagon_TPREL_HI16:
190     return ELF::R_HEX_TPREL_HI16;
191   case fixup_Hexagon_TPREL_32:
192     return ELF::R_HEX_TPREL_32;
193   case fixup_Hexagon_TPREL_16:
194     return ELF::R_HEX_TPREL_16;
195   case fixup_Hexagon_6_PCREL_X:
196     return ELF::R_HEX_6_PCREL_X;
197   case fixup_Hexagon_GOTREL_32_6_X:
198     return ELF::R_HEX_GOTREL_32_6_X;
199   case fixup_Hexagon_GOTREL_16_X:
200     return ELF::R_HEX_GOTREL_16_X;
201   case fixup_Hexagon_GOTREL_11_X:
202     return ELF::R_HEX_GOTREL_11_X;
203   case fixup_Hexagon_GOT_32_6_X:
204     return ELF::R_HEX_GOT_32_6_X;
205   case fixup_Hexagon_GOT_16_X:
206     return ELF::R_HEX_GOT_16_X;
207   case fixup_Hexagon_GOT_11_X:
208     return ELF::R_HEX_GOT_11_X;
209   case fixup_Hexagon_DTPREL_32_6_X:
210     return ELF::R_HEX_DTPREL_32_6_X;
211   case fixup_Hexagon_DTPREL_16_X:
212     return ELF::R_HEX_DTPREL_16_X;
213   case fixup_Hexagon_DTPREL_11_X:
214     return ELF::R_HEX_DTPREL_11_X;
215   case fixup_Hexagon_GD_GOT_32_6_X:
216     return ELF::R_HEX_GD_GOT_32_6_X;
217   case fixup_Hexagon_GD_GOT_16_X:
218     return ELF::R_HEX_GD_GOT_16_X;
219   case fixup_Hexagon_GD_GOT_11_X:
220     return ELF::R_HEX_GD_GOT_11_X;
221   case fixup_Hexagon_LD_GOT_32_6_X:
222     return ELF::R_HEX_LD_GOT_32_6_X;
223   case fixup_Hexagon_LD_GOT_16_X:
224     return ELF::R_HEX_LD_GOT_16_X;
225   case fixup_Hexagon_LD_GOT_11_X:
226     return ELF::R_HEX_LD_GOT_11_X;
227   case fixup_Hexagon_IE_32_6_X:
228     return ELF::R_HEX_IE_32_6_X;
229   case fixup_Hexagon_IE_16_X:
230     return ELF::R_HEX_IE_16_X;
231   case fixup_Hexagon_IE_GOT_32_6_X:
232     return ELF::R_HEX_IE_GOT_32_6_X;
233   case fixup_Hexagon_IE_GOT_16_X:
234     return ELF::R_HEX_IE_GOT_16_X;
235   case fixup_Hexagon_IE_GOT_11_X:
236     return ELF::R_HEX_IE_GOT_11_X;
237   case fixup_Hexagon_TPREL_32_6_X:
238     return ELF::R_HEX_TPREL_32_6_X;
239   case fixup_Hexagon_TPREL_16_X:
240     return ELF::R_HEX_TPREL_16_X;
241   case fixup_Hexagon_TPREL_11_X:
242     return ELF::R_HEX_TPREL_11_X;
243   }
244 }
245 
createHexagonELFObjectWriter(raw_pwrite_stream & OS,uint8_t OSABI,StringRef CPU)246 MCObjectWriter *llvm::createHexagonELFObjectWriter(raw_pwrite_stream &OS,
247                                                    uint8_t OSABI,
248                                                    StringRef CPU) {
249   MCELFObjectTargetWriter *MOTW = new HexagonELFObjectWriter(OSABI, CPU);
250   return createELFObjectWriter(MOTW, OS, /*IsLittleEndian*/ true);
251 }
252