blob: 53b600713e48daed13fa320972fad3fcc3c84836 [file] [log] [blame]
David Goodwinb50ea5c2009-07-02 22:18:33 +00001//===- Thumb2InstrInfo.cpp - Thumb-2 Instruction Information --------*- C++ -*-===//
Anton Korobeynikovd49ea772009-06-26 21:28:53 +00002//
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//
David Goodwinb50ea5c2009-07-02 22:18:33 +000010// This file contains the Thumb-2 implementation of the TargetInstrInfo class.
Anton Korobeynikovd49ea772009-06-26 21:28:53 +000011//
12//===----------------------------------------------------------------------===//
13
14#include "ARMInstrInfo.h"
15#include "ARM.h"
16#include "ARMGenInstrInfo.inc"
17#include "ARMMachineFunctionInfo.h"
18#include "llvm/CodeGen/MachineFrameInfo.h"
19#include "llvm/CodeGen/MachineInstrBuilder.h"
20#include "llvm/ADT/SmallVector.h"
David Goodwinb50ea5c2009-07-02 22:18:33 +000021#include "Thumb2InstrInfo.h"
Anton Korobeynikovd49ea772009-06-26 21:28:53 +000022
23using namespace llvm;
24
David Goodwinb50ea5c2009-07-02 22:18:33 +000025Thumb2InstrInfo::Thumb2InstrInfo(const ARMSubtarget &STI)
Anton Korobeynikova98cbc52009-06-27 12:16:40 +000026 : ARMBaseInstrInfo(STI), RI(*this, STI) {
Anton Korobeynikovd49ea772009-06-26 21:28:53 +000027}
28
Evan Cheng446c4282009-07-11 06:43:01 +000029unsigned Thumb2InstrInfo::getUnindexedOpcode(unsigned Opc) const {
David Goodwin334c2642009-07-08 16:09:28 +000030 // FIXME
31 return 0;
32}
33
Evan Cheng446c4282009-07-11 06:43:01 +000034unsigned Thumb2InstrInfo::getOpcode(ARMII::Op Op) const {
David Goodwin334c2642009-07-08 16:09:28 +000035 switch (Op) {
36 case ARMII::ADDri: return ARM::t2ADDri;
37 case ARMII::ADDrs: return ARM::t2ADDrs;
38 case ARMII::ADDrr: return ARM::t2ADDrr;
39 case ARMII::B: return ARM::t2B;
40 case ARMII::Bcc: return ARM::t2Bcc;
Evan Cheng446c4282009-07-11 06:43:01 +000041 case ARMII::BX_RET: return ARM::tBX_RET;
David Goodwin5ff58b52009-07-24 00:16:18 +000042 case ARMII::LDRri: return ARM::t2LDRi12;
David Goodwin334c2642009-07-08 16:09:28 +000043 case ARMII::MOVr: return ARM::t2MOVr;
David Goodwin5ff58b52009-07-24 00:16:18 +000044 case ARMII::STRri: return ARM::t2STRi12;
David Goodwin334c2642009-07-08 16:09:28 +000045 case ARMII::SUBri: return ARM::t2SUBri;
46 case ARMII::SUBrs: return ARM::t2SUBrs;
47 case ARMII::SUBrr: return ARM::t2SUBrr;
David Goodwin334c2642009-07-08 16:09:28 +000048 default:
49 break;
50 }
51
52 return 0;
53}
54
55bool
56Thumb2InstrInfo::BlockHasNoFallThrough(const MachineBasicBlock &MBB) const {
57 if (MBB.empty()) return false;
58
David Goodwin334c2642009-07-08 16:09:28 +000059 switch (MBB.back().getOpcode()) {
David Goodwinb1beca62009-07-10 15:33:46 +000060 case ARM::t2LDM_RET:
David Goodwin334c2642009-07-08 16:09:28 +000061 case ARM::t2B: // Uncond branch.
Evan Cheng66ac5312009-07-25 00:33:29 +000062 case ARM::t2BR_JT: // Jumptable branch.
Evan Cheng23606e32009-07-24 18:20:16 +000063 case ARM::tBR_JTr: // Jumptable branch (16-bit version).
David Goodwin334c2642009-07-08 16:09:28 +000064 case ARM::tBX_RET:
65 case ARM::tBX_RET_vararg:
66 case ARM::tPOP_RET:
67 case ARM::tB:
David Goodwin334c2642009-07-08 16:09:28 +000068 return true;
69 default:
70 break;
71 }
72
73 return false;
74}
Anton Korobeynikovb8e9ac82009-07-16 23:26:06 +000075
76bool
77Thumb2InstrInfo::copyRegToReg(MachineBasicBlock &MBB,
78 MachineBasicBlock::iterator I,
79 unsigned DestReg, unsigned SrcReg,
80 const TargetRegisterClass *DestRC,
81 const TargetRegisterClass *SrcRC) const {
82 DebugLoc DL = DebugLoc::getUnknownLoc();
83 if (I != MBB.end()) DL = I->getDebugLoc();
84
Evan Cheng08b93c62009-07-27 00:33:08 +000085 if (DestRC == ARM::GPRRegisterClass &&
86 SrcRC == ARM::GPRRegisterClass) {
Evan Chengc6b54d52009-07-25 01:25:08 +000087 AddDefaultCC(AddDefaultPred(BuildMI(MBB, I, DL, get(ARM::t2MOVr),
Anton Korobeynikovb8e9ac82009-07-16 23:26:06 +000088 DestReg).addReg(SrcReg)));
89 return true;
Evan Cheng08b93c62009-07-27 00:33:08 +000090 } else if (DestRC == ARM::GPRRegisterClass &&
91 SrcRC == ARM::tGPRRegisterClass) {
92 BuildMI(MBB, I, DL, get(ARM::tMOVtgpr2gpr), DestReg).addReg(SrcReg);
93 return true;
94 } else if (DestRC == ARM::tGPRRegisterClass &&
95 SrcRC == ARM::GPRRegisterClass) {
96 BuildMI(MBB, I, DL, get(ARM::tMOVgpr2tgpr), DestReg).addReg(SrcReg);
97 return true;
Anton Korobeynikovb8e9ac82009-07-16 23:26:06 +000098 }
99
Evan Cheng08b93c62009-07-27 00:33:08 +0000100 // Handle SPR, DPR, and QPR copies.
Anton Korobeynikovb8e9ac82009-07-16 23:26:06 +0000101 return ARMBaseInstrInfo::copyRegToReg(MBB, I, DestReg, SrcReg, DestRC, SrcRC);
102}
Evan Cheng5732ca02009-07-27 03:14:20 +0000103
104void Thumb2InstrInfo::
105storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
106 unsigned SrcReg, bool isKill, int FI,
107 const TargetRegisterClass *RC) const {
108 DebugLoc DL = DebugLoc::getUnknownLoc();
109 if (I != MBB.end()) DL = I->getDebugLoc();
110
111 if (RC == ARM::GPRRegisterClass) {
112 AddDefaultPred(BuildMI(MBB, I, DL, get(ARM::t2STRi12))
113 .addReg(SrcReg, getKillRegState(isKill))
114 .addFrameIndex(FI).addImm(0));
115 return;
116 }
117
118 ARMBaseInstrInfo::storeRegToStackSlot(MBB, I, SrcReg, isKill, FI, RC);
119}
120
121void Thumb2InstrInfo::
122loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
123 unsigned DestReg, int FI,
124 const TargetRegisterClass *RC) const {
125 DebugLoc DL = DebugLoc::getUnknownLoc();
126 if (I != MBB.end()) DL = I->getDebugLoc();
127
128 if (RC == ARM::GPRRegisterClass) {
129 AddDefaultPred(BuildMI(MBB, I, DL, get(ARM::t2LDRi12), DestReg)
130 .addFrameIndex(FI).addImm(0));
131 return;
132 }
133
134 ARMBaseInstrInfo::loadRegFromStackSlot(MBB, I, DestReg, FI, RC);
135}