11d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand//===-- SystemZMCInstLower.cpp - Lower MachineInstr to MCInst -------------===// 21d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// 31d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// The LLVM Compiler Infrastructure 41d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// 51d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// This file is distributed under the University of Illinois Open Source 61d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// License. See LICENSE.TXT for details. 71d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// 81d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand//===----------------------------------------------------------------------===// 91d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 101d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand#include "SystemZMCInstLower.h" 111d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand#include "SystemZAsmPrinter.h" 1236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines#include "llvm/IR/Mangler.h" 131d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand#include "llvm/MC/MCExpr.h" 141d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand#include "llvm/MC/MCStreamer.h" 151d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 161d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigandusing namespace llvm; 171d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 181d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand// Return the VK_* enumeration for MachineOperand target flags Flags. 191d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigandstatic MCSymbolRefExpr::VariantKind getVariantKind(unsigned Flags) { 201d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand switch (Flags & SystemZII::MO_SYMBOL_MODIFIER) { 211d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand case 0: 221d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand return MCSymbolRefExpr::VK_None; 231d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand case SystemZII::MO_GOT: 241d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand return MCSymbolRefExpr::VK_GOT; 25ebe69fe11e48d322045d5949c83283927a0d790bStephen Hines case SystemZII::MO_INDNTPOFF: 26ebe69fe11e48d322045d5949c83283927a0d790bStephen Hines return MCSymbolRefExpr::VK_INDNTPOFF; 271d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand } 281d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand llvm_unreachable("Unrecognised MO_ACCESS_MODEL"); 291d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand} 301d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 318eff5d998e88ba8763d72f4e94d7a32f2dbb9005Rafael EspindolaSystemZMCInstLower::SystemZMCInstLower(MCContext &ctx, 321d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand SystemZAsmPrinter &asmprinter) 338eff5d998e88ba8763d72f4e94d7a32f2dbb9005Rafael Espindola : Ctx(ctx), AsmPrinter(asmprinter) {} 341d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 3576f8ae87b4705f5c08c3995948223531715a2d58Richard Sandifordconst MCExpr * 3676f8ae87b4705f5c08c3995948223531715a2d58Richard SandifordSystemZMCInstLower::getExpr(const MachineOperand &MO, 3776f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford MCSymbolRefExpr::VariantKind Kind) const { 3876f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford const MCSymbol *Symbol; 3976f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford bool HasOffset = true; 4076f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford switch (MO.getType()) { 4176f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford case MachineOperand::MO_MachineBasicBlock: 4276f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford Symbol = MO.getMBB()->getSymbol(); 4376f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford HasOffset = false; 4476f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford break; 4576f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford 4676f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford case MachineOperand::MO_GlobalAddress: 47ffc7dca885151ed42642c2d6733e8db75d276621Rafael Espindola Symbol = AsmPrinter.getSymbol(MO.getGlobal()); 4876f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford break; 4976f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford 5076f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford case MachineOperand::MO_ExternalSymbol: 5176f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford Symbol = AsmPrinter.GetExternalSymbolSymbol(MO.getSymbolName()); 5276f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford break; 5376f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford 5476f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford case MachineOperand::MO_JumpTableIndex: 5576f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford Symbol = AsmPrinter.GetJTISymbol(MO.getIndex()); 5676f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford HasOffset = false; 5776f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford break; 5876f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford 5976f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford case MachineOperand::MO_ConstantPoolIndex: 6076f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford Symbol = AsmPrinter.GetCPISymbol(MO.getIndex()); 6176f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford break; 6276f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford 6376f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford case MachineOperand::MO_BlockAddress: 6476f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford Symbol = AsmPrinter.GetBlockAddressSymbol(MO.getBlockAddress()); 6576f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford break; 6676f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford 6776f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford default: 6876f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford llvm_unreachable("unknown operand type"); 691d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand } 7076f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford const MCExpr *Expr = MCSymbolRefExpr::Create(Symbol, Kind, Ctx); 7176f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford if (HasOffset) 7276f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford if (int64_t Offset = MO.getOffset()) { 7376f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford const MCExpr *OffsetExpr = MCConstantExpr::Create(Offset, Ctx); 7476f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford Expr = MCBinaryExpr::CreateAdd(Expr, OffsetExpr, Ctx); 7576f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford } 7676f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford return Expr; 771d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand} 781d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 791d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich WeigandMCOperand SystemZMCInstLower::lowerOperand(const MachineOperand &MO) const { 801d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand switch (MO.getType()) { 811d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand case MachineOperand::MO_Register: 821d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand return MCOperand::CreateReg(MO.getReg()); 831d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 841d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand case MachineOperand::MO_Immediate: 851d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand return MCOperand::CreateImm(MO.getImm()); 861d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 8776f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford default: { 8876f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford MCSymbolRefExpr::VariantKind Kind = getVariantKind(MO.getTargetFlags()); 8976f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford return MCOperand::CreateExpr(getExpr(MO, Kind)); 901d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand } 911d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand } 921d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand} 931d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand 941d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigandvoid SystemZMCInstLower::lower(const MachineInstr *MI, MCInst &OutMI) const { 9576f8ae87b4705f5c08c3995948223531715a2d58Richard Sandiford OutMI.setOpcode(MI->getOpcode()); 961d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand for (unsigned I = 0, E = MI->getNumOperands(); I != E; ++I) { 971d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand const MachineOperand &MO = MI->getOperand(I); 985e009541973b7935386055066689902aa7134e2dRichard Sandiford // Ignore all implicit register operands. 995e009541973b7935386055066689902aa7134e2dRichard Sandiford if (!MO.isReg() || !MO.isImplicit()) 1005e009541973b7935386055066689902aa7134e2dRichard Sandiford OutMI.addOperand(lowerOperand(MO)); 1011d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand } 1021d09d56fe1e3f3faadd4bf4ccf3e585ddb3c3b07Ulrich Weigand} 103