SystemZInstPrinter.cpp revision 9188443a2d35352c4e8a2cffd1b4d31d47843b26
1//===-- SystemZInstPrinter.cpp - Convert SystemZ MCInst to assembly syntax ===//
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#define DEBUG_TYPE "asm-printer"
11
12#include "SystemZInstPrinter.h"
13#include "llvm/MC/MCExpr.h"
14#include "llvm/MC/MCInstrInfo.h"
15#include "llvm/Support/raw_ostream.h"
16
17using namespace llvm;
18
19#include "SystemZGenAsmWriter.inc"
20
21void SystemZInstPrinter::printAddress(unsigned Base, int64_t Disp,
22                                      unsigned Index, raw_ostream &O) {
23  O << Disp;
24  if (Base) {
25    O << '(';
26    if (Index)
27      O << '%' << getRegisterName(Index) << ',';
28    O << '%' << getRegisterName(Base) << ')';
29  } else
30    assert(!Index && "Shouldn't have an index without a base");
31}
32
33void SystemZInstPrinter::printOperand(const MCOperand &MO, raw_ostream &O) {
34  if (MO.isReg())
35    O << '%' << getRegisterName(MO.getReg());
36  else if (MO.isImm())
37    O << MO.getImm();
38  else if (MO.isExpr())
39    O << *MO.getExpr();
40  else
41    llvm_unreachable("Invalid operand");
42}
43
44void SystemZInstPrinter::printInst(const MCInst *MI, raw_ostream &O,
45                                   StringRef Annot) {
46  printInstruction(MI, O);
47  printAnnotation(O, Annot);
48}
49
50void SystemZInstPrinter::printRegName(raw_ostream &O, unsigned RegNo) const {
51  O << '%' << getRegisterName(RegNo);
52}
53
54void SystemZInstPrinter::printU4ImmOperand(const MCInst *MI, int OpNum,
55                                           raw_ostream &O) {
56  int64_t Value = MI->getOperand(OpNum).getImm();
57  assert(isUInt<4>(Value) && "Invalid u4imm argument");
58  O << Value;
59}
60
61void SystemZInstPrinter::printU6ImmOperand(const MCInst *MI, int OpNum,
62                                           raw_ostream &O) {
63  int64_t Value = MI->getOperand(OpNum).getImm();
64  assert(isUInt<6>(Value) && "Invalid u6imm argument");
65  O << Value;
66}
67
68void SystemZInstPrinter::printS8ImmOperand(const MCInst *MI, int OpNum,
69                                           raw_ostream &O) {
70  int64_t Value = MI->getOperand(OpNum).getImm();
71  assert(isInt<8>(Value) && "Invalid s8imm argument");
72  O << Value;
73}
74
75void SystemZInstPrinter::printU8ImmOperand(const MCInst *MI, int OpNum,
76                                           raw_ostream &O) {
77  int64_t Value = MI->getOperand(OpNum).getImm();
78  assert(isUInt<8>(Value) && "Invalid u8imm argument");
79  O << Value;
80}
81
82void SystemZInstPrinter::printS16ImmOperand(const MCInst *MI, int OpNum,
83                                            raw_ostream &O) {
84  int64_t Value = MI->getOperand(OpNum).getImm();
85  assert(isInt<16>(Value) && "Invalid s16imm argument");
86  O << Value;
87}
88
89void SystemZInstPrinter::printU16ImmOperand(const MCInst *MI, int OpNum,
90                                            raw_ostream &O) {
91  int64_t Value = MI->getOperand(OpNum).getImm();
92  assert(isUInt<16>(Value) && "Invalid u16imm argument");
93  O << Value;
94}
95
96void SystemZInstPrinter::printS32ImmOperand(const MCInst *MI, int OpNum,
97                                            raw_ostream &O) {
98  int64_t Value = MI->getOperand(OpNum).getImm();
99  assert(isInt<32>(Value) && "Invalid s32imm argument");
100  O << Value;
101}
102
103void SystemZInstPrinter::printU32ImmOperand(const MCInst *MI, int OpNum,
104                                            raw_ostream &O) {
105  int64_t Value = MI->getOperand(OpNum).getImm();
106  assert(isUInt<32>(Value) && "Invalid u32imm argument");
107  O << Value;
108}
109
110void SystemZInstPrinter::printAccessRegOperand(const MCInst *MI, int OpNum,
111                                               raw_ostream &O) {
112  uint64_t Value = MI->getOperand(OpNum).getImm();
113  assert(Value < 16 && "Invalid access register number");
114  O << "%a" << (unsigned int)Value;
115}
116
117void SystemZInstPrinter::printPCRelOperand(const MCInst *MI, int OpNum,
118                                           raw_ostream &O) {
119  const MCOperand &MO = MI->getOperand(OpNum);
120  if (MO.isImm()) {
121    O << "0x";
122    O.write_hex(MO.getImm());
123  } else
124    O << *MO.getExpr();
125}
126
127void SystemZInstPrinter::printCallOperand(const MCInst *MI, int OpNum,
128                                          raw_ostream &O) {
129  const MCOperand &MO = MI->getOperand(OpNum);
130  if (MO.isImm()) {
131    O << "0x";
132    O.write_hex(MO.getImm());
133  } else {
134    O << *MO.getExpr();
135    O << "@PLT";
136  }
137}
138
139void SystemZInstPrinter::printOperand(const MCInst *MI, int OpNum,
140                                      raw_ostream &O) {
141  printOperand(MI->getOperand(OpNum), O);
142}
143
144void SystemZInstPrinter::printBDAddrOperand(const MCInst *MI, int OpNum,
145                                            raw_ostream &O) {
146  printAddress(MI->getOperand(OpNum).getReg(),
147               MI->getOperand(OpNum + 1).getImm(), 0, O);
148}
149
150void SystemZInstPrinter::printBDXAddrOperand(const MCInst *MI, int OpNum,
151                                             raw_ostream &O) {
152  printAddress(MI->getOperand(OpNum).getReg(),
153               MI->getOperand(OpNum + 1).getImm(),
154               MI->getOperand(OpNum + 2).getReg(), O);
155}
156
157void SystemZInstPrinter::printBDLAddrOperand(const MCInst *MI, int OpNum,
158                                             raw_ostream &O) {
159  unsigned Base = MI->getOperand(OpNum).getReg();
160  uint64_t Disp = MI->getOperand(OpNum + 1).getImm();
161  uint64_t Length = MI->getOperand(OpNum + 2).getImm();
162  O << Disp << '(' << Length;
163  if (Base)
164    O << ",%" << getRegisterName(Base);
165  O << ')';
166}
167
168void SystemZInstPrinter::printCond4Operand(const MCInst *MI, int OpNum,
169                                           raw_ostream &O) {
170  static const char *const CondNames[] = {
171    "o", "h", "nle", "l", "nhe", "lh", "ne",
172    "e", "nlh", "he", "nl", "le", "nh", "no"
173  };
174  uint64_t Imm = MI->getOperand(OpNum).getImm();
175  assert(Imm > 0 && Imm < 15 && "Invalid condition");
176  O << CondNames[Imm - 1];
177}
178