1f48ef2f2SRichard Trieu //===-- XCoreInstPrinter.cpp - Convert XCore MCInst to assembly syntax ----===//
2f48ef2f2SRichard Trieu //
3f48ef2f2SRichard Trieu // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4f48ef2f2SRichard Trieu // See https://llvm.org/LICENSE.txt for license information.
5f48ef2f2SRichard Trieu // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6f48ef2f2SRichard Trieu //
7f48ef2f2SRichard Trieu //===----------------------------------------------------------------------===//
8f48ef2f2SRichard Trieu //
9f48ef2f2SRichard Trieu // This class prints an XCore MCInst to a .s file.
10f48ef2f2SRichard Trieu //
11f48ef2f2SRichard Trieu //===----------------------------------------------------------------------===//
12f48ef2f2SRichard Trieu 
13f48ef2f2SRichard Trieu #include "XCoreInstPrinter.h"
14f48ef2f2SRichard Trieu #include "llvm/ADT/StringRef.h"
15f48ef2f2SRichard Trieu #include "llvm/MC/MCExpr.h"
16f48ef2f2SRichard Trieu #include "llvm/MC/MCInst.h"
17f48ef2f2SRichard Trieu #include "llvm/MC/MCSymbol.h"
18f48ef2f2SRichard Trieu #include "llvm/Support/Casting.h"
19f48ef2f2SRichard Trieu #include "llvm/Support/ErrorHandling.h"
20f48ef2f2SRichard Trieu #include "llvm/Support/raw_ostream.h"
21f48ef2f2SRichard Trieu #include <cassert>
22f48ef2f2SRichard Trieu 
23f48ef2f2SRichard Trieu using namespace llvm;
24f48ef2f2SRichard Trieu 
25f48ef2f2SRichard Trieu #define DEBUG_TYPE "asm-printer"
26f48ef2f2SRichard Trieu 
27f48ef2f2SRichard Trieu #include "XCoreGenAsmWriter.inc"
28f48ef2f2SRichard Trieu 
printRegName(raw_ostream & OS,unsigned RegNo) const29f48ef2f2SRichard Trieu void XCoreInstPrinter::printRegName(raw_ostream &OS, unsigned RegNo) const {
30f48ef2f2SRichard Trieu   OS << StringRef(getRegisterName(RegNo)).lower();
31f48ef2f2SRichard Trieu }
32f48ef2f2SRichard Trieu 
printInst(const MCInst * MI,uint64_t Address,StringRef Annot,const MCSubtargetInfo & STI,raw_ostream & O)33aa708763SFangrui Song void XCoreInstPrinter::printInst(const MCInst *MI, uint64_t Address,
34aa708763SFangrui Song                                  StringRef Annot, const MCSubtargetInfo &STI,
35aa708763SFangrui Song                                  raw_ostream &O) {
36*3d87d0b9SFangrui Song   printInstruction(MI, Address, O);
37f48ef2f2SRichard Trieu   printAnnotation(O, Annot);
38f48ef2f2SRichard Trieu }
39f48ef2f2SRichard Trieu 
40f48ef2f2SRichard Trieu void XCoreInstPrinter::
printInlineJT(const MCInst * MI,int opNum,raw_ostream & O)41f48ef2f2SRichard Trieu printInlineJT(const MCInst *MI, int opNum, raw_ostream &O) {
42f48ef2f2SRichard Trieu   report_fatal_error("can't handle InlineJT");
43f48ef2f2SRichard Trieu }
44f48ef2f2SRichard Trieu 
45f48ef2f2SRichard Trieu void XCoreInstPrinter::
printInlineJT32(const MCInst * MI,int opNum,raw_ostream & O)46f48ef2f2SRichard Trieu printInlineJT32(const MCInst *MI, int opNum, raw_ostream &O) {
47f48ef2f2SRichard Trieu   report_fatal_error("can't handle InlineJT32");
48f48ef2f2SRichard Trieu }
49f48ef2f2SRichard Trieu 
printExpr(const MCExpr * Expr,const MCAsmInfo * MAI,raw_ostream & OS)50f48ef2f2SRichard Trieu static void printExpr(const MCExpr *Expr, const MCAsmInfo *MAI,
51f48ef2f2SRichard Trieu                       raw_ostream &OS) {
52f48ef2f2SRichard Trieu   int Offset = 0;
53f48ef2f2SRichard Trieu   const MCSymbolRefExpr *SRE;
54f48ef2f2SRichard Trieu 
55f48ef2f2SRichard Trieu   if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(Expr)) {
56f48ef2f2SRichard Trieu     SRE = dyn_cast<MCSymbolRefExpr>(BE->getLHS());
57f48ef2f2SRichard Trieu     const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(BE->getRHS());
58f48ef2f2SRichard Trieu     assert(SRE && CE && "Binary expression must be sym+const.");
59f48ef2f2SRichard Trieu     Offset = CE->getValue();
60f48ef2f2SRichard Trieu   } else {
61f48ef2f2SRichard Trieu     SRE = dyn_cast<MCSymbolRefExpr>(Expr);
62f48ef2f2SRichard Trieu     assert(SRE && "Unexpected MCExpr type.");
63f48ef2f2SRichard Trieu   }
64f48ef2f2SRichard Trieu   assert(SRE->getKind() == MCSymbolRefExpr::VK_None);
65f48ef2f2SRichard Trieu 
66f48ef2f2SRichard Trieu   SRE->getSymbol().print(OS, MAI);
67f48ef2f2SRichard Trieu 
68f48ef2f2SRichard Trieu   if (Offset) {
69f48ef2f2SRichard Trieu     if (Offset > 0)
70f48ef2f2SRichard Trieu       OS << '+';
71f48ef2f2SRichard Trieu     OS << Offset;
72f48ef2f2SRichard Trieu   }
73f48ef2f2SRichard Trieu }
74f48ef2f2SRichard Trieu 
75f48ef2f2SRichard Trieu void XCoreInstPrinter::
printOperand(const MCInst * MI,unsigned OpNo,raw_ostream & O)76f48ef2f2SRichard Trieu printOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) {
77f48ef2f2SRichard Trieu   const MCOperand &Op = MI->getOperand(OpNo);
78f48ef2f2SRichard Trieu   if (Op.isReg()) {
79f48ef2f2SRichard Trieu     printRegName(O, Op.getReg());
80f48ef2f2SRichard Trieu     return;
81f48ef2f2SRichard Trieu   }
82f48ef2f2SRichard Trieu 
83f48ef2f2SRichard Trieu   if (Op.isImm()) {
84f48ef2f2SRichard Trieu     O << Op.getImm();
85f48ef2f2SRichard Trieu     return;
86f48ef2f2SRichard Trieu   }
87f48ef2f2SRichard Trieu 
88f48ef2f2SRichard Trieu   assert(Op.isExpr() && "unknown operand kind in printOperand");
89f48ef2f2SRichard Trieu   printExpr(Op.getExpr(), &MAI, O);
90f48ef2f2SRichard Trieu }
91