LLVM 20.0.0git
R600InstPrinter.cpp
Go to the documentation of this file.
1//===-- R600InstPrinter.cpp - AMDGPU MC Inst -> ASM ---------------------===//
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// \file
8//===----------------------------------------------------------------------===//
9
10#include "R600InstPrinter.h"
11#include "AMDGPUInstPrinter.h"
12#include "R600MCTargetDesc.h"
13#include "llvm/MC/MCExpr.h"
14#include "llvm/MC/MCInst.h"
15#include "llvm/MC/MCInstrInfo.h"
17
18using namespace llvm;
19
21 StringRef Annot, const MCSubtargetInfo &STI,
22 raw_ostream &O) {
24 printAnnotation(O, Annot);
25}
26
27void R600InstPrinter::printAbs(const MCInst *MI, unsigned OpNo,
28 raw_ostream &O) {
29 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, '|');
30}
31
32void R600InstPrinter::printBankSwizzle(const MCInst *MI, unsigned OpNo,
33 raw_ostream &O) {
34 int BankSwizzle = MI->getOperand(OpNo).getImm();
35 switch (BankSwizzle) {
36 case 1:
37 O << "BS:VEC_021/SCL_122";
38 break;
39 case 2:
40 O << "BS:VEC_120/SCL_212";
41 break;
42 case 3:
43 O << "BS:VEC_102/SCL_221";
44 break;
45 case 4:
46 O << "BS:VEC_201";
47 break;
48 case 5:
49 O << "BS:VEC_210";
50 break;
51 default:
52 break;
53 }
54}
55
56void R600InstPrinter::printClamp(const MCInst *MI, unsigned OpNo,
57 raw_ostream &O) {
58 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, "_SAT");
59}
60
61void R600InstPrinter::printCT(const MCInst *MI, unsigned OpNo, raw_ostream &O) {
62 unsigned CT = MI->getOperand(OpNo).getImm();
63 switch (CT) {
64 case 0:
65 O << 'U';
66 break;
67 case 1:
68 O << 'N';
69 break;
70 default:
71 break;
72 }
73}
74
75void R600InstPrinter::printKCache(const MCInst *MI, unsigned OpNo,
76 raw_ostream &O) {
77 int KCacheMode = MI->getOperand(OpNo).getImm();
78 if (KCacheMode > 0) {
79 int KCacheBank = MI->getOperand(OpNo - 2).getImm();
80 O << "CB" << KCacheBank << ':';
81 int KCacheAddr = MI->getOperand(OpNo + 2).getImm();
82 int LineSize = (KCacheMode == 1) ? 16 : 32;
83 O << KCacheAddr * 16 << '-' << KCacheAddr * 16 + LineSize;
84 }
85}
86
87void R600InstPrinter::printLast(const MCInst *MI, unsigned OpNo,
88 raw_ostream &O) {
89 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, "*", " ");
90}
91
92void R600InstPrinter::printLiteral(const MCInst *MI, unsigned OpNo,
93 raw_ostream &O) {
94 const MCOperand &Op = MI->getOperand(OpNo);
95 assert(Op.isImm() || Op.isExpr());
96 if (Op.isImm()) {
97 int64_t Imm = Op.getImm();
98 O << Imm << '(' << llvm::bit_cast<float>(static_cast<uint32_t>(Imm)) << ')';
99 }
100 if (Op.isExpr()) {
101 Op.getExpr()->print(O << '@', &MAI);
102 }
103}
104
105void R600InstPrinter::printNeg(const MCInst *MI, unsigned OpNo,
106 raw_ostream &O) {
107 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, '-');
108}
109
110void R600InstPrinter::printOMOD(const MCInst *MI, unsigned OpNo,
111 raw_ostream &O) {
112 switch (MI->getOperand(OpNo).getImm()) {
113 default:
114 break;
115 case 1:
116 O << " * 2.0";
117 break;
118 case 2:
119 O << " * 4.0";
120 break;
121 case 3:
122 O << " / 2.0";
123 break;
124 }
125}
126
127void R600InstPrinter::printMemOperand(const MCInst *MI, unsigned OpNo,
128 raw_ostream &O) {
129 printOperand(MI, OpNo, O);
130 O << ", ";
131 printOperand(MI, OpNo + 1, O);
132}
133
134void R600InstPrinter::printOperand(const MCInst *MI, unsigned OpNo,
135 raw_ostream &O) {
136 if (OpNo >= MI->getNumOperands()) {
137 O << "/*Missing OP" << OpNo << "*/";
138 return;
139 }
140
141 const MCOperand &Op = MI->getOperand(OpNo);
142 if (Op.isReg()) {
143 switch (Op.getReg().id()) {
144 // This is the default predicate state, so we don't need to print it.
145 case R600::PRED_SEL_OFF:
146 break;
147
148 default:
149 O << getRegisterName(Op.getReg());
150 break;
151 }
152 } else if (Op.isImm()) {
153 O << Op.getImm();
154 } else if (Op.isDFPImm()) {
155 // We special case 0.0 because otherwise it will be printed as an integer.
156 if (Op.getDFPImm() == 0.0)
157 O << "0.0";
158 else {
159 O << bit_cast<double>(Op.getDFPImm());
160 }
161 } else if (Op.isExpr()) {
162 const MCExpr *Exp = Op.getExpr();
163 Exp->print(O, &MAI);
164 } else {
165 O << "/*INV_OP*/";
166 }
167}
168
169void R600InstPrinter::printRel(const MCInst *MI, unsigned OpNo,
170 raw_ostream &O) {
171 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, '+');
172}
173
174void R600InstPrinter::printRSel(const MCInst *MI, unsigned OpNo,
175 raw_ostream &O) {
176 unsigned Sel = MI->getOperand(OpNo).getImm();
177 switch (Sel) {
178 case 0:
179 O << 'X';
180 break;
181 case 1:
182 O << 'Y';
183 break;
184 case 2:
185 O << 'Z';
186 break;
187 case 3:
188 O << 'W';
189 break;
190 case 4:
191 O << '0';
192 break;
193 case 5:
194 O << '1';
195 break;
196 case 7:
197 O << '_';
198 break;
199 default:
200 break;
201 }
202}
203
205 raw_ostream &O) {
206 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, "ExecMask,");
207}
208
209void R600InstPrinter::printUpdatePred(const MCInst *MI, unsigned OpNo,
210 raw_ostream &O) {
211 AMDGPUInstPrinter::printIfSet(MI, OpNo, O, "Pred,");
212}
213
214void R600InstPrinter::printWrite(const MCInst *MI, unsigned OpNo,
215 raw_ostream &O) {
216 const MCOperand &Op = MI->getOperand(OpNo);
217 if (Op.getImm() == 0) {
218 O << " (MASKED)";
219 }
220}
221
222#include "R600GenAsmWriter.inc"
IRTranslator LLVM IR MI
Provides R600 specific target descriptions.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static void printIfSet(const MCInst *MI, unsigned OpNo, raw_ostream &O, StringRef Asm, StringRef Default="")
This class represents an Operation in the Expression.
bool print(raw_ostream &OS, DIDumpOptions DumpOpts, const DWARFExpression *Expr, DWARFUnit *U) const
Base class for the full range of assembler expressions which are needed for parsing.
Definition: MCExpr.h:34
void printAnnotation(raw_ostream &OS, StringRef Annot)
Utility function for printing annotations.
const MCAsmInfo & MAI
Definition: MCInstPrinter.h:52
Instances of this class represent a single low-level machine instruction.
Definition: MCInst.h:185
Instances of this class represent operands of the MCInst class.
Definition: MCInst.h:37
Generic base class for all target subtargets.
static const char * getRegisterName(MCRegister Reg)
void printAbs(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printClamp(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printUpdateExecMask(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printRel(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printRSel(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printNeg(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printOMOD(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printUpdatePred(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printLiteral(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printInstruction(const MCInst *MI, uint64_t Address, raw_ostream &O)
void printWrite(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printCT(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printInst(const MCInst *MI, uint64_t Address, StringRef Annot, const MCSubtargetInfo &STI, raw_ostream &O) override
Print the specified MCInst to the specified raw_ostream.
void printMemOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printLast(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printKCache(const MCInst *MI, unsigned OpNo, raw_ostream &O)
void printBankSwizzle(const MCInst *MI, unsigned OpNo, raw_ostream &O)
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:51
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition: raw_ostream.h:52
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18