LLVM API Documentation
00001 //===-- MSP430MCInstLower.cpp - Convert MSP430 MachineInstr to an MCInst --===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This file contains code to lower MSP430 MachineInstrs to their corresponding 00011 // MCInst records. 00012 // 00013 //===----------------------------------------------------------------------===// 00014 00015 #include "MSP430MCInstLower.h" 00016 #include "llvm/ADT/SmallString.h" 00017 #include "llvm/CodeGen/AsmPrinter.h" 00018 #include "llvm/CodeGen/MachineBasicBlock.h" 00019 #include "llvm/CodeGen/MachineInstr.h" 00020 #include "llvm/MC/MCAsmInfo.h" 00021 #include "llvm/MC/MCContext.h" 00022 #include "llvm/MC/MCExpr.h" 00023 #include "llvm/MC/MCInst.h" 00024 #include "llvm/Support/ErrorHandling.h" 00025 #include "llvm/Support/raw_ostream.h" 00026 #include "llvm/Target/Mangler.h" 00027 using namespace llvm; 00028 00029 MCSymbol *MSP430MCInstLower:: 00030 GetGlobalAddressSymbol(const MachineOperand &MO) const { 00031 switch (MO.getTargetFlags()) { 00032 default: llvm_unreachable("Unknown target flag on GV operand"); 00033 case 0: break; 00034 } 00035 00036 return Printer.Mang->getSymbol(MO.getGlobal()); 00037 } 00038 00039 MCSymbol *MSP430MCInstLower:: 00040 GetExternalSymbolSymbol(const MachineOperand &MO) const { 00041 switch (MO.getTargetFlags()) { 00042 default: llvm_unreachable("Unknown target flag on GV operand"); 00043 case 0: break; 00044 } 00045 00046 return Printer.GetExternalSymbolSymbol(MO.getSymbolName()); 00047 } 00048 00049 MCSymbol *MSP430MCInstLower:: 00050 GetJumpTableSymbol(const MachineOperand &MO) const { 00051 SmallString<256> Name; 00052 raw_svector_ostream(Name) << Printer.MAI->getPrivateGlobalPrefix() << "JTI" 00053 << Printer.getFunctionNumber() << '_' 00054 << MO.getIndex(); 00055 00056 switch (MO.getTargetFlags()) { 00057 default: llvm_unreachable("Unknown target flag on GV operand"); 00058 case 0: break; 00059 } 00060 00061 // Create a symbol for the name. 00062 return Ctx.GetOrCreateSymbol(Name.str()); 00063 } 00064 00065 MCSymbol *MSP430MCInstLower:: 00066 GetConstantPoolIndexSymbol(const MachineOperand &MO) const { 00067 SmallString<256> Name; 00068 raw_svector_ostream(Name) << Printer.MAI->getPrivateGlobalPrefix() << "CPI" 00069 << Printer.getFunctionNumber() << '_' 00070 << MO.getIndex(); 00071 00072 switch (MO.getTargetFlags()) { 00073 default: llvm_unreachable("Unknown target flag on GV operand"); 00074 case 0: break; 00075 } 00076 00077 // Create a symbol for the name. 00078 return Ctx.GetOrCreateSymbol(Name.str()); 00079 } 00080 00081 MCSymbol *MSP430MCInstLower:: 00082 GetBlockAddressSymbol(const MachineOperand &MO) const { 00083 switch (MO.getTargetFlags()) { 00084 default: llvm_unreachable("Unknown target flag on GV operand"); 00085 case 0: break; 00086 } 00087 00088 return Printer.GetBlockAddressSymbol(MO.getBlockAddress()); 00089 } 00090 00091 MCOperand MSP430MCInstLower:: 00092 LowerSymbolOperand(const MachineOperand &MO, MCSymbol *Sym) const { 00093 // FIXME: We would like an efficient form for this, so we don't have to do a 00094 // lot of extra uniquing. 00095 const MCExpr *Expr = MCSymbolRefExpr::Create(Sym, Ctx); 00096 00097 switch (MO.getTargetFlags()) { 00098 default: llvm_unreachable("Unknown target flag on GV operand"); 00099 case 0: break; 00100 } 00101 00102 if (!MO.isJTI() && MO.getOffset()) 00103 Expr = MCBinaryExpr::CreateAdd(Expr, 00104 MCConstantExpr::Create(MO.getOffset(), Ctx), 00105 Ctx); 00106 return MCOperand::CreateExpr(Expr); 00107 } 00108 00109 void MSP430MCInstLower::Lower(const MachineInstr *MI, MCInst &OutMI) const { 00110 OutMI.setOpcode(MI->getOpcode()); 00111 00112 for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) { 00113 const MachineOperand &MO = MI->getOperand(i); 00114 00115 MCOperand MCOp; 00116 switch (MO.getType()) { 00117 default: 00118 MI->dump(); 00119 llvm_unreachable("unknown operand type"); 00120 case MachineOperand::MO_Register: 00121 // Ignore all implicit register operands. 00122 if (MO.isImplicit()) continue; 00123 MCOp = MCOperand::CreateReg(MO.getReg()); 00124 break; 00125 case MachineOperand::MO_Immediate: 00126 MCOp = MCOperand::CreateImm(MO.getImm()); 00127 break; 00128 case MachineOperand::MO_MachineBasicBlock: 00129 MCOp = MCOperand::CreateExpr(MCSymbolRefExpr::Create( 00130 MO.getMBB()->getSymbol(), Ctx)); 00131 break; 00132 case MachineOperand::MO_GlobalAddress: 00133 MCOp = LowerSymbolOperand(MO, GetGlobalAddressSymbol(MO)); 00134 break; 00135 case MachineOperand::MO_ExternalSymbol: 00136 MCOp = LowerSymbolOperand(MO, GetExternalSymbolSymbol(MO)); 00137 break; 00138 case MachineOperand::MO_JumpTableIndex: 00139 MCOp = LowerSymbolOperand(MO, GetJumpTableSymbol(MO)); 00140 break; 00141 case MachineOperand::MO_ConstantPoolIndex: 00142 MCOp = LowerSymbolOperand(MO, GetConstantPoolIndexSymbol(MO)); 00143 break; 00144 case MachineOperand::MO_BlockAddress: 00145 MCOp = LowerSymbolOperand(MO, GetBlockAddressSymbol(MO)); 00146 break; 00147 case MachineOperand::MO_RegisterMask: 00148 continue; 00149 } 00150 00151 OutMI.addOperand(MCOp); 00152 } 00153 }