1 //===-- HexagonMCCodeEmitter.cpp - Hexagon Target Descriptions ------------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
11 #include "MCTargetDesc/HexagonBaseInfo.h"
12 #include "MCTargetDesc/HexagonFixupKinds.h"
13 #include "MCTargetDesc/HexagonMCCodeEmitter.h"
14 #include "MCTargetDesc/HexagonMCInstrInfo.h"
15 #include "MCTargetDesc/HexagonMCTargetDesc.h"
16 #include "llvm/ADT/Statistic.h"
17 #include "llvm/MC/MCCodeEmitter.h"
18 #include "llvm/MC/MCContext.h"
19 #include "llvm/MC/MCExpr.h"
20 #include "llvm/MC/MCInst.h"
21 #include "llvm/MC/MCInstrInfo.h"
22 #include "llvm/MC/MCRegisterInfo.h"
23 #include "llvm/MC/MCSubtargetInfo.h"
24 #include "llvm/Support/Debug.h"
25 #include "llvm/Support/raw_ostream.h"
27 #define DEBUG_TYPE "mccodeemitter"
30 using namespace Hexagon;
32 STATISTIC(MCNumEmitted, "Number of MC instructions emitted");
35 /// \brief 10.6 Instruction Packets
36 /// Possible values for instruction packet parse field.
37 enum class ParseField { duplex = 0x0, last0 = 0x1, last1 = 0x2, end = 0x3 };
38 /// \brief Returns the packet bits based on instruction position.
39 uint32_t getPacketBits(MCInst const &HMI) {
40 unsigned const ParseFieldOffset = 14;
41 ParseField Field = HexagonMCInstrInfo::isPacketEnd(HMI) ? ParseField::end
43 return static_cast<uint32_t>(Field) << ParseFieldOffset;
45 void emitLittleEndian(uint64_t Binary, raw_ostream &OS) {
46 OS << static_cast<uint8_t>((Binary >> 0x00) & 0xff);
47 OS << static_cast<uint8_t>((Binary >> 0x08) & 0xff);
48 OS << static_cast<uint8_t>((Binary >> 0x10) & 0xff);
49 OS << static_cast<uint8_t>((Binary >> 0x18) & 0xff);
53 HexagonMCCodeEmitter::HexagonMCCodeEmitter(MCInstrInfo const &aMII,
55 : MCT(aMCT), MCII(aMII), Addend(new unsigned(0)),
56 Extended(new bool(false)) {}
58 void HexagonMCCodeEmitter::encodeInstruction(MCInst const &MI, raw_ostream &OS,
59 SmallVectorImpl<MCFixup> &Fixups,
60 MCSubtargetInfo const &STI) const {
61 uint64_t Binary = getBinaryCodeForInstr(MI, Fixups, STI) | getPacketBits(MI);
62 assert(HexagonMCInstrInfo::getDesc(MCII, MI).getSize() == 4 &&
63 "All instructions should be 32bit");
65 emitLittleEndian(Binary, OS);
69 static Hexagon::Fixups getFixupNoBits(MCInstrInfo const &MCII, const MCInst &MI,
71 const MCSymbolRefExpr::VariantKind kind) {
72 const MCInstrDesc &MCID = HexagonMCInstrInfo::getDesc(MCII, MI);
73 unsigned insnType = llvm::HexagonMCInstrInfo::getType(MCII, MI);
75 if (insnType == HexagonII::TypePREFIX) {
77 case llvm::MCSymbolRefExpr::VK_GOTOFF:
78 return Hexagon::fixup_Hexagon_GOTREL_32_6_X;
79 case llvm::MCSymbolRefExpr::VK_GOT:
80 return Hexagon::fixup_Hexagon_GOT_32_6_X;
81 case llvm::MCSymbolRefExpr::VK_TPREL:
82 return Hexagon::fixup_Hexagon_TPREL_32_6_X;
83 case llvm::MCSymbolRefExpr::VK_DTPREL:
84 return Hexagon::fixup_Hexagon_DTPREL_32_6_X;
85 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
86 return Hexagon::fixup_Hexagon_GD_GOT_32_6_X;
87 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
88 return Hexagon::fixup_Hexagon_LD_GOT_32_6_X;
89 case llvm::MCSymbolRefExpr::VK_Hexagon_IE:
90 return Hexagon::fixup_Hexagon_IE_32_6_X;
91 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
92 return Hexagon::fixup_Hexagon_IE_GOT_32_6_X;
95 return Hexagon::fixup_Hexagon_B32_PCREL_X;
97 return Hexagon::fixup_Hexagon_32_6_X;
99 } else if (MCID.isBranch())
100 return (Hexagon::fixup_Hexagon_B13_PCREL);
102 switch (MCID.getOpcode()) {
104 case Hexagon::A2_tfrih:
106 case llvm::MCSymbolRefExpr::VK_GOT:
107 return Hexagon::fixup_Hexagon_GOT_HI16;
108 case llvm::MCSymbolRefExpr::VK_GOTOFF:
109 return Hexagon::fixup_Hexagon_GOTREL_HI16;
110 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
111 return Hexagon::fixup_Hexagon_GD_GOT_HI16;
112 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
113 return Hexagon::fixup_Hexagon_LD_GOT_HI16;
114 case llvm::MCSymbolRefExpr::VK_Hexagon_IE:
115 return Hexagon::fixup_Hexagon_IE_HI16;
116 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
117 return Hexagon::fixup_Hexagon_IE_GOT_HI16;
118 case llvm::MCSymbolRefExpr::VK_TPREL:
119 return Hexagon::fixup_Hexagon_TPREL_HI16;
120 case llvm::MCSymbolRefExpr::VK_DTPREL:
121 return Hexagon::fixup_Hexagon_DTPREL_HI16;
123 return Hexagon::fixup_Hexagon_HI16;
127 case Hexagon::A2_tfril:
129 case llvm::MCSymbolRefExpr::VK_GOT:
130 return Hexagon::fixup_Hexagon_GOT_LO16;
131 case llvm::MCSymbolRefExpr::VK_GOTOFF:
132 return Hexagon::fixup_Hexagon_GOTREL_LO16;
133 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
134 return Hexagon::fixup_Hexagon_GD_GOT_LO16;
135 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
136 return Hexagon::fixup_Hexagon_LD_GOT_LO16;
137 case llvm::MCSymbolRefExpr::VK_Hexagon_IE:
138 return Hexagon::fixup_Hexagon_IE_LO16;
139 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
140 return Hexagon::fixup_Hexagon_IE_GOT_LO16;
141 case llvm::MCSymbolRefExpr::VK_TPREL:
142 return Hexagon::fixup_Hexagon_TPREL_LO16;
143 case llvm::MCSymbolRefExpr::VK_DTPREL:
144 return Hexagon::fixup_Hexagon_DTPREL_LO16;
146 return Hexagon::fixup_Hexagon_LO16;
149 // The only relocs left should be GP relative:
151 if (MCID.mayStore() || MCID.mayLoad()) {
152 for (const uint16_t *ImpUses = MCID.getImplicitUses(); *ImpUses;
154 if (*ImpUses == Hexagon::GP) {
155 switch (HexagonMCInstrInfo::getAccessSize(MCII, MI)) {
156 case HexagonII::MemAccessSize::ByteAccess:
157 return fixup_Hexagon_GPREL16_0;
158 case HexagonII::MemAccessSize::HalfWordAccess:
159 return fixup_Hexagon_GPREL16_1;
160 case HexagonII::MemAccessSize::WordAccess:
161 return fixup_Hexagon_GPREL16_2;
162 case HexagonII::MemAccessSize::DoubleWordAccess:
163 return fixup_Hexagon_GPREL16_3;
165 llvm_unreachable("unhandled fixup");
170 llvm_unreachable("unhandled fixup");
173 return LastTargetFixupKind;
176 unsigned HexagonMCCodeEmitter::getExprOpValue(const MCInst &MI,
179 SmallVectorImpl<MCFixup> &Fixups,
180 const MCSubtargetInfo &STI) const
185 if (ME->EvaluateAsAbsolute(Res))
188 MCExpr::ExprKind MK = ME->getKind();
189 if (MK == MCExpr::Constant) {
190 return cast<MCConstantExpr>(ME)->getValue();
192 if (MK == MCExpr::Binary) {
194 Res = getExprOpValue(MI, MO, cast<MCBinaryExpr>(ME)->getLHS(), Fixups, STI);
196 getExprOpValue(MI, MO, cast<MCBinaryExpr>(ME)->getRHS(), Fixups, STI);
200 assert(MK == MCExpr::SymbolRef);
202 Hexagon::Fixups FixupKind =
203 Hexagon::Fixups(Hexagon::fixup_Hexagon_TPREL_LO16);
204 const MCSymbolRefExpr *MCSRE = static_cast<const MCSymbolRefExpr *>(ME);
205 const MCInstrDesc &MCID = HexagonMCInstrInfo::getDesc(MCII, MI);
206 unsigned bits = HexagonMCInstrInfo::getExtentBits(MCII, MI) -
207 HexagonMCInstrInfo::getExtentAlignment(MCII, MI);
208 const MCSymbolRefExpr::VariantKind kind = MCSRE->getKind();
210 DEBUG(dbgs() << "----------------------------------------\n");
211 DEBUG(dbgs() << "Opcode Name: " << HexagonMCInstrInfo::getName(MCII, MI)
213 DEBUG(dbgs() << "Opcode: " << MCID.getOpcode() << "\n");
214 DEBUG(dbgs() << "Relocation bits: " << bits << "\n");
215 DEBUG(dbgs() << "Addend: " << *Addend << "\n");
216 DEBUG(dbgs() << "----------------------------------------\n");
220 DEBUG(dbgs() << "unrecognized bit count of " << bits << '\n');
225 case llvm::MCSymbolRefExpr::VK_Hexagon_PCREL:
226 FixupKind = Hexagon::fixup_Hexagon_32_PCREL;
228 case llvm::MCSymbolRefExpr::VK_GOT:
229 FixupKind = *Extended ? Hexagon::fixup_Hexagon_GOT_32_6_X
230 : Hexagon::fixup_Hexagon_GOT_32;
232 case llvm::MCSymbolRefExpr::VK_GOTOFF:
233 FixupKind = *Extended ? Hexagon::fixup_Hexagon_GOTREL_32_6_X
234 : Hexagon::fixup_Hexagon_GOTREL_32;
236 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
237 FixupKind = *Extended ? Hexagon::fixup_Hexagon_GD_GOT_32_6_X
238 : Hexagon::fixup_Hexagon_GD_GOT_32;
240 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
241 FixupKind = *Extended ? Hexagon::fixup_Hexagon_LD_GOT_32_6_X
242 : Hexagon::fixup_Hexagon_LD_GOT_32;
244 case llvm::MCSymbolRefExpr::VK_Hexagon_IE:
245 FixupKind = *Extended ? Hexagon::fixup_Hexagon_IE_32_6_X
246 : Hexagon::fixup_Hexagon_IE_32;
248 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
249 FixupKind = *Extended ? Hexagon::fixup_Hexagon_IE_GOT_32_6_X
250 : Hexagon::fixup_Hexagon_IE_GOT_32;
252 case llvm::MCSymbolRefExpr::VK_TPREL:
253 FixupKind = *Extended ? Hexagon::fixup_Hexagon_TPREL_32_6_X
254 : Hexagon::fixup_Hexagon_TPREL_32;
256 case llvm::MCSymbolRefExpr::VK_DTPREL:
257 FixupKind = *Extended ? Hexagon::fixup_Hexagon_DTPREL_32_6_X
258 : Hexagon::fixup_Hexagon_DTPREL_32;
262 *Extended ? Hexagon::fixup_Hexagon_32_6_X : Hexagon::fixup_Hexagon_32;
269 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_PLT:
270 FixupKind = Hexagon::fixup_Hexagon_GD_PLT_B22_PCREL;
272 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_PLT:
273 FixupKind = Hexagon::fixup_Hexagon_LD_PLT_B22_PCREL;
276 if (MCID.isBranch() || MCID.isCall()) {
277 FixupKind = *Extended ? Hexagon::fixup_Hexagon_B22_PCREL_X
278 : Hexagon::fixup_Hexagon_B22_PCREL;
280 errs() << "unrecognized relocation, bits: " << bits << "\n";
281 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
291 FixupKind = Hexagon::fixup_Hexagon_16_X;
293 case llvm::MCSymbolRefExpr::VK_GOT:
294 FixupKind = Hexagon::fixup_Hexagon_GOT_16_X;
296 case llvm::MCSymbolRefExpr::VK_GOTOFF:
297 FixupKind = Hexagon::fixup_Hexagon_GOTREL_16_X;
299 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
300 FixupKind = Hexagon::fixup_Hexagon_GD_GOT_16_X;
302 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
303 FixupKind = Hexagon::fixup_Hexagon_LD_GOT_16_X;
305 case llvm::MCSymbolRefExpr::VK_Hexagon_IE:
306 FixupKind = Hexagon::fixup_Hexagon_IE_16_X;
308 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
309 FixupKind = Hexagon::fixup_Hexagon_IE_GOT_16_X;
311 case llvm::MCSymbolRefExpr::VK_TPREL:
312 FixupKind = Hexagon::fixup_Hexagon_TPREL_16_X;
314 case llvm::MCSymbolRefExpr::VK_DTPREL:
315 FixupKind = Hexagon::fixup_Hexagon_DTPREL_16_X;
321 errs() << "unrecognized relocation, bits " << bits << "\n";
322 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
324 case llvm::MCSymbolRefExpr::VK_GOTOFF:
325 if ((MCID.getOpcode() == Hexagon::HI) ||
326 (MCID.getOpcode() == Hexagon::LO_H))
327 FixupKind = Hexagon::fixup_Hexagon_GOTREL_HI16;
329 FixupKind = Hexagon::fixup_Hexagon_GOTREL_LO16;
331 case llvm::MCSymbolRefExpr::VK_Hexagon_GPREL:
332 FixupKind = Hexagon::fixup_Hexagon_GPREL16_0;
334 case llvm::MCSymbolRefExpr::VK_Hexagon_LO16:
335 FixupKind = Hexagon::fixup_Hexagon_LO16;
337 case llvm::MCSymbolRefExpr::VK_Hexagon_HI16:
338 FixupKind = Hexagon::fixup_Hexagon_HI16;
340 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
341 FixupKind = Hexagon::fixup_Hexagon_GD_GOT_16;
343 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
344 FixupKind = Hexagon::fixup_Hexagon_LD_GOT_16;
346 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
347 FixupKind = Hexagon::fixup_Hexagon_IE_GOT_16;
349 case llvm::MCSymbolRefExpr::VK_TPREL:
350 FixupKind = Hexagon::fixup_Hexagon_TPREL_16;
352 case llvm::MCSymbolRefExpr::VK_DTPREL:
353 FixupKind = Hexagon::fixup_Hexagon_DTPREL_16;
359 if (MCID.isBranch() || MCID.isCall())
360 FixupKind = *Extended ? Hexagon::fixup_Hexagon_B15_PCREL_X
361 : Hexagon::fixup_Hexagon_B15_PCREL;
366 FixupKind = Hexagon::fixup_Hexagon_B13_PCREL;
368 errs() << "unrecognized relocation, bits " << bits << "\n";
369 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
377 FixupKind = Hexagon::fixup_Hexagon_12_X;
379 // There isn't a GOT_12_X, both 11_X and 16_X resolve to 6/26
380 case llvm::MCSymbolRefExpr::VK_GOT:
381 FixupKind = Hexagon::fixup_Hexagon_GOT_16_X;
383 case llvm::MCSymbolRefExpr::VK_GOTOFF:
384 FixupKind = Hexagon::fixup_Hexagon_GOTREL_16_X;
388 errs() << "unrecognized relocation, bits " << bits << "\n";
389 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
397 FixupKind = Hexagon::fixup_Hexagon_11_X;
399 case llvm::MCSymbolRefExpr::VK_GOT:
400 FixupKind = Hexagon::fixup_Hexagon_GOT_11_X;
402 case llvm::MCSymbolRefExpr::VK_GOTOFF:
403 FixupKind = Hexagon::fixup_Hexagon_GOTREL_11_X;
405 case llvm::MCSymbolRefExpr::VK_Hexagon_GD_GOT:
406 FixupKind = Hexagon::fixup_Hexagon_GD_GOT_11_X;
408 case llvm::MCSymbolRefExpr::VK_Hexagon_LD_GOT:
409 FixupKind = Hexagon::fixup_Hexagon_LD_GOT_11_X;
411 case llvm::MCSymbolRefExpr::VK_Hexagon_IE_GOT:
412 FixupKind = Hexagon::fixup_Hexagon_IE_GOT_11_X;
414 case llvm::MCSymbolRefExpr::VK_TPREL:
415 FixupKind = Hexagon::fixup_Hexagon_TPREL_11_X;
417 case llvm::MCSymbolRefExpr::VK_DTPREL:
418 FixupKind = Hexagon::fixup_Hexagon_DTPREL_11_X;
422 errs() << "unrecognized relocation, bits " << bits << "\n";
423 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
429 FixupKind = Hexagon::fixup_Hexagon_10_X;
433 if (MCID.isBranch() ||
434 (llvm::HexagonMCInstrInfo::getType(MCII, MI) == HexagonII::TypeCR))
435 FixupKind = *Extended ? Hexagon::fixup_Hexagon_B9_PCREL_X
436 : Hexagon::fixup_Hexagon_B9_PCREL;
438 FixupKind = Hexagon::fixup_Hexagon_9_X;
440 errs() << "unrecognized relocation, bits " << bits << "\n";
441 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
447 FixupKind = Hexagon::fixup_Hexagon_8_X;
449 errs() << "unrecognized relocation, bits " << bits << "\n";
450 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
455 if (MCID.isBranch() ||
456 (llvm::HexagonMCInstrInfo::getType(MCII, MI) == HexagonII::TypeCR))
457 FixupKind = *Extended ? Hexagon::fixup_Hexagon_B7_PCREL_X
458 : Hexagon::fixup_Hexagon_B7_PCREL;
460 FixupKind = Hexagon::fixup_Hexagon_7_X;
462 errs() << "unrecognized relocation, bits " << bits << "\n";
463 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
471 FixupKind = Hexagon::fixup_Hexagon_6_X;
473 case llvm::MCSymbolRefExpr::VK_Hexagon_PCREL:
474 FixupKind = Hexagon::fixup_Hexagon_6_PCREL_X;
476 // This is part of an extender, GOT_11 is a
477 // Word32_U6 unsigned/truncated reloc.
478 case llvm::MCSymbolRefExpr::VK_GOT:
479 FixupKind = Hexagon::fixup_Hexagon_GOT_11_X;
481 case llvm::MCSymbolRefExpr::VK_GOTOFF:
482 FixupKind = Hexagon::fixup_Hexagon_GOTREL_11_X;
486 errs() << "unrecognized relocation, bits " << bits << "\n";
487 errs() << "name = " << HexagonMCInstrInfo::getName(MCII, MI) << "\n";
492 FixupKind = getFixupNoBits(MCII, MI, MO, kind);
497 MCFixup::create(*Addend, MO.getExpr(), MCFixupKind(FixupKind));
498 Fixups.push_back(fixup);
499 // All of the information is in the fixup.
504 HexagonMCCodeEmitter::getMachineOpValue(MCInst const &MI, MCOperand const &MO,
505 SmallVectorImpl<MCFixup> &Fixups,
506 MCSubtargetInfo const &STI) const {
508 return MCT.getRegisterInfo()->getEncodingValue(MO.getReg());
510 return static_cast<unsigned>(MO.getImm());
514 return getExprOpValue(MI, MO, MO.getExpr(), Fixups, STI);
517 MCCodeEmitter *llvm::createHexagonMCCodeEmitter(MCInstrInfo const &MII,
518 MCRegisterInfo const &MRI,
520 return new HexagonMCCodeEmitter(MII, MCT);
523 #include "HexagonGenMCCodeEmitter.inc"