xref: /llvm-project/llvm/lib/Target/CSKY/CSKYAsmPrinter.cpp (revision 7a2a36f952e5f1c0184e5de0bb8a32b5d2382427)
1cf78715cSZi Xuan Wu //===-- CSKYAsmPrinter.cpp - CSKY LLVM assembly writer --------------------===//
2cf78715cSZi Xuan Wu //
3cf78715cSZi Xuan Wu // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4cf78715cSZi Xuan Wu // See https://llvm.org/LICENSE.txt for license information.
5cf78715cSZi Xuan Wu // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6cf78715cSZi Xuan Wu //
7cf78715cSZi Xuan Wu //===----------------------------------------------------------------------===//
8cf78715cSZi Xuan Wu //
9cf78715cSZi Xuan Wu // This file contains a printer that converts from our internal representation
10cf78715cSZi Xuan Wu // of machine-dependent LLVM code to the CSKY assembly language.
11cf78715cSZi Xuan Wu //
12cf78715cSZi Xuan Wu //===----------------------------------------------------------------------===//
13cf78715cSZi Xuan Wu #include "CSKYAsmPrinter.h"
14cf78715cSZi Xuan Wu #include "CSKY.h"
158ddc8169SZi Xuan Wu #include "CSKYConstantPoolValue.h"
16cf78715cSZi Xuan Wu #include "CSKYTargetMachine.h"
17cf78715cSZi Xuan Wu #include "MCTargetDesc/CSKYInstPrinter.h"
18cf78715cSZi Xuan Wu #include "MCTargetDesc/CSKYMCExpr.h"
1932977589SZi Xuan Wu #include "MCTargetDesc/CSKYTargetStreamer.h"
20cf78715cSZi Xuan Wu #include "TargetInfo/CSKYTargetInfo.h"
21cf78715cSZi Xuan Wu #include "llvm/ADT/Statistic.h"
22cf78715cSZi Xuan Wu #include "llvm/CodeGen/AsmPrinter.h"
23cf78715cSZi Xuan Wu #include "llvm/CodeGen/MachineConstantPool.h"
24989f1c72Sserge-sans-paille #include "llvm/CodeGen/MachineFrameInfo.h"
25cf78715cSZi Xuan Wu #include "llvm/IR/DataLayout.h"
26cf78715cSZi Xuan Wu #include "llvm/MC/MCAsmInfo.h"
27cf78715cSZi Xuan Wu #include "llvm/MC/MCContext.h"
28cf78715cSZi Xuan Wu #include "llvm/MC/MCInstBuilder.h"
29cf78715cSZi Xuan Wu #include "llvm/MC/MCStreamer.h"
30cf78715cSZi Xuan Wu #include "llvm/MC/TargetRegistry.h"
31cf78715cSZi Xuan Wu 
32cf78715cSZi Xuan Wu using namespace llvm;
33cf78715cSZi Xuan Wu 
34cf78715cSZi Xuan Wu #define DEBUG_TYPE "csky-asm-printer"
35cf78715cSZi Xuan Wu 
36bdd7c53dSZi Xuan Wu STATISTIC(CSKYNumInstrsCompressed,
37bdd7c53dSZi Xuan Wu           "Number of C-SKY Compressed instructions emitted");
38bdd7c53dSZi Xuan Wu 
39cf78715cSZi Xuan Wu CSKYAsmPrinter::CSKYAsmPrinter(llvm::TargetMachine &TM,
40cf78715cSZi Xuan Wu                                std::unique_ptr<llvm::MCStreamer> Streamer)
41cf78715cSZi Xuan Wu     : AsmPrinter(TM, std::move(Streamer)), MCInstLowering(OutContext, *this) {}
42cf78715cSZi Xuan Wu 
43cf78715cSZi Xuan Wu bool CSKYAsmPrinter::runOnMachineFunction(MachineFunction &MF) {
44065e0324SZi Xuan Wu   MCP = MF.getConstantPool();
4532977589SZi Xuan Wu   TII = MF.getSubtarget().getInstrInfo();
4632977589SZi Xuan Wu 
4732977589SZi Xuan Wu   // Set the current MCSubtargetInfo to a copy which has the correct
4832977589SZi Xuan Wu   // feature bits for the current MachineFunction
4932977589SZi Xuan Wu   MCSubtargetInfo &NewSTI =
5032977589SZi Xuan Wu       OutStreamer->getContext().getSubtargetCopy(*TM.getMCSubtargetInfo());
5132977589SZi Xuan Wu   NewSTI.setFeatureBits(MF.getSubtarget().getFeatureBits());
5232977589SZi Xuan Wu   Subtarget = &NewSTI;
5332977589SZi Xuan Wu 
54cf78715cSZi Xuan Wu   return AsmPrinter::runOnMachineFunction(MF);
55cf78715cSZi Xuan Wu }
56cf78715cSZi Xuan Wu 
57bdd7c53dSZi Xuan Wu #define GEN_COMPRESS_INSTR
58bdd7c53dSZi Xuan Wu #include "CSKYGenCompressInstEmitter.inc"
59bdd7c53dSZi Xuan Wu void CSKYAsmPrinter::EmitToStreamer(MCStreamer &S, const MCInst &Inst) {
60bdd7c53dSZi Xuan Wu   MCInst CInst;
61e4abfc4cSwangpc   bool Res = compressInst(CInst, Inst, *Subtarget);
62bdd7c53dSZi Xuan Wu   if (Res)
63bdd7c53dSZi Xuan Wu     ++CSKYNumInstrsCompressed;
64bdd7c53dSZi Xuan Wu   AsmPrinter::EmitToStreamer(*OutStreamer, Res ? CInst : Inst);
65bdd7c53dSZi Xuan Wu }
66bdd7c53dSZi Xuan Wu 
67cf78715cSZi Xuan Wu // Simple pseudo-instructions have their lowering (with expansion to real
68cf78715cSZi Xuan Wu // instructions) auto-generated.
69cf78715cSZi Xuan Wu #include "CSKYGenMCPseudoLowering.inc"
70cf78715cSZi Xuan Wu 
7182bb8a58SZi Xuan Wu void CSKYAsmPrinter::expandTLSLA(const MachineInstr *MI) {
7282bb8a58SZi Xuan Wu   DebugLoc DL = MI->getDebugLoc();
7382bb8a58SZi Xuan Wu 
7482bb8a58SZi Xuan Wu   MCSymbol *PCLabel = OutContext.getOrCreateSymbol(
7582bb8a58SZi Xuan Wu       Twine(MAI->getPrivateGlobalPrefix()) + "PC" + Twine(getFunctionNumber()) +
7682bb8a58SZi Xuan Wu       "_" + Twine(MI->getOperand(3).getImm()));
7782bb8a58SZi Xuan Wu 
7882bb8a58SZi Xuan Wu   OutStreamer->emitLabel(PCLabel);
7982bb8a58SZi Xuan Wu 
8082bb8a58SZi Xuan Wu   auto Instr = BuildMI(*MF, DL, TII->get(CSKY::LRW32))
8182bb8a58SZi Xuan Wu                    .add(MI->getOperand(0))
8282bb8a58SZi Xuan Wu                    .add(MI->getOperand(2));
8382bb8a58SZi Xuan Wu   MCInst LRWInst;
8482bb8a58SZi Xuan Wu   MCInstLowering.Lower(Instr, LRWInst);
8582bb8a58SZi Xuan Wu   EmitToStreamer(*OutStreamer, LRWInst);
8682bb8a58SZi Xuan Wu 
8782bb8a58SZi Xuan Wu   Instr = BuildMI(*MF, DL, TII->get(CSKY::GRS32))
8882bb8a58SZi Xuan Wu               .add(MI->getOperand(1))
8982bb8a58SZi Xuan Wu               .addSym(PCLabel);
9082bb8a58SZi Xuan Wu   MCInst GRSInst;
9182bb8a58SZi Xuan Wu   MCInstLowering.Lower(Instr, GRSInst);
9282bb8a58SZi Xuan Wu   EmitToStreamer(*OutStreamer, GRSInst);
9382bb8a58SZi Xuan Wu   return;
9482bb8a58SZi Xuan Wu }
9582bb8a58SZi Xuan Wu 
96065e0324SZi Xuan Wu void CSKYAsmPrinter::emitCustomConstantPool(const MachineInstr *MI) {
97065e0324SZi Xuan Wu 
98065e0324SZi Xuan Wu   // This instruction represents a floating constant pool in the function.
99065e0324SZi Xuan Wu   // The first operand is the ID# for this instruction, the second is the
100065e0324SZi Xuan Wu   // index into the MachineConstantPool that this is, the third is the size
101065e0324SZi Xuan Wu   // in bytes of this constant pool entry.
102065e0324SZi Xuan Wu   // The required alignment is specified on the basic block holding this MI.
103065e0324SZi Xuan Wu   unsigned LabelId = (unsigned)MI->getOperand(0).getImm();
104065e0324SZi Xuan Wu   unsigned CPIdx = (unsigned)MI->getOperand(1).getIndex();
105065e0324SZi Xuan Wu 
106065e0324SZi Xuan Wu   // If this is the first entry of the pool, mark it.
107065e0324SZi Xuan Wu   if (!InConstantPool) {
108e52a41d0SZi Xuan Wu (Zeson)     OutStreamer->emitValueToAlignment(Align(4));
109065e0324SZi Xuan Wu     InConstantPool = true;
110065e0324SZi Xuan Wu   }
111065e0324SZi Xuan Wu 
112065e0324SZi Xuan Wu   OutStreamer->emitLabel(GetCPISymbol(LabelId));
113065e0324SZi Xuan Wu 
114065e0324SZi Xuan Wu   const MachineConstantPoolEntry &MCPE = MCP->getConstants()[CPIdx];
115065e0324SZi Xuan Wu   if (MCPE.isMachineConstantPoolEntry())
116065e0324SZi Xuan Wu     emitMachineConstantPoolValue(MCPE.Val.MachineCPVal);
117065e0324SZi Xuan Wu   else
118065e0324SZi Xuan Wu     emitGlobalConstant(MF->getDataLayout(), MCPE.Val.ConstVal);
119065e0324SZi Xuan Wu   return;
120065e0324SZi Xuan Wu }
121065e0324SZi Xuan Wu 
122065e0324SZi Xuan Wu void CSKYAsmPrinter::emitFunctionBodyEnd() {
123065e0324SZi Xuan Wu   // Make sure to terminate any constant pools that were at the end
124065e0324SZi Xuan Wu   // of the function.
125065e0324SZi Xuan Wu   if (!InConstantPool)
126065e0324SZi Xuan Wu     return;
127065e0324SZi Xuan Wu   InConstantPool = false;
128065e0324SZi Xuan Wu }
129065e0324SZi Xuan Wu 
13032977589SZi Xuan Wu void CSKYAsmPrinter::emitStartOfAsmFile(Module &M) {
13132977589SZi Xuan Wu   if (TM.getTargetTriple().isOSBinFormatELF())
13232977589SZi Xuan Wu     emitAttributes();
13332977589SZi Xuan Wu }
13432977589SZi Xuan Wu 
13532977589SZi Xuan Wu void CSKYAsmPrinter::emitEndOfAsmFile(Module &M) {
13632977589SZi Xuan Wu   CSKYTargetStreamer &CTS =
13732977589SZi Xuan Wu       static_cast<CSKYTargetStreamer &>(*OutStreamer->getTargetStreamer());
13832977589SZi Xuan Wu 
13932977589SZi Xuan Wu   if (TM.getTargetTriple().isOSBinFormatELF())
14032977589SZi Xuan Wu     CTS.finishAttributeSection();
14132977589SZi Xuan Wu }
14232977589SZi Xuan Wu 
143cf78715cSZi Xuan Wu void CSKYAsmPrinter::emitInstruction(const MachineInstr *MI) {
1443e0bf1c7SDavid Green   CSKY_MC::verifyInstructionPredicates(MI->getOpcode(),
1453e0bf1c7SDavid Green                                        getSubtargetInfo().getFeatureBits());
1463e0bf1c7SDavid Green 
147cf78715cSZi Xuan Wu   // Do any auto-generated pseudo lowerings.
148*7a2a36f9SSergei Barannikov   if (MCInst OutInst; lowerPseudoInstExpansion(MI, OutInst)) {
149*7a2a36f9SSergei Barannikov     EmitToStreamer(*OutStreamer, OutInst);
150cf78715cSZi Xuan Wu     return;
151*7a2a36f9SSergei Barannikov   }
152cf78715cSZi Xuan Wu 
153065e0324SZi Xuan Wu   // If we just ended a constant pool, mark it as such.
154065e0324SZi Xuan Wu   if (InConstantPool && MI->getOpcode() != CSKY::CONSTPOOL_ENTRY) {
155065e0324SZi Xuan Wu     InConstantPool = false;
156065e0324SZi Xuan Wu   }
157065e0324SZi Xuan Wu 
15882bb8a58SZi Xuan Wu   if (MI->getOpcode() == CSKY::PseudoTLSLA32)
15982bb8a58SZi Xuan Wu     return expandTLSLA(MI);
16082bb8a58SZi Xuan Wu 
161065e0324SZi Xuan Wu   if (MI->getOpcode() == CSKY::CONSTPOOL_ENTRY)
162065e0324SZi Xuan Wu     return emitCustomConstantPool(MI);
163065e0324SZi Xuan Wu 
164cf78715cSZi Xuan Wu   MCInst TmpInst;
165cf78715cSZi Xuan Wu   MCInstLowering.Lower(MI, TmpInst);
166cf78715cSZi Xuan Wu   EmitToStreamer(*OutStreamer, TmpInst);
167cf78715cSZi Xuan Wu }
168cf78715cSZi Xuan Wu 
1698ddc8169SZi Xuan Wu // Convert a CSKY-specific constant pool modifier into the associated
1708ddc8169SZi Xuan Wu // MCSymbolRefExpr variant kind.
1718ddc8169SZi Xuan Wu static CSKYMCExpr::VariantKind
1728ddc8169SZi Xuan Wu getModifierVariantKind(CSKYCP::CSKYCPModifier Modifier) {
1738ddc8169SZi Xuan Wu   switch (Modifier) {
1748ddc8169SZi Xuan Wu   case CSKYCP::NO_MOD:
1758ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_None;
1768ddc8169SZi Xuan Wu   case CSKYCP::ADDR:
1778ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_ADDR;
1788ddc8169SZi Xuan Wu   case CSKYCP::GOT:
1798ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_GOT;
1808ddc8169SZi Xuan Wu   case CSKYCP::GOTOFF:
1818ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_GOTOFF;
1828ddc8169SZi Xuan Wu   case CSKYCP::PLT:
1838ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_PLT;
1848ddc8169SZi Xuan Wu   case CSKYCP::TLSGD:
1858ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_TLSGD;
1868ddc8169SZi Xuan Wu   case CSKYCP::TLSLE:
1878ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_TLSLE;
1888ddc8169SZi Xuan Wu   case CSKYCP::TLSIE:
1898ddc8169SZi Xuan Wu     return CSKYMCExpr::VK_CSKY_TLSIE;
1908ddc8169SZi Xuan Wu   }
1918ddc8169SZi Xuan Wu   llvm_unreachable("Invalid CSKYCPModifier!");
1928ddc8169SZi Xuan Wu }
1938ddc8169SZi Xuan Wu 
1948ddc8169SZi Xuan Wu void CSKYAsmPrinter::emitMachineConstantPoolValue(
1958ddc8169SZi Xuan Wu     MachineConstantPoolValue *MCPV) {
1968ddc8169SZi Xuan Wu   int Size = getDataLayout().getTypeAllocSize(MCPV->getType());
1978ddc8169SZi Xuan Wu   CSKYConstantPoolValue *CCPV = static_cast<CSKYConstantPoolValue *>(MCPV);
1988ddc8169SZi Xuan Wu   MCSymbol *MCSym;
1998ddc8169SZi Xuan Wu 
2008ddc8169SZi Xuan Wu   if (CCPV->isBlockAddress()) {
2018ddc8169SZi Xuan Wu     const BlockAddress *BA =
2028ddc8169SZi Xuan Wu         cast<CSKYConstantPoolConstant>(CCPV)->getBlockAddress();
2038ddc8169SZi Xuan Wu     MCSym = GetBlockAddressSymbol(BA);
2048ddc8169SZi Xuan Wu   } else if (CCPV->isGlobalValue()) {
2058ddc8169SZi Xuan Wu     const GlobalValue *GV = cast<CSKYConstantPoolConstant>(CCPV)->getGV();
2068ddc8169SZi Xuan Wu     MCSym = getSymbol(GV);
2078ddc8169SZi Xuan Wu   } else if (CCPV->isMachineBasicBlock()) {
2088ddc8169SZi Xuan Wu     const MachineBasicBlock *MBB = cast<CSKYConstantPoolMBB>(CCPV)->getMBB();
2098ddc8169SZi Xuan Wu     MCSym = MBB->getSymbol();
2108ddc8169SZi Xuan Wu   } else if (CCPV->isJT()) {
2118ddc8169SZi Xuan Wu     signed JTI = cast<CSKYConstantPoolJT>(CCPV)->getJTI();
2128ddc8169SZi Xuan Wu     MCSym = GetJTISymbol(JTI);
213f4d61cdfSZi Xuan Wu (Zeson)   } else if (CCPV->isConstPool()) {
214f4d61cdfSZi Xuan Wu (Zeson)     const Constant *C = cast<CSKYConstantPoolConstant>(CCPV)->getConstantPool();
215f4d61cdfSZi Xuan Wu (Zeson)     MCSym = GetCPISymbol(MCP->getConstantPoolIndex(C, Align(4)));
2168ddc8169SZi Xuan Wu   } else {
2178ddc8169SZi Xuan Wu     assert(CCPV->isExtSymbol() && "unrecognized constant pool value");
2188ddc8169SZi Xuan Wu     StringRef Sym = cast<CSKYConstantPoolSymbol>(CCPV)->getSymbol();
2198ddc8169SZi Xuan Wu     MCSym = GetExternalSymbolSymbol(Sym);
2208ddc8169SZi Xuan Wu   }
2218ddc8169SZi Xuan Wu   // Create an MCSymbol for the reference.
2228ddc8169SZi Xuan Wu   const MCExpr *Expr =
2238ddc8169SZi Xuan Wu       MCSymbolRefExpr::create(MCSym, MCSymbolRefExpr::VK_None, OutContext);
2248ddc8169SZi Xuan Wu 
2258ddc8169SZi Xuan Wu   if (CCPV->getPCAdjustment()) {
2268ddc8169SZi Xuan Wu 
2278ddc8169SZi Xuan Wu     MCSymbol *PCLabel = OutContext.getOrCreateSymbol(
2288ddc8169SZi Xuan Wu         Twine(MAI->getPrivateGlobalPrefix()) + "PC" +
2298ddc8169SZi Xuan Wu         Twine(getFunctionNumber()) + "_" + Twine(CCPV->getLabelID()));
2308ddc8169SZi Xuan Wu 
2318ddc8169SZi Xuan Wu     const MCExpr *PCRelExpr = MCSymbolRefExpr::create(PCLabel, OutContext);
2328ddc8169SZi Xuan Wu     if (CCPV->mustAddCurrentAddress()) {
2338ddc8169SZi Xuan Wu       // We want "(<expr> - .)", but MC doesn't have a concept of the '.'
2348ddc8169SZi Xuan Wu       // label, so just emit a local label end reference that instead.
2358ddc8169SZi Xuan Wu       MCSymbol *DotSym = OutContext.createTempSymbol();
2368ddc8169SZi Xuan Wu       OutStreamer->emitLabel(DotSym);
2378ddc8169SZi Xuan Wu       const MCExpr *DotExpr = MCSymbolRefExpr::create(DotSym, OutContext);
2388ddc8169SZi Xuan Wu       PCRelExpr = MCBinaryExpr::createSub(PCRelExpr, DotExpr, OutContext);
2398ddc8169SZi Xuan Wu     }
2408ddc8169SZi Xuan Wu     Expr = MCBinaryExpr::createSub(Expr, PCRelExpr, OutContext);
2418ddc8169SZi Xuan Wu   }
2428ddc8169SZi Xuan Wu 
2438ddc8169SZi Xuan Wu   // Create an MCSymbol for the reference.
2448ddc8169SZi Xuan Wu   Expr = CSKYMCExpr::create(Expr, getModifierVariantKind(CCPV->getModifier()),
2458ddc8169SZi Xuan Wu                             OutContext);
2468ddc8169SZi Xuan Wu 
2478ddc8169SZi Xuan Wu   OutStreamer->emitValue(Expr, Size);
2488ddc8169SZi Xuan Wu }
2498ddc8169SZi Xuan Wu 
25032977589SZi Xuan Wu void CSKYAsmPrinter::emitAttributes() {
25132977589SZi Xuan Wu   CSKYTargetStreamer &CTS =
25232977589SZi Xuan Wu       static_cast<CSKYTargetStreamer &>(*OutStreamer->getTargetStreamer());
25332977589SZi Xuan Wu 
25432977589SZi Xuan Wu   const Triple &TT = TM.getTargetTriple();
25532977589SZi Xuan Wu   StringRef CPU = TM.getTargetCPU();
25632977589SZi Xuan Wu   StringRef FS = TM.getTargetFeatureString();
25732977589SZi Xuan Wu   const CSKYTargetMachine &CTM = static_cast<const CSKYTargetMachine &>(TM);
25832977589SZi Xuan Wu   /* TuneCPU doesn't impact emission of ELF attributes, ELF attributes only
25932977589SZi Xuan Wu      care about arch related features, so we can set TuneCPU as CPU.  */
26032977589SZi Xuan Wu   const CSKYSubtarget STI(TT, CPU, /*TuneCPU=*/CPU, FS, CTM);
26132977589SZi Xuan Wu 
26232977589SZi Xuan Wu   CTS.emitTargetAttributes(STI);
26332977589SZi Xuan Wu }
26432977589SZi Xuan Wu 
265a190fcdfSZi Xuan Wu bool CSKYAsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNo,
266a190fcdfSZi Xuan Wu                                      const char *ExtraCode, raw_ostream &OS) {
267a190fcdfSZi Xuan Wu   // First try the generic code, which knows about modifiers like 'c' and 'n'.
268a190fcdfSZi Xuan Wu   if (!AsmPrinter::PrintAsmOperand(MI, OpNo, ExtraCode, OS))
269a190fcdfSZi Xuan Wu     return false;
270a190fcdfSZi Xuan Wu 
271a190fcdfSZi Xuan Wu   const MachineOperand &MO = MI->getOperand(OpNo);
272a190fcdfSZi Xuan Wu   if (ExtraCode && ExtraCode[0]) {
273a190fcdfSZi Xuan Wu     if (ExtraCode[1] != 0)
274a190fcdfSZi Xuan Wu       return true; // Unknown modifier.
275a190fcdfSZi Xuan Wu 
276a190fcdfSZi Xuan Wu     switch (ExtraCode[0]) {
277a190fcdfSZi Xuan Wu     default:
278a190fcdfSZi Xuan Wu       return true; // Unknown modifier.
279a190fcdfSZi Xuan Wu     case 'R':
280a190fcdfSZi Xuan Wu       if (MO.getType() == MachineOperand::MO_Register) {
281a190fcdfSZi Xuan Wu         OS << CSKYInstPrinter::getRegisterName(MO.getReg() + 1);
282a190fcdfSZi Xuan Wu         return false;
283a190fcdfSZi Xuan Wu       }
284a190fcdfSZi Xuan Wu     }
285a190fcdfSZi Xuan Wu   }
286a190fcdfSZi Xuan Wu 
287a190fcdfSZi Xuan Wu   switch (MO.getType()) {
288a190fcdfSZi Xuan Wu   case MachineOperand::MO_Immediate:
289a190fcdfSZi Xuan Wu     OS << MO.getImm();
290a190fcdfSZi Xuan Wu     return false;
291a190fcdfSZi Xuan Wu   case MachineOperand::MO_Register:
292a190fcdfSZi Xuan Wu     if (MO.getReg() == CSKY::C)
293a190fcdfSZi Xuan Wu       return false;
294a190fcdfSZi Xuan Wu     OS << CSKYInstPrinter::getRegisterName(MO.getReg());
295a190fcdfSZi Xuan Wu     return false;
296a190fcdfSZi Xuan Wu   case MachineOperand::MO_GlobalAddress:
297a190fcdfSZi Xuan Wu     PrintSymbolOperand(MO, OS);
298a190fcdfSZi Xuan Wu     return false;
299a190fcdfSZi Xuan Wu   case MachineOperand::MO_BlockAddress: {
300a190fcdfSZi Xuan Wu     MCSymbol *Sym = GetBlockAddressSymbol(MO.getBlockAddress());
301a190fcdfSZi Xuan Wu     Sym->print(OS, MAI);
302a190fcdfSZi Xuan Wu     return false;
303a190fcdfSZi Xuan Wu   }
304a190fcdfSZi Xuan Wu   default:
305a190fcdfSZi Xuan Wu     break;
306a190fcdfSZi Xuan Wu   }
307a190fcdfSZi Xuan Wu 
308a190fcdfSZi Xuan Wu   return true;
309a190fcdfSZi Xuan Wu }
310a190fcdfSZi Xuan Wu 
311a190fcdfSZi Xuan Wu bool CSKYAsmPrinter::PrintAsmMemoryOperand(const MachineInstr *MI,
312a190fcdfSZi Xuan Wu                                            unsigned OpNo, const char *ExtraCode,
313a190fcdfSZi Xuan Wu                                            raw_ostream &OS) {
314a190fcdfSZi Xuan Wu   if (!ExtraCode) {
315a190fcdfSZi Xuan Wu     const MachineOperand &MO = MI->getOperand(OpNo);
316a190fcdfSZi Xuan Wu     // For now, we only support register memory operands in registers and
317a190fcdfSZi Xuan Wu     // assume there is no addend
318a190fcdfSZi Xuan Wu     if (!MO.isReg())
319a190fcdfSZi Xuan Wu       return true;
320a190fcdfSZi Xuan Wu 
321a190fcdfSZi Xuan Wu     OS << "(" << CSKYInstPrinter::getRegisterName(MO.getReg()) << ", 0)";
322a190fcdfSZi Xuan Wu     return false;
323a190fcdfSZi Xuan Wu   }
324a190fcdfSZi Xuan Wu 
325a190fcdfSZi Xuan Wu   return AsmPrinter::PrintAsmMemoryOperand(MI, OpNo, ExtraCode, OS);
326a190fcdfSZi Xuan Wu }
327a190fcdfSZi Xuan Wu 
328cf78715cSZi Xuan Wu extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeCSKYAsmPrinter() {
329cf78715cSZi Xuan Wu   RegisterAsmPrinter<CSKYAsmPrinter> X(getTheCSKYTarget());
330cf78715cSZi Xuan Wu }
331