1 | //===- lib/MC/MCInst.cpp - MCInst implementation --------------------------===// |
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 | //===----------------------------------------------------------------------===// |
8 | |
9 | #include "llvm/MC/MCInst.h" |
10 | #include "llvm/Config/llvm-config.h" |
11 | #include "llvm/MC/MCAsmInfo.h" |
12 | #include "llvm/MC/MCContext.h" |
13 | #include "llvm/MC/MCExpr.h" |
14 | #include "llvm/MC/MCInstPrinter.h" |
15 | #include "llvm/MC/MCRegisterInfo.h" |
16 | #include "llvm/Support/Casting.h" |
17 | #include "llvm/Support/Compiler.h" |
18 | #include "llvm/Support/Debug.h" |
19 | #include "llvm/Support/raw_ostream.h" |
20 | |
21 | using namespace llvm; |
22 | |
23 | void MCOperand::print(raw_ostream &OS, const MCContext *Ctx) const { |
24 | OS << "<MCOperand " ; |
25 | if (!isValid()) |
26 | OS << "INVALID" ; |
27 | else if (isReg()) { |
28 | OS << "Reg:" ; |
29 | if (Ctx && Ctx->getRegisterInfo()) |
30 | OS << Ctx->getRegisterInfo()->getName(RegNo: getReg()); |
31 | else |
32 | OS << getReg(); |
33 | } else if (isImm()) |
34 | OS << "Imm:" << getImm(); |
35 | else if (isSFPImm()) |
36 | OS << "SFPImm:" << bit_cast<float>(from: getSFPImm()); |
37 | else if (isDFPImm()) |
38 | OS << "DFPImm:" << bit_cast<double>(from: getDFPImm()); |
39 | else if (isExpr()) { |
40 | OS << "Expr:" ; |
41 | if (Ctx) |
42 | Ctx->getAsmInfo()->printExpr(OS, *getExpr()); |
43 | else |
44 | getExpr()->print(OS, MAI: nullptr); |
45 | } else if (isInst()) { |
46 | OS << "Inst:(" ; |
47 | if (const auto *Inst = getInst()) |
48 | Inst->print(OS, Ctx); |
49 | else |
50 | OS << "NULL" ; |
51 | OS << ")" ; |
52 | } else |
53 | OS << "UNDEFINED" ; |
54 | OS << ">" ; |
55 | } |
56 | |
57 | bool MCOperand::evaluateAsConstantImm(int64_t &Imm) const { |
58 | if (isImm()) { |
59 | Imm = getImm(); |
60 | return true; |
61 | } |
62 | return false; |
63 | } |
64 | |
65 | bool MCOperand::isBareSymbolRef() const { |
66 | assert(isExpr() && |
67 | "isBareSymbolRef expects only expressions" ); |
68 | const MCExpr *Expr = getExpr(); |
69 | MCExpr::ExprKind Kind = getExpr()->getKind(); |
70 | return Kind == MCExpr::SymbolRef && |
71 | cast<MCSymbolRefExpr>(Val: Expr)->getSpecifier() == 0; |
72 | } |
73 | |
74 | #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) |
75 | LLVM_DUMP_METHOD void MCOperand::dump() const { |
76 | print(dbgs()); |
77 | dbgs() << "\n" ; |
78 | } |
79 | #endif |
80 | |
81 | void MCInst::print(raw_ostream &OS, const MCContext *Ctx) const { |
82 | OS << "<MCInst " << getOpcode(); |
83 | for (unsigned i = 0, e = getNumOperands(); i != e; ++i) { |
84 | OS << " " ; |
85 | getOperand(i).print(OS, Ctx); |
86 | } |
87 | OS << ">" ; |
88 | } |
89 | |
90 | void MCInst::dump_pretty(raw_ostream &OS, const MCInstPrinter *Printer, |
91 | StringRef Separator, const MCContext *Ctx) const { |
92 | StringRef InstName = Printer ? Printer->getOpcodeName(Opcode: getOpcode()) : "" ; |
93 | dump_pretty(OS, Name: InstName, Separator, Ctx); |
94 | } |
95 | |
96 | void MCInst::dump_pretty(raw_ostream &OS, StringRef Name, StringRef Separator, |
97 | const MCContext *Ctx) const { |
98 | OS << "<MCInst #" << getOpcode(); |
99 | |
100 | // Show the instruction opcode name if we have it. |
101 | if (!Name.empty()) |
102 | OS << ' ' << Name; |
103 | |
104 | for (unsigned i = 0, e = getNumOperands(); i != e; ++i) { |
105 | OS << Separator; |
106 | getOperand(i).print(OS, Ctx); |
107 | } |
108 | OS << ">" ; |
109 | } |
110 | |
111 | #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) |
112 | LLVM_DUMP_METHOD void MCInst::dump() const { |
113 | print(dbgs()); |
114 | dbgs() << "\n" ; |
115 | } |
116 | #endif |
117 | |