LLVM API Documentation

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
SparcInstrInfo.cpp
Go to the documentation of this file.
1 //===-- SparcInstrInfo.cpp - Sparc Instruction Information ----------------===//
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 Sparc implementation of the TargetInstrInfo class.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #include "SparcInstrInfo.h"
15 #include "Sparc.h"
17 #include "SparcSubtarget.h"
18 #include "llvm/ADT/STLExtras.h"
19 #include "llvm/ADT/SmallVector.h"
26 
27 #define GET_INSTRINFO_CTOR_DTOR
28 #include "SparcGenInstrInfo.inc"
29 
30 using namespace llvm;
31 
32 
33 // Pin the vtable to this file.
34 void SparcInstrInfo::anchor() {}
35 
37  : SparcGenInstrInfo(SP::ADJCALLSTACKDOWN, SP::ADJCALLSTACKUP),
38  RI(ST), Subtarget(ST) {
39 }
40 
41 /// isLoadFromStackSlot - If the specified machine instruction is a direct
42 /// load from a stack slot, return the virtual or physical register number of
43 /// the destination along with the FrameIndex of the loaded stack slot. If
44 /// not, return 0. This predicate must return 0 if the instruction has
45 /// any side effects other than loading from the stack slot.
47  int &FrameIndex) const {
48  if (MI->getOpcode() == SP::LDri ||
49  MI->getOpcode() == SP::LDXri ||
50  MI->getOpcode() == SP::LDFri ||
51  MI->getOpcode() == SP::LDDFri ||
52  MI->getOpcode() == SP::LDQFri) {
53  if (MI->getOperand(1).isFI() && MI->getOperand(2).isImm() &&
54  MI->getOperand(2).getImm() == 0) {
55  FrameIndex = MI->getOperand(1).getIndex();
56  return MI->getOperand(0).getReg();
57  }
58  }
59  return 0;
60 }
61 
62 /// isStoreToStackSlot - If the specified machine instruction is a direct
63 /// store to a stack slot, return the virtual or physical register number of
64 /// the source reg along with the FrameIndex of the loaded stack slot. If
65 /// not, return 0. This predicate must return 0 if the instruction has
66 /// any side effects other than storing to the stack slot.
68  int &FrameIndex) const {
69  if (MI->getOpcode() == SP::STri ||
70  MI->getOpcode() == SP::STXri ||
71  MI->getOpcode() == SP::STFri ||
72  MI->getOpcode() == SP::STDFri ||
73  MI->getOpcode() == SP::STQFri) {
74  if (MI->getOperand(0).isFI() && MI->getOperand(1).isImm() &&
75  MI->getOperand(1).getImm() == 0) {
76  FrameIndex = MI->getOperand(0).getIndex();
77  return MI->getOperand(2).getReg();
78  }
79  }
80  return 0;
81 }
82 
83 static bool IsIntegerCC(unsigned CC)
84 {
85  return (CC <= SPCC::ICC_VC);
86 }
87 
88 
90 {
91  switch(CC) {
92  case SPCC::ICC_NE: return SPCC::ICC_E;
93  case SPCC::ICC_E: return SPCC::ICC_NE;
94  case SPCC::ICC_G: return SPCC::ICC_LE;
95  case SPCC::ICC_LE: return SPCC::ICC_G;
96  case SPCC::ICC_GE: return SPCC::ICC_L;
97  case SPCC::ICC_L: return SPCC::ICC_GE;
98  case SPCC::ICC_GU: return SPCC::ICC_LEU;
99  case SPCC::ICC_LEU: return SPCC::ICC_GU;
100  case SPCC::ICC_CC: return SPCC::ICC_CS;
101  case SPCC::ICC_CS: return SPCC::ICC_CC;
102  case SPCC::ICC_POS: return SPCC::ICC_NEG;
103  case SPCC::ICC_NEG: return SPCC::ICC_POS;
104  case SPCC::ICC_VC: return SPCC::ICC_VS;
105  case SPCC::ICC_VS: return SPCC::ICC_VC;
106 
107  case SPCC::FCC_U: return SPCC::FCC_O;
108  case SPCC::FCC_O: return SPCC::FCC_U;
109  case SPCC::FCC_G: return SPCC::FCC_ULE;
110  case SPCC::FCC_LE: return SPCC::FCC_UG;
111  case SPCC::FCC_UG: return SPCC::FCC_LE;
112  case SPCC::FCC_ULE: return SPCC::FCC_G;
113  case SPCC::FCC_L: return SPCC::FCC_UGE;
114  case SPCC::FCC_GE: return SPCC::FCC_UL;
115  case SPCC::FCC_UL: return SPCC::FCC_GE;
116  case SPCC::FCC_UGE: return SPCC::FCC_L;
117  case SPCC::FCC_LG: return SPCC::FCC_UE;
118  case SPCC::FCC_UE: return SPCC::FCC_LG;
119  case SPCC::FCC_NE: return SPCC::FCC_E;
120  case SPCC::FCC_E: return SPCC::FCC_NE;
121  }
122  llvm_unreachable("Invalid cond code");
123 }
124 
126  MachineBasicBlock *&TBB,
127  MachineBasicBlock *&FBB,
129  bool AllowModify) const
130 {
131 
133  MachineBasicBlock::iterator UnCondBrIter = MBB.end();
134  while (I != MBB.begin()) {
135  --I;
136 
137  if (I->isDebugValue())
138  continue;
139 
140  // When we see a non-terminator, we are done.
141  if (!isUnpredicatedTerminator(I))
142  break;
143 
144  // Terminator is not a branch.
145  if (!I->isBranch())
146  return true;
147 
148  // Handle Unconditional branches.
149  if (I->getOpcode() == SP::BA) {
150  UnCondBrIter = I;
151 
152  if (!AllowModify) {
153  TBB = I->getOperand(0).getMBB();
154  continue;
155  }
156 
157  while (llvm::next(I) != MBB.end())
158  llvm::next(I)->eraseFromParent();
159 
160  Cond.clear();
161  FBB = 0;
162 
163  if (MBB.isLayoutSuccessor(I->getOperand(0).getMBB())) {
164  TBB = 0;
165  I->eraseFromParent();
166  I = MBB.end();
167  UnCondBrIter = MBB.end();
168  continue;
169  }
170 
171  TBB = I->getOperand(0).getMBB();
172  continue;
173  }
174 
175  unsigned Opcode = I->getOpcode();
176  if (Opcode != SP::BCOND && Opcode != SP::FBCOND)
177  return true; // Unknown Opcode.
178 
179  SPCC::CondCodes BranchCode = (SPCC::CondCodes)I->getOperand(1).getImm();
180 
181  if (Cond.empty()) {
182  MachineBasicBlock *TargetBB = I->getOperand(0).getMBB();
183  if (AllowModify && UnCondBrIter != MBB.end() &&
184  MBB.isLayoutSuccessor(TargetBB)) {
185 
186  // Transform the code
187  //
188  // brCC L1
189  // ba L2
190  // L1:
191  // ..
192  // L2:
193  //
194  // into
195  //
196  // brnCC L2
197  // L1:
198  // ...
199  // L2:
200  //
201  BranchCode = GetOppositeBranchCondition(BranchCode);
202  MachineBasicBlock::iterator OldInst = I;
203  BuildMI(MBB, UnCondBrIter, MBB.findDebugLoc(I), get(Opcode))
204  .addMBB(UnCondBrIter->getOperand(0).getMBB()).addImm(BranchCode);
205  BuildMI(MBB, UnCondBrIter, MBB.findDebugLoc(I), get(SP::BA))
206  .addMBB(TargetBB);
207 
208  OldInst->eraseFromParent();
209  UnCondBrIter->eraseFromParent();
210 
211  UnCondBrIter = MBB.end();
212  I = MBB.end();
213  continue;
214  }
215  FBB = TBB;
216  TBB = I->getOperand(0).getMBB();
217  Cond.push_back(MachineOperand::CreateImm(BranchCode));
218  continue;
219  }
220  // FIXME: Handle subsequent conditional branches.
221  // For now, we can't handle multiple conditional branches.
222  return true;
223  }
224  return false;
225 }
226 
227 unsigned
229  MachineBasicBlock *FBB,
231  DebugLoc DL) const {
232  assert(TBB && "InsertBranch must not be told to insert a fallthrough");
233  assert((Cond.size() == 1 || Cond.size() == 0) &&
234  "Sparc branch conditions should have one component!");
235 
236  if (Cond.empty()) {
237  assert(!FBB && "Unconditional branch with multiple successors!");
238  BuildMI(&MBB, DL, get(SP::BA)).addMBB(TBB);
239  return 1;
240  }
241 
242  // Conditional branch
243  unsigned CC = Cond[0].getImm();
244 
245  if (IsIntegerCC(CC))
246  BuildMI(&MBB, DL, get(SP::BCOND)).addMBB(TBB).addImm(CC);
247  else
248  BuildMI(&MBB, DL, get(SP::FBCOND)).addMBB(TBB).addImm(CC);
249  if (!FBB)
250  return 1;
251 
252  BuildMI(&MBB, DL, get(SP::BA)).addMBB(FBB);
253  return 2;
254 }
255 
257 {
259  unsigned Count = 0;
260  while (I != MBB.begin()) {
261  --I;
262 
263  if (I->isDebugValue())
264  continue;
265 
266  if (I->getOpcode() != SP::BA
267  && I->getOpcode() != SP::BCOND
268  && I->getOpcode() != SP::FBCOND)
269  break; // Not a branch
270 
271  I->eraseFromParent();
272  I = MBB.end();
273  ++Count;
274  }
275  return Count;
276 }
277 
280  unsigned DestReg, unsigned SrcReg,
281  bool KillSrc) const {
282  unsigned numSubRegs = 0;
283  unsigned movOpc = 0;
284  const unsigned *subRegIdx = 0;
285 
286  const unsigned DFP_FP_SubRegsIdx[] = { SP::sub_even, SP::sub_odd };
287  const unsigned QFP_DFP_SubRegsIdx[] = { SP::sub_even64, SP::sub_odd64 };
288  const unsigned QFP_FP_SubRegsIdx[] = { SP::sub_even, SP::sub_odd,
289  SP::sub_odd64_then_sub_even,
290  SP::sub_odd64_then_sub_odd };
291 
292  if (SP::IntRegsRegClass.contains(DestReg, SrcReg))
293  BuildMI(MBB, I, DL, get(SP::ORrr), DestReg).addReg(SP::G0)
294  .addReg(SrcReg, getKillRegState(KillSrc));
295  else if (SP::FPRegsRegClass.contains(DestReg, SrcReg))
296  BuildMI(MBB, I, DL, get(SP::FMOVS), DestReg)
297  .addReg(SrcReg, getKillRegState(KillSrc));
298  else if (SP::DFPRegsRegClass.contains(DestReg, SrcReg)) {
299  if (Subtarget.isV9()) {
300  BuildMI(MBB, I, DL, get(SP::FMOVD), DestReg)
301  .addReg(SrcReg, getKillRegState(KillSrc));
302  } else {
303  // Use two FMOVS instructions.
304  subRegIdx = DFP_FP_SubRegsIdx;
305  numSubRegs = 2;
306  movOpc = SP::FMOVS;
307  }
308  } else if (SP::QFPRegsRegClass.contains(DestReg, SrcReg)) {
309  if (Subtarget.isV9()) {
310  if (Subtarget.hasHardQuad()) {
311  BuildMI(MBB, I, DL, get(SP::FMOVQ), DestReg)
312  .addReg(SrcReg, getKillRegState(KillSrc));
313  } else {
314  // Use two FMOVD instructions.
315  subRegIdx = QFP_DFP_SubRegsIdx;
316  numSubRegs = 2;
317  movOpc = SP::FMOVD;
318  }
319  } else {
320  // Use four FMOVS instructions.
321  subRegIdx = QFP_FP_SubRegsIdx;
322  numSubRegs = 4;
323  movOpc = SP::FMOVS;
324  }
325  } else
326  llvm_unreachable("Impossible reg-to-reg copy");
327 
328  if (numSubRegs == 0 || subRegIdx == 0 || movOpc == 0)
329  return;
330 
331  const TargetRegisterInfo *TRI = &getRegisterInfo();
332  MachineInstr *MovMI = 0;
333 
334  for (unsigned i = 0; i != numSubRegs; ++i) {
335  unsigned Dst = TRI->getSubReg(DestReg, subRegIdx[i]);
336  unsigned Src = TRI->getSubReg(SrcReg, subRegIdx[i]);
337  assert(Dst && Src && "Bad sub-register");
338 
339  MovMI = BuildMI(MBB, I, DL, get(movOpc), Dst).addReg(Src);
340  }
341  // Add implicit super-register defs and kills to the last MovMI.
342  MovMI->addRegisterDefined(DestReg, TRI);
343  if (KillSrc)
344  MovMI->addRegisterKilled(SrcReg, TRI);
345 }
346 
347 void SparcInstrInfo::
349  unsigned SrcReg, bool isKill, int FI,
350  const TargetRegisterClass *RC,
351  const TargetRegisterInfo *TRI) const {
352  DebugLoc DL;
353  if (I != MBB.end()) DL = I->getDebugLoc();
354 
355  MachineFunction *MF = MBB.getParent();
356  const MachineFrameInfo &MFI = *MF->getFrameInfo();
357  MachineMemOperand *MMO =
360  MFI.getObjectSize(FI),
361  MFI.getObjectAlignment(FI));
362 
363  // On the order of operands here: think "[FrameIdx + 0] = SrcReg".
364  if (RC == &SP::I64RegsRegClass)
365  BuildMI(MBB, I, DL, get(SP::STXri)).addFrameIndex(FI).addImm(0)
366  .addReg(SrcReg, getKillRegState(isKill)).addMemOperand(MMO);
367  else if (RC == &SP::IntRegsRegClass)
368  BuildMI(MBB, I, DL, get(SP::STri)).addFrameIndex(FI).addImm(0)
369  .addReg(SrcReg, getKillRegState(isKill)).addMemOperand(MMO);
370  else if (RC == &SP::FPRegsRegClass)
371  BuildMI(MBB, I, DL, get(SP::STFri)).addFrameIndex(FI).addImm(0)
372  .addReg(SrcReg, getKillRegState(isKill)).addMemOperand(MMO);
373  else if (SP::DFPRegsRegClass.hasSubClassEq(RC))
374  BuildMI(MBB, I, DL, get(SP::STDFri)).addFrameIndex(FI).addImm(0)
375  .addReg(SrcReg, getKillRegState(isKill)).addMemOperand(MMO);
376  else if (SP::QFPRegsRegClass.hasSubClassEq(RC))
377  // Use STQFri irrespective of its legality. If STQ is not legal, it will be
378  // lowered into two STDs in eliminateFrameIndex.
379  BuildMI(MBB, I, DL, get(SP::STQFri)).addFrameIndex(FI).addImm(0)
380  .addReg(SrcReg, getKillRegState(isKill)).addMemOperand(MMO);
381  else
382  llvm_unreachable("Can't store this register to stack slot");
383 }
384 
385 void SparcInstrInfo::
387  unsigned DestReg, int FI,
388  const TargetRegisterClass *RC,
389  const TargetRegisterInfo *TRI) const {
390  DebugLoc DL;
391  if (I != MBB.end()) DL = I->getDebugLoc();
392 
393  MachineFunction *MF = MBB.getParent();
394  const MachineFrameInfo &MFI = *MF->getFrameInfo();
395  MachineMemOperand *MMO =
398  MFI.getObjectSize(FI),
399  MFI.getObjectAlignment(FI));
400 
401  if (RC == &SP::I64RegsRegClass)
402  BuildMI(MBB, I, DL, get(SP::LDXri), DestReg).addFrameIndex(FI).addImm(0)
403  .addMemOperand(MMO);
404  else if (RC == &SP::IntRegsRegClass)
405  BuildMI(MBB, I, DL, get(SP::LDri), DestReg).addFrameIndex(FI).addImm(0)
406  .addMemOperand(MMO);
407  else if (RC == &SP::FPRegsRegClass)
408  BuildMI(MBB, I, DL, get(SP::LDFri), DestReg).addFrameIndex(FI).addImm(0)
409  .addMemOperand(MMO);
410  else if (SP::DFPRegsRegClass.hasSubClassEq(RC))
411  BuildMI(MBB, I, DL, get(SP::LDDFri), DestReg).addFrameIndex(FI).addImm(0)
412  .addMemOperand(MMO);
413  else if (SP::QFPRegsRegClass.hasSubClassEq(RC))
414  // Use LDQFri irrespective of its legality. If LDQ is not legal, it will be
415  // lowered into two LDDs in eliminateFrameIndex.
416  BuildMI(MBB, I, DL, get(SP::LDQFri), DestReg).addFrameIndex(FI).addImm(0)
417  .addMemOperand(MMO);
418  else
419  llvm_unreachable("Can't load this register from stack slot");
420 }
421 
423 {
425  unsigned GlobalBaseReg = SparcFI->getGlobalBaseReg();
426  if (GlobalBaseReg != 0)
427  return GlobalBaseReg;
428 
429  // Insert the set of GlobalBaseReg into the first MBB of the function
430  MachineBasicBlock &FirstMBB = MF->front();
431  MachineBasicBlock::iterator MBBI = FirstMBB.begin();
432  MachineRegisterInfo &RegInfo = MF->getRegInfo();
433 
434  GlobalBaseReg = RegInfo.createVirtualRegister(&SP::IntRegsRegClass);
435 
436 
437  DebugLoc dl;
438 
439  BuildMI(FirstMBB, MBBI, dl, get(SP::GETPCX), GlobalBaseReg);
440  SparcFI->setGlobalBaseReg(GlobalBaseReg);
441  return GlobalBaseReg;
442 }
The memory access reads data.
const MachineFunction * getParent() const
The memory access writes data.
unsigned getGlobalBaseReg(MachineFunction *MF) const
virtual void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, DebugLoc DL, unsigned DestReg, unsigned SrcReg, bool KillSrc) const
unsigned createVirtualRegister(const TargetRegisterClass *RegClass)
virtual void loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, unsigned DestReg, int FrameIndex, const TargetRegisterClass *RC, const TargetRegisterInfo *TRI) const
MachineMemOperand * getMachineMemOperand(MachinePointerInfo PtrInfo, unsigned f, uint64_t s, unsigned base_alignment, const MDNode *TBAAInfo=0, const MDNode *Ranges=0)
virtual const SparcRegisterInfo & getRegisterInfo() const
virtual unsigned RemoveBranch(MachineBasicBlock &MBB) const
static MachinePointerInfo getFixedStack(int FI, int64_t offset=0)
virtual bool AnalyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, MachineBasicBlock *&FBB, SmallVectorImpl< MachineOperand > &Cond, bool AllowModify=false) const
bool isImm() const
isImm - Tests if this is a MO_Immediate operand.
#define llvm_unreachable(msg)
Abstract Stack Frame Information.
const MachineInstrBuilder & addImm(int64_t Val) const
static bool IsIntegerCC(unsigned CC)
const MachineBasicBlock & front() const
bool isFI() const
isFI - Tests if this is a MO_FrameIndex operand.
bool LLVM_ATTRIBUTE_UNUSED_RESULT empty() const
Definition: SmallVector.h:56
int getOpcode() const
Definition: MachineInstr.h:261
virtual void storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, unsigned SrcReg, bool isKill, int FrameIndex, const TargetRegisterClass *RC, const TargetRegisterInfo *TRI) const
int64_t getImm() const
unsigned getKillRegState(bool B)
bundle_iterator< MachineInstr, instr_iterator > iterator
const MachineOperand & getOperand(unsigned i) const
Definition: MachineInstr.h:267
unsigned getSubReg(unsigned Reg, unsigned Idx) const
Returns the physical register number of sub-register "Index" for physical register RegNo...
virtual unsigned isStoreToStackSlot(const MachineInstr *MI, int &FrameIndex) const
ItTy next(ItTy it, Dist n)
Definition: STLExtras.h:154
virtual unsigned isLoadFromStackSlot(const MachineInstr *MI, int &FrameIndex) const
MachineInstrBuilder BuildMI(MachineFunction &MF, DebugLoc DL, const MCInstrDesc &MCID)
DebugLoc findDebugLoc(instr_iterator MBBI)
bool hasHardQuad() const
unsigned getObjectAlignment(int ObjectIdx) const
getObjectAlignment - Return the alignment of the specified stack object.
MachineFrameInfo * getFrameInfo()
const MachineInstrBuilder & addFrameIndex(int Idx) const
static SPCC::CondCodes GetOppositeBranchCondition(SPCC::CondCodes CC)
CondCodes
Definition: Sparc.h:38
MachineRegisterInfo & getRegInfo()
SparcInstrInfo(SparcSubtarget &ST)
const MachineInstrBuilder & addMemOperand(MachineMemOperand *MMO) const
static MachineOperand CreateImm(int64_t Val)
#define I(x, y, z)
Definition: MD5.cpp:54
unsigned getReg() const
getReg - Returns the register number.
const MachineInstrBuilder & addMBB(MachineBasicBlock *MBB, unsigned char TargetFlags=0) const
bool isV9() const
virtual unsigned InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, MachineBasicBlock *FBB, const SmallVectorImpl< MachineOperand > &Cond, DebugLoc DL) const
void addRegisterDefined(unsigned Reg, const TargetRegisterInfo *RegInfo=0)
bool addRegisterKilled(unsigned IncomingReg, const TargetRegisterInfo *RegInfo, bool AddIfNotFound=false)
bool isLayoutSuccessor(const MachineBasicBlock *MBB) const
const MachineInstrBuilder & addReg(unsigned RegNo, unsigned flags=0, unsigned SubReg=0) const
int64_t getObjectSize(int ObjectIdx) const