LLVM  10.0.0svn
NVPTXInstrInfo.cpp
Go to the documentation of this file.
1 //===- NVPTXInstrInfo.cpp - NVPTX Instruction Information -----------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file contains the NVPTX implementation of the TargetInstrInfo class.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "NVPTXInstrInfo.h"
14 #include "NVPTX.h"
15 #include "NVPTXTargetMachine.h"
16 #include "llvm/ADT/STLExtras.h"
20 #include "llvm/IR/Function.h"
21 
22 using namespace llvm;
23 
24 #define GET_INSTRINFO_CTOR_DTOR
25 #include "NVPTXGenInstrInfo.inc"
26 
27 // Pin the vtable to this file.
28 void NVPTXInstrInfo::anchor() {}
29 
31 
34  const DebugLoc &DL, unsigned DestReg,
35  unsigned SrcReg, bool KillSrc) const {
36  const MachineRegisterInfo &MRI = MBB.getParent()->getRegInfo();
37  const TargetRegisterClass *DestRC = MRI.getRegClass(DestReg);
38  const TargetRegisterClass *SrcRC = MRI.getRegClass(SrcReg);
39 
40  if (RegInfo.getRegSizeInBits(*DestRC) != RegInfo.getRegSizeInBits(*SrcRC))
41  report_fatal_error("Copy one register into another with a different width");
42 
43  unsigned Op;
44  if (DestRC == &NVPTX::Int1RegsRegClass) {
45  Op = NVPTX::IMOV1rr;
46  } else if (DestRC == &NVPTX::Int16RegsRegClass) {
47  Op = NVPTX::IMOV16rr;
48  } else if (DestRC == &NVPTX::Int32RegsRegClass) {
49  Op = (SrcRC == &NVPTX::Int32RegsRegClass ? NVPTX::IMOV32rr
50  : NVPTX::BITCONVERT_32_F2I);
51  } else if (DestRC == &NVPTX::Int64RegsRegClass) {
52  Op = (SrcRC == &NVPTX::Int64RegsRegClass ? NVPTX::IMOV64rr
53  : NVPTX::BITCONVERT_64_F2I);
54  } else if (DestRC == &NVPTX::Float16RegsRegClass) {
55  Op = (SrcRC == &NVPTX::Float16RegsRegClass ? NVPTX::FMOV16rr
56  : NVPTX::BITCONVERT_16_I2F);
57  } else if (DestRC == &NVPTX::Float16x2RegsRegClass) {
58  Op = NVPTX::IMOV32rr;
59  } else if (DestRC == &NVPTX::Float32RegsRegClass) {
60  Op = (SrcRC == &NVPTX::Float32RegsRegClass ? NVPTX::FMOV32rr
61  : NVPTX::BITCONVERT_32_I2F);
62  } else if (DestRC == &NVPTX::Float64RegsRegClass) {
63  Op = (SrcRC == &NVPTX::Float64RegsRegClass ? NVPTX::FMOV64rr
64  : NVPTX::BITCONVERT_64_I2F);
65  } else {
66  llvm_unreachable("Bad register copy");
67  }
68  BuildMI(MBB, I, DL, get(Op), DestReg)
69  .addReg(SrcReg, getKillRegState(KillSrc));
70 }
71 
72 /// AnalyzeBranch - Analyze the branching code at the end of MBB, returning
73 /// true if it cannot be understood (e.g. it's a switch dispatch or isn't
74 /// implemented for a target). Upon success, this returns false and returns
75 /// with the following information in various cases:
76 ///
77 /// 1. If this block ends with no branches (it just falls through to its succ)
78 /// just return false, leaving TBB/FBB null.
79 /// 2. If this block ends with only an unconditional branch, it sets TBB to be
80 /// the destination block.
81 /// 3. If this block ends with an conditional branch and it falls through to
82 /// an successor block, it sets TBB to be the branch destination block and a
83 /// list of operands that evaluate the condition. These
84 /// operands can be passed to other TargetInstrInfo methods to create new
85 /// branches.
86 /// 4. If this block ends with an conditional branch and an unconditional
87 /// block, it returns the 'true' destination in TBB, the 'false' destination
88 /// in FBB, and a list of operands that evaluate the condition. These
89 /// operands can be passed to other TargetInstrInfo methods to create new
90 /// branches.
91 ///
92 /// Note that removeBranch and insertBranch must be implemented to support
93 /// cases where this method returns success.
94 ///
96  MachineBasicBlock *&TBB,
97  MachineBasicBlock *&FBB,
99  bool AllowModify) const {
100  // If the block has no terminators, it just falls into the block after it.
102  if (I == MBB.begin() || !isUnpredicatedTerminator(*--I))
103  return false;
104 
105  // Get the last instruction in the block.
106  MachineInstr &LastInst = *I;
107 
108  // If there is only one terminator instruction, process it.
109  if (I == MBB.begin() || !isUnpredicatedTerminator(*--I)) {
110  if (LastInst.getOpcode() == NVPTX::GOTO) {
111  TBB = LastInst.getOperand(0).getMBB();
112  return false;
113  } else if (LastInst.getOpcode() == NVPTX::CBranch) {
114  // Block ends with fall-through condbranch.
115  TBB = LastInst.getOperand(1).getMBB();
116  Cond.push_back(LastInst.getOperand(0));
117  return false;
118  }
119  // Otherwise, don't know what this is.
120  return true;
121  }
122 
123  // Get the instruction before it if it's a terminator.
124  MachineInstr &SecondLastInst = *I;
125 
126  // If there are three terminators, we don't know what sort of block this is.
127  if (I != MBB.begin() && isUnpredicatedTerminator(*--I))
128  return true;
129 
130  // If the block ends with NVPTX::GOTO and NVPTX:CBranch, handle it.
131  if (SecondLastInst.getOpcode() == NVPTX::CBranch &&
132  LastInst.getOpcode() == NVPTX::GOTO) {
133  TBB = SecondLastInst.getOperand(1).getMBB();
134  Cond.push_back(SecondLastInst.getOperand(0));
135  FBB = LastInst.getOperand(0).getMBB();
136  return false;
137  }
138 
139  // If the block ends with two NVPTX:GOTOs, handle it. The second one is not
140  // executed, so remove it.
141  if (SecondLastInst.getOpcode() == NVPTX::GOTO &&
142  LastInst.getOpcode() == NVPTX::GOTO) {
143  TBB = SecondLastInst.getOperand(0).getMBB();
144  I = LastInst;
145  if (AllowModify)
146  I->eraseFromParent();
147  return false;
148  }
149 
150  // Otherwise, can't handle this.
151  return true;
152 }
153 
155  int *BytesRemoved) const {
156  assert(!BytesRemoved && "code size not handled");
158  if (I == MBB.begin())
159  return 0;
160  --I;
161  if (I->getOpcode() != NVPTX::GOTO && I->getOpcode() != NVPTX::CBranch)
162  return 0;
163 
164  // Remove the branch.
165  I->eraseFromParent();
166 
167  I = MBB.end();
168 
169  if (I == MBB.begin())
170  return 1;
171  --I;
172  if (I->getOpcode() != NVPTX::CBranch)
173  return 1;
174 
175  // Remove the branch.
176  I->eraseFromParent();
177  return 2;
178 }
179 
181  MachineBasicBlock *TBB,
182  MachineBasicBlock *FBB,
184  const DebugLoc &DL,
185  int *BytesAdded) const {
186  assert(!BytesAdded && "code size not handled");
187 
188  // Shouldn't be a fall through.
189  assert(TBB && "insertBranch must not be told to insert a fallthrough");
190  assert((Cond.size() == 1 || Cond.size() == 0) &&
191  "NVPTX branch conditions have two components!");
192 
193  // One-way branch.
194  if (!FBB) {
195  if (Cond.empty()) // Unconditional branch
196  BuildMI(&MBB, DL, get(NVPTX::GOTO)).addMBB(TBB);
197  else // Conditional branch
198  BuildMI(&MBB, DL, get(NVPTX::CBranch)).addReg(Cond[0].getReg())
199  .addMBB(TBB);
200  return 1;
201  }
202 
203  // Two-way Conditional Branch.
204  BuildMI(&MBB, DL, get(NVPTX::CBranch)).addReg(Cond[0].getReg()).addMBB(TBB);
205  BuildMI(&MBB, DL, get(NVPTX::GOTO)).addMBB(FBB);
206  return 2;
207 }
void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, const DebugLoc &DL, unsigned DestReg, unsigned SrcReg, bool KillSrc) const override
MachineBasicBlock * getMBB() const
const TargetRegisterClass * getRegClass(unsigned Reg) const
Return the register class of the specified virtual register.
LLVM_ATTRIBUTE_NORETURN void report_fatal_error(Error Err, bool gen_crash_diag=true)
Report a serious error, calling any installed error handler.
Definition: Error.cpp:139
This class represents lattice values for constants.
Definition: AllocatorList.h:23
A debug info location.
Definition: DebugLoc.h:33
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
Definition: APFloat.h:41
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
Definition: MachineInstr.h:411
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory)...
Definition: APInt.h:32
unsigned getKillRegState(bool B)
MachineInstrBuilder BuildMI(MachineFunction &MF, const DebugLoc &DL, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
unsigned const MachineRegisterInfo * MRI
size_t size() const
size - Get the array size.
Definition: ArrayRef.h:148
bool analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, MachineBasicBlock *&FBB, SmallVectorImpl< MachineOperand > &Cond, bool AllowModify) const override
AnalyzeBranch - Analyze the branching code at the end of MBB, returning true if it cannot be understo...
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
unsigned insertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, MachineBasicBlock *FBB, ArrayRef< MachineOperand > Cond, const DebugLoc &DL, int *BytesAdded=nullptr) const override
static unsigned getReg(const void *D, unsigned RC, unsigned RegNo)
MachineRegisterInfo - Keep track of information for virtual and physical registers, including vreg register classes, use/def chains for registers, etc.
Representation of each machine instruction.
Definition: MachineInstr.h:64
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
#define I(x, y, z)
Definition: MD5.cpp:58
unsigned removeBranch(MachineBasicBlock &MBB, int *BytesRemoved=nullptr) const override
const MachineInstrBuilder & addReg(unsigned RegNo, unsigned flags=0, unsigned SubReg=0) const
Add a new virtual register operand.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
const MachineInstrBuilder & addMBB(MachineBasicBlock *MBB, unsigned char TargetFlags=0) const
const MachineOperand & getOperand(unsigned i) const
Definition: MachineInstr.h:416
bool empty() const
empty - Check if the array is empty.
Definition: ArrayRef.h:143