MipsInstrInfo.cpp revision 1acb7df498485249d92f62febeaefd91cae3d98c
1//===- MipsInstrInfo.cpp - Mips Instruction Information ---------*- C++ -*-===//
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 the Mips implementation of the TargetInstrInfo class.
11//
12//===----------------------------------------------------------------------===//
13
14#include "MipsInstrInfo.h"
15#include "MipsTargetMachine.h"
16#include "MipsMachineFunction.h"
17#include "InstPrinter/MipsInstPrinter.h"
18#include "llvm/CodeGen/MachineInstrBuilder.h"
19#include "llvm/CodeGen/MachineRegisterInfo.h"
20#include "llvm/Support/ErrorHandling.h"
21#include "llvm/Support/TargetRegistry.h"
22#include "llvm/ADT/STLExtras.h"
23
24#define GET_INSTRINFO_CTOR
25#include "MipsGenInstrInfo.inc"
26
27using namespace llvm;
28
29MipsInstrInfo::MipsInstrInfo(MipsTargetMachine &tm)
30  : MipsGenInstrInfo(Mips::ADJCALLSTACKDOWN, Mips::ADJCALLSTACKUP),
31    TM(tm), IsN64(TM.getSubtarget<MipsSubtarget>().isABI_N64()),
32    RI(*TM.getSubtargetImpl(), *this) {}
33
34
35const MipsRegisterInfo &MipsInstrInfo::getRegisterInfo() const {
36  return RI;
37}
38
39static bool isZeroImm(const MachineOperand &op) {
40  return op.isImm() && op.getImm() == 0;
41}
42
43/// isLoadFromStackSlot - If the specified machine instruction is a direct
44/// load from a stack slot, return the virtual or physical register number of
45/// the destination along with the FrameIndex of the loaded stack slot.  If
46/// not, return 0.  This predicate must return 0 if the instruction has
47/// any side effects other than loading from the stack slot.
48unsigned MipsInstrInfo::
49isLoadFromStackSlot(const MachineInstr *MI, int &FrameIndex) const
50{
51  unsigned Opc = MI->getOpcode();
52
53  if ((Opc == Mips::LW)    || (Opc == Mips::LW_P8)  || (Opc == Mips::LD) ||
54      (Opc == Mips::LD_P8) || (Opc == Mips::LWC1)   || (Opc == Mips::LWC1_P8) ||
55      (Opc == Mips::LDC1)  || (Opc == Mips::LDC164) ||
56      (Opc == Mips::LDC164_P8)) {
57    if ((MI->getOperand(1).isFI()) && // is a stack slot
58        (MI->getOperand(2).isImm()) &&  // the imm is zero
59        (isZeroImm(MI->getOperand(2)))) {
60      FrameIndex = MI->getOperand(1).getIndex();
61      return MI->getOperand(0).getReg();
62    }
63  }
64
65  return 0;
66}
67
68/// isStoreToStackSlot - If the specified machine instruction is a direct
69/// store to a stack slot, return the virtual or physical register number of
70/// the source reg along with the FrameIndex of the loaded stack slot.  If
71/// not, return 0.  This predicate must return 0 if the instruction has
72/// any side effects other than storing to the stack slot.
73unsigned MipsInstrInfo::
74isStoreToStackSlot(const MachineInstr *MI, int &FrameIndex) const
75{
76  unsigned Opc = MI->getOpcode();
77
78  if ((Opc == Mips::SW)    || (Opc == Mips::SW_P8)  || (Opc == Mips::SD) ||
79      (Opc == Mips::SD_P8) || (Opc == Mips::SWC1)   || (Opc == Mips::SWC1_P8) ||
80      (Opc == Mips::SDC1)  || (Opc == Mips::SDC164) ||
81      (Opc == Mips::SDC164_P8)) {
82    if ((MI->getOperand(1).isFI()) && // is a stack slot
83        (MI->getOperand(2).isImm()) &&  // the imm is zero
84        (isZeroImm(MI->getOperand(2)))) {
85      FrameIndex = MI->getOperand(1).getIndex();
86      return MI->getOperand(0).getReg();
87    }
88  }
89  return 0;
90}
91
92/// insertNoop - If data hazard condition is found insert the target nop
93/// instruction.
94void MipsInstrInfo::
95insertNoop(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI) const
96{
97  DebugLoc DL;
98  BuildMI(MBB, MI, DL, get(Mips::NOP));
99}
100
101void MipsInstrInfo::
102copyPhysReg(MachineBasicBlock &MBB,
103            MachineBasicBlock::iterator I, DebugLoc DL,
104            unsigned DestReg, unsigned SrcReg,
105            bool KillSrc) const {
106  unsigned Opc = 0, ZeroReg = 0;
107
108  if (Mips::CPURegsRegClass.contains(DestReg)) { // Copy to CPU Reg.
109    if (Mips::CPURegsRegClass.contains(SrcReg))
110      Opc = Mips::ADDu, ZeroReg = Mips::ZERO;
111    else if (Mips::CCRRegClass.contains(SrcReg))
112      Opc = Mips::CFC1;
113    else if (Mips::FGR32RegClass.contains(SrcReg))
114      Opc = Mips::MFC1;
115    else if (SrcReg == Mips::HI)
116      Opc = Mips::MFHI, SrcReg = 0;
117    else if (SrcReg == Mips::LO)
118      Opc = Mips::MFLO, SrcReg = 0;
119  }
120  else if (Mips::CPURegsRegClass.contains(SrcReg)) { // Copy from CPU Reg.
121    if (Mips::CCRRegClass.contains(DestReg))
122      Opc = Mips::CTC1;
123    else if (Mips::FGR32RegClass.contains(DestReg))
124      Opc = Mips::MTC1;
125    else if (DestReg == Mips::HI)
126      Opc = Mips::MTHI, DestReg = 0;
127    else if (DestReg == Mips::LO)
128      Opc = Mips::MTLO, DestReg = 0;
129  }
130  else if (Mips::FGR32RegClass.contains(DestReg, SrcReg))
131    Opc = Mips::FMOV_S;
132  else if (Mips::AFGR64RegClass.contains(DestReg, SrcReg))
133    Opc = Mips::FMOV_D32;
134  else if (Mips::CCRRegClass.contains(DestReg, SrcReg))
135    Opc = Mips::MOVCCRToCCR;
136  else if (Mips::CPU64RegsRegClass.contains(DestReg)) { // Copy to CPU64 Reg.
137    if (Mips::CPU64RegsRegClass.contains(SrcReg))
138      Opc = Mips::DADDu, ZeroReg = Mips::ZERO_64;
139    else if (SrcReg == Mips::HI64)
140      Opc = Mips::MFHI64, SrcReg = 0;
141    else if (SrcReg == Mips::LO64)
142      Opc = Mips::MFLO64, SrcReg = 0;
143  }
144  else if (Mips::CPU64RegsRegClass.contains(SrcReg)) { // Copy from CPU64 Reg.
145    if (DestReg == Mips::HI64)
146      Opc = Mips::MTHI64, DestReg = 0;
147    else if (DestReg == Mips::LO64)
148      Opc = Mips::MTLO64, DestReg = 0;
149  }
150
151  assert(Opc && "Cannot copy registers");
152
153  MachineInstrBuilder MIB = BuildMI(MBB, I, DL, get(Opc));
154
155  if (DestReg)
156    MIB.addReg(DestReg, RegState::Define);
157
158  if (ZeroReg)
159    MIB.addReg(ZeroReg);
160
161  if (SrcReg)
162    MIB.addReg(SrcReg, getKillRegState(KillSrc));
163}
164
165void MipsInstrInfo::
166storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
167                    unsigned SrcReg, bool isKill, int FI,
168                    const TargetRegisterClass *RC,
169                    const TargetRegisterInfo *TRI) const {
170  DebugLoc DL;
171  if (I != MBB.end()) DL = I->getDebugLoc();
172  unsigned Opc = 0;
173
174  if (RC == Mips::CPURegsRegisterClass)
175    Opc = IsN64 ? Mips::SW_P8 : Mips::SW;
176  else if (RC == Mips::CPU64RegsRegisterClass)
177    Opc = IsN64 ? Mips::SD_P8 : Mips::SD;
178  else if (RC == Mips::FGR32RegisterClass)
179    Opc = IsN64 ? Mips::SWC1_P8 : Mips::SWC1;
180  else if (RC == Mips::AFGR64RegisterClass)
181    Opc = Mips::SDC1;
182  else if (RC == Mips::FGR64RegisterClass)
183    Opc = IsN64 ? Mips::SDC164_P8 : Mips::SDC164;
184
185  assert(Opc && "Register class not handled!");
186  BuildMI(MBB, I, DL, get(Opc)).addReg(SrcReg, getKillRegState(isKill))
187    .addFrameIndex(FI).addImm(0);
188}
189
190void MipsInstrInfo::
191loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
192                     unsigned DestReg, int FI,
193                     const TargetRegisterClass *RC,
194                     const TargetRegisterInfo *TRI) const
195{
196  DebugLoc DL;
197  if (I != MBB.end()) DL = I->getDebugLoc();
198  unsigned Opc = 0;
199
200  if (RC == Mips::CPURegsRegisterClass)
201    Opc = IsN64 ? Mips::LW_P8 : Mips::LW;
202  else if (RC == Mips::CPU64RegsRegisterClass)
203    Opc = IsN64 ? Mips::LD_P8 : Mips::LD;
204  else if (RC == Mips::FGR32RegisterClass)
205    Opc = IsN64 ? Mips::LWC1_P8 : Mips::LWC1;
206  else if (RC == Mips::AFGR64RegisterClass)
207    Opc = Mips::LDC1;
208  else if (RC == Mips::FGR64RegisterClass)
209    Opc = IsN64 ? Mips::LDC164_P8 : Mips::LDC164;
210
211  assert(Opc && "Register class not handled!");
212  BuildMI(MBB, I, DL, get(Opc), DestReg).addFrameIndex(FI).addImm(0);
213}
214
215MachineInstr*
216MipsInstrInfo::emitFrameIndexDebugValue(MachineFunction &MF, int FrameIx,
217                                        uint64_t Offset, const MDNode *MDPtr,
218                                        DebugLoc DL) const {
219  MachineInstrBuilder MIB = BuildMI(MF, DL, get(Mips::DBG_VALUE))
220    .addFrameIndex(FrameIx).addImm(0).addImm(Offset).addMetadata(MDPtr);
221  return &*MIB;
222}
223
224//===----------------------------------------------------------------------===//
225// Branch Analysis
226//===----------------------------------------------------------------------===//
227
228static unsigned GetAnalyzableBrOpc(unsigned Opc) {
229  return (Opc == Mips::BEQ  || Opc == Mips::BNE  || Opc == Mips::BGTZ ||
230          Opc == Mips::BGEZ || Opc == Mips::BLTZ || Opc == Mips::BLEZ ||
231          Opc == Mips::BC1T || Opc == Mips::BC1F || Opc == Mips::J) ? Opc : 0;
232}
233
234/// GetOppositeBranchOpc - Return the inverse of the specified
235/// opcode, e.g. turning BEQ to BNE.
236unsigned Mips::GetOppositeBranchOpc(unsigned Opc)
237{
238  switch (Opc) {
239  default: llvm_unreachable("Illegal opcode!");
240  case Mips::BEQ  : return Mips::BNE;
241  case Mips::BNE  : return Mips::BEQ;
242  case Mips::BGTZ : return Mips::BLEZ;
243  case Mips::BGEZ : return Mips::BLTZ;
244  case Mips::BLTZ : return Mips::BGEZ;
245  case Mips::BLEZ : return Mips::BGTZ;
246  case Mips::BC1T : return Mips::BC1F;
247  case Mips::BC1F : return Mips::BC1T;
248  }
249}
250
251static void AnalyzeCondBr(const MachineInstr* Inst, unsigned Opc,
252                          MachineBasicBlock *&BB,
253                          SmallVectorImpl<MachineOperand>& Cond) {
254  assert(GetAnalyzableBrOpc(Opc) && "Not an analyzable branch");
255  int NumOp = Inst->getNumExplicitOperands();
256
257  // for both int and fp branches, the last explicit operand is the
258  // MBB.
259  BB = Inst->getOperand(NumOp-1).getMBB();
260  Cond.push_back(MachineOperand::CreateImm(Opc));
261
262  for (int i=0; i<NumOp-1; i++)
263    Cond.push_back(Inst->getOperand(i));
264}
265
266bool MipsInstrInfo::AnalyzeBranch(MachineBasicBlock &MBB,
267                                  MachineBasicBlock *&TBB,
268                                  MachineBasicBlock *&FBB,
269                                  SmallVectorImpl<MachineOperand> &Cond,
270                                  bool AllowModify) const
271{
272  MachineBasicBlock::reverse_iterator I = MBB.rbegin(), REnd = MBB.rend();
273
274  // Skip all the debug instructions.
275  while (I != REnd && I->isDebugValue())
276    ++I;
277
278  if (I == REnd || !isUnpredicatedTerminator(&*I)) {
279    // If this block ends with no branches (it just falls through to its succ)
280    // just return false, leaving TBB/FBB null.
281    TBB = FBB = NULL;
282    return false;
283  }
284
285  MachineInstr *LastInst = &*I;
286  unsigned LastOpc = LastInst->getOpcode();
287
288  // Not an analyzable branch (must be an indirect jump).
289  if (!GetAnalyzableBrOpc(LastOpc))
290    return true;
291
292  // Get the second to last instruction in the block.
293  unsigned SecondLastOpc = 0;
294  MachineInstr *SecondLastInst = NULL;
295
296  if (++I != REnd) {
297    SecondLastInst = &*I;
298    SecondLastOpc = GetAnalyzableBrOpc(SecondLastInst->getOpcode());
299
300    // Not an analyzable branch (must be an indirect jump).
301    if (isUnpredicatedTerminator(SecondLastInst) && !SecondLastOpc)
302      return true;
303  }
304
305  // If there is only one terminator instruction, process it.
306  if (!SecondLastOpc) {
307    // Unconditional branch
308    if (LastOpc == Mips::J) {
309      TBB = LastInst->getOperand(0).getMBB();
310      return false;
311    }
312
313    // Conditional branch
314    AnalyzeCondBr(LastInst, LastOpc, TBB, Cond);
315    return false;
316  }
317
318  // If we reached here, there are two branches.
319  // If there are three terminators, we don't know what sort of block this is.
320  if (++I != REnd && isUnpredicatedTerminator(&*I))
321    return true;
322
323  // If second to last instruction is an unconditional branch,
324  // analyze it and remove the last instruction.
325  if (SecondLastOpc == Mips::J) {
326    // Return if the last instruction cannot be removed.
327    if (!AllowModify)
328      return true;
329
330    TBB = SecondLastInst->getOperand(0).getMBB();
331    LastInst->eraseFromParent();
332    return false;
333  }
334
335  // Conditional branch followed by an unconditional branch.
336  // The last one must be unconditional.
337  if (LastOpc != Mips::J)
338    return true;
339
340  AnalyzeCondBr(SecondLastInst, SecondLastOpc, TBB, Cond);
341  FBB = LastInst->getOperand(0).getMBB();
342
343  return false;
344}
345
346void MipsInstrInfo::BuildCondBr(MachineBasicBlock &MBB,
347                                MachineBasicBlock *TBB, DebugLoc DL,
348                                const SmallVectorImpl<MachineOperand>& Cond)
349  const {
350  unsigned Opc = Cond[0].getImm();
351  const MCInstrDesc &MCID = get(Opc);
352  MachineInstrBuilder MIB = BuildMI(&MBB, DL, MCID);
353
354  for (unsigned i = 1; i < Cond.size(); ++i)
355    MIB.addReg(Cond[i].getReg());
356
357  MIB.addMBB(TBB);
358}
359
360unsigned MipsInstrInfo::
361InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB,
362             MachineBasicBlock *FBB,
363             const SmallVectorImpl<MachineOperand> &Cond,
364             DebugLoc DL) const {
365  // Shouldn't be a fall through.
366  assert(TBB && "InsertBranch must not be told to insert a fallthrough");
367
368  // # of condition operands:
369  //  Unconditional branches: 0
370  //  Floating point branches: 1 (opc)
371  //  Int BranchZero: 2 (opc, reg)
372  //  Int Branch: 3 (opc, reg0, reg1)
373  assert((Cond.size() <= 3) &&
374         "# of Mips branch conditions must be <= 3!");
375
376  // Two-way Conditional branch.
377  if (FBB) {
378    BuildCondBr(MBB, TBB, DL, Cond);
379    BuildMI(&MBB, DL, get(Mips::J)).addMBB(FBB);
380    return 2;
381  }
382
383  // One way branch.
384  // Unconditional branch.
385  if (Cond.empty())
386    BuildMI(&MBB, DL, get(Mips::J)).addMBB(TBB);
387  else // Conditional branch.
388    BuildCondBr(MBB, TBB, DL, Cond);
389  return 1;
390}
391
392unsigned MipsInstrInfo::
393RemoveBranch(MachineBasicBlock &MBB) const
394{
395  MachineBasicBlock::reverse_iterator I = MBB.rbegin(), REnd = MBB.rend();
396  MachineBasicBlock::reverse_iterator FirstBr;
397  unsigned removed;
398
399  // Skip all the debug instructions.
400  while (I != REnd && I->isDebugValue())
401    ++I;
402
403  FirstBr = I;
404
405  // Up to 2 branches are removed.
406  // Note that indirect branches are not removed.
407  for(removed = 0; I != REnd && removed < 2; ++I, ++removed)
408    if (!GetAnalyzableBrOpc(I->getOpcode()))
409      break;
410
411  MBB.erase(I.base(), FirstBr.base());
412
413  return removed;
414}
415
416/// ReverseBranchCondition - Return the inverse opcode of the
417/// specified Branch instruction.
418bool MipsInstrInfo::
419ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const
420{
421  assert( (Cond.size() && Cond.size() <= 3) &&
422          "Invalid Mips branch condition!");
423  Cond[0].setImm(Mips::GetOppositeBranchOpc(Cond[0].getImm()));
424  return false;
425}
426
427/// getGlobalBaseReg - Return a virtual register initialized with the
428/// the global base register value. Output instructions required to
429/// initialize the register in the function entry block, if necessary.
430///
431unsigned MipsInstrInfo::getGlobalBaseReg(MachineFunction *MF) const {
432  MipsFunctionInfo *MipsFI = MF->getInfo<MipsFunctionInfo>();
433  unsigned GlobalBaseReg = MipsFI->getGlobalBaseReg();
434  if (GlobalBaseReg != 0)
435    return GlobalBaseReg;
436
437  // Insert the set of GlobalBaseReg into the first MBB of the function
438  MachineBasicBlock &FirstMBB = MF->front();
439  MachineBasicBlock::iterator MBBI = FirstMBB.begin();
440  MachineRegisterInfo &RegInfo = MF->getRegInfo();
441  const TargetInstrInfo *TII = MF->getTarget().getInstrInfo();
442
443  GlobalBaseReg = RegInfo.createVirtualRegister(Mips::CPURegsRegisterClass);
444  BuildMI(FirstMBB, MBBI, DebugLoc(), TII->get(TargetOpcode::COPY),
445          GlobalBaseReg).addReg(Mips::GP);
446  RegInfo.addLiveIn(Mips::GP);
447
448  MipsFI->setGlobalBaseReg(GlobalBaseReg);
449  return GlobalBaseReg;
450}
451