blob: 9ba169821b1922a6cd5614ac2384005dcbb265d3 [file] [log] [blame]
Chris Lattner9cf0eb52009-10-19 20:21:05 +00001//===-- ARMMCInstLower.cpp - Convert ARM MachineInstr to an MCInst --------===//
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// This file contains code to lower ARM MachineInstrs to their corresponding
11// MCInst records.
12//
13//===----------------------------------------------------------------------===//
14
Chris Lattner112f2392010-11-14 20:31:06 +000015#include "ARM.h"
Chris Lattner96bc2172009-10-20 00:52:47 +000016#include "llvm/CodeGen/AsmPrinter.h"
Jim Grosbach26edbcb2010-09-15 18:47:08 +000017#include "llvm/Constants.h"
Chris Lattner96bc2172009-10-20 00:52:47 +000018#include "llvm/CodeGen/MachineBasicBlock.h"
Chris Lattner6f997762009-10-19 21:53:00 +000019#include "llvm/MC/MCExpr.h"
Chris Lattner9cf0eb52009-10-19 20:21:05 +000020#include "llvm/MC/MCInst.h"
Chris Lattnerd62f1b42010-03-12 21:19:23 +000021#include "llvm/Target/Mangler.h"
Chris Lattner9cf0eb52009-10-19 20:21:05 +000022using namespace llvm;
23
Chris Lattner1612a612010-11-14 20:58:38 +000024
25static MCOperand GetSymbolRef(const MachineOperand &MO, const MCSymbol *Symbol,
26 AsmPrinter &Printer) {
27 MCContext &Ctx = Printer.OutContext;
Chris Lattnerde36af42010-11-14 20:40:08 +000028 const MCExpr *Expr;
29 switch (MO.getTargetFlags()) {
30 default: assert(0 && "Unknown target flag on symbol operand");
31 case 0:
32 Expr = MCSymbolRefExpr::Create(Symbol, MCSymbolRefExpr::VK_None, Ctx);
33 break;
34 case ARMII::MO_LO16:
35 Expr = MCSymbolRefExpr::Create(Symbol, MCSymbolRefExpr::VK_ARM_LO16, Ctx);
36 break;
37 case ARMII::MO_HI16:
38 Expr = MCSymbolRefExpr::Create(Symbol, MCSymbolRefExpr::VK_ARM_HI16, Ctx);
39 break;
40 case ARMII::MO_PLT:
41 Expr = MCSymbolRefExpr::Create(Symbol, MCSymbolRefExpr::VK_ARM_PLT, Ctx);
42 break;
43 }
44
Jim Grosbachc686e332010-09-17 18:25:25 +000045 if (!MO.isJTI() && MO.getOffset())
46 Expr = MCBinaryExpr::CreateAdd(Expr,
47 MCConstantExpr::Create(MO.getOffset(), Ctx),
48 Ctx);
49 return MCOperand::CreateExpr(Expr);
Chris Lattnerde36af42010-11-14 20:40:08 +000050
Jim Grosbachc686e332010-09-17 18:25:25 +000051}
52
Chris Lattner30e2cc22010-11-14 21:00:02 +000053void llvm::LowerARMMachineInstrToMCInst(const MachineInstr *MI, MCInst &OutMI,
Chris Lattner77ec2562010-11-14 21:16:04 +000054 AsmPrinter &AP) {
Chris Lattner9cf0eb52009-10-19 20:21:05 +000055 OutMI.setOpcode(MI->getOpcode());
Jim Grosbachfc16a892010-09-13 18:25:42 +000056
Chris Lattner9cf0eb52009-10-19 20:21:05 +000057 for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
58 const MachineOperand &MO = MI->getOperand(i);
Jim Grosbachfc16a892010-09-13 18:25:42 +000059
Chris Lattner9cf0eb52009-10-19 20:21:05 +000060 MCOperand MCOp;
61 switch (MO.getType()) {
62 default:
63 MI->dump();
64 assert(0 && "unknown operand type");
65 case MachineOperand::MO_Register:
Jim Grosbach1685caf2010-09-14 20:41:27 +000066 // Ignore all non-CPSR implicit register operands.
67 if (MO.isImplicit() && MO.getReg() != ARM::CPSR) continue;
Anton Korobeynikove8ea0112009-11-07 15:20:32 +000068 assert(!MO.getSubReg() && "Subregs should be eliminated!");
Chris Lattner9cf0eb52009-10-19 20:21:05 +000069 MCOp = MCOperand::CreateReg(MO.getReg());
70 break;
71 case MachineOperand::MO_Immediate:
72 MCOp = MCOperand::CreateImm(MO.getImm());
73 break;
Chris Lattner9cf0eb52009-10-19 20:21:05 +000074 case MachineOperand::MO_MachineBasicBlock:
75 MCOp = MCOperand::CreateExpr(MCSymbolRefExpr::Create(
Chris Lattner1612a612010-11-14 20:58:38 +000076 MO.getMBB()->getSymbol(), AP.OutContext));
Chris Lattner9cf0eb52009-10-19 20:21:05 +000077 break;
78 case MachineOperand::MO_GlobalAddress:
Chris Lattner1612a612010-11-14 20:58:38 +000079 MCOp = GetSymbolRef(MO, AP.Mang->getSymbol(MO.getGlobal()), AP);
Chris Lattner9cf0eb52009-10-19 20:21:05 +000080 break;
81 case MachineOperand::MO_ExternalSymbol:
Chris Lattnerde36af42010-11-14 20:40:08 +000082 MCOp = GetSymbolRef(MO,
Chris Lattner1612a612010-11-14 20:58:38 +000083 AP.GetExternalSymbolSymbol(MO.getSymbolName()), AP);
Chris Lattner9cf0eb52009-10-19 20:21:05 +000084 break;
85 case MachineOperand::MO_JumpTableIndex:
Chris Lattner1612a612010-11-14 20:58:38 +000086 MCOp = GetSymbolRef(MO, AP.GetJTISymbol(MO.getIndex()), AP);
Chris Lattner9cf0eb52009-10-19 20:21:05 +000087 break;
88 case MachineOperand::MO_ConstantPoolIndex:
Chris Lattner1612a612010-11-14 20:58:38 +000089 MCOp = GetSymbolRef(MO, AP.GetCPISymbol(MO.getIndex()), AP);
Chris Lattner9cf0eb52009-10-19 20:21:05 +000090 break;
Bob Wilsonddb16df2009-10-30 05:45:42 +000091 case MachineOperand::MO_BlockAddress:
Chris Lattner1612a612010-11-14 20:58:38 +000092 MCOp = GetSymbolRef(MO,AP.GetBlockAddressSymbol(MO.getBlockAddress()),AP);
Bob Wilsonddb16df2009-10-30 05:45:42 +000093 break;
Jim Grosbach26edbcb2010-09-15 18:47:08 +000094 case MachineOperand::MO_FPImmediate:
Jim Grosbach1d51c412010-09-16 17:37:30 +000095 APFloat Val = MO.getFPImm()->getValueAPF();
96 bool ignored;
97 Val.convert(APFloat::IEEEdouble, APFloat::rmTowardZero, &ignored);
98 MCOp = MCOperand::CreateFPImm(Val.convertToDouble());
Jim Grosbach26edbcb2010-09-15 18:47:08 +000099 break;
Chris Lattner9cf0eb52009-10-19 20:21:05 +0000100 }
Jim Grosbachfc16a892010-09-13 18:25:42 +0000101
Chris Lattner9cf0eb52009-10-19 20:21:05 +0000102 OutMI.addOperand(MCOp);
103 }
Chris Lattner9cf0eb52009-10-19 20:21:05 +0000104}