42 typedef Counters RegCounters[512];
43 typedef std::pair<unsigned, unsigned> RegInterval;
54 static const Counters WaitCounts;
57 static const Counters ZeroCounts;
69 RegCounters DefinedRegs;
72 unsigned ExpInstrTypesSeen;
89 const Counters &Counts);
102 ExpInstrTypesSeen(0) { }
106 const char *getPassName()
const {
107 return "SI insert wait instructions";
116 const Counters SIInsertWaits::WaitCounts = { { 15, 7, 7 } };
117 const Counters SIInsertWaits::ZeroCounts = { { 0, 0, 0 } };
120 return new SIInsertWaits(tm);
140 assert(Op.
isReg() &&
"First LGKM operand must be a register!");
143 unsigned Size = TRI->getMinimalPhysRegClass(Reg)->getSize();
144 Result.Named.LGKM = Size > 4 ? 2 : 1;
148 Result.Named.LGKM = 1;
152 Result.Named.LGKM = 0;
180 if (
I->isReg() &&
I->isUse())
189 if (!Op.
isReg() || !TRI->isInAllocatableClass(Op.
getReg()))
190 return std::make_pair(0, 0);
192 unsigned Reg = Op.
getReg();
193 unsigned Size = TRI->getMinimalPhysRegClass(Reg)->getSize();
198 Result.first = TRI->getEncodingValue(Reg);
199 Result.second = Result.first + Size / 4;
207 Counters Increment = getHwCounts(MI);
210 for (
unsigned i = 0; i < 3; ++i) {
211 LastIssued.Array[i] += Increment.Array[i];
212 Sum += Increment.Array[i];
220 if (Increment.Named.EXP) {
221 ExpInstrTypesSeen |= MI.
getOpcode() == AMDGPU::EXP ? 1 : 2;
227 if (!isOpRelevant(Op))
230 RegInterval
Interval = getRegInterval(Op);
231 for (
unsigned j = Interval.first; j < Interval.second; ++j) {
235 DefinedRegs[j] = LastIssued;
239 UsedRegs[j] = LastIssued;
249 if (I != MBB.
end() && I->getOpcode() == AMDGPU::S_ENDPGM)
259 Ordered[1] = ExpInstrTypesSeen == 3;
265 Counters Counts = WaitCounts;
268 bool NeedWait =
false;
270 for (
unsigned i = 0; i < 3; ++i) {
272 if (Required.Array[i] <= WaitedOn.Array[i])
278 unsigned Value = LastIssued.Array[i] - Required.Array[i];
281 Counts.Array[i] = std::min(Value, WaitCounts.Array[i]);
287 WaitedOn.Array[i] = LastIssued.Array[i] - Counts.Array[i];
294 if (Counts.Named.EXP == 0)
295 ExpInstrTypesSeen = 0;
299 .addImm((Counts.Named.VM & 0xF) |
300 ((Counts.Named.EXP & 0x7) << 4) |
301 ((Counts.Named.LGKM & 0x7) << 8));
309 for (
unsigned i = 0; i < 3; ++i)
310 Dst.Array[i] = std::max(Dst.Array[i], Src.Array[i]);
313 Counters SIInsertWaits::handleOperands(
MachineInstr &MI) {
315 Counters Result = ZeroCounts;
322 RegInterval Interval = getRegInterval(Op);
323 for (
unsigned j = Interval.first; j < Interval.second; ++j) {
339 bool Changes =
false;
346 WaitedOn = ZeroCounts;
347 LastIssued = ZeroCounts;
349 memset(&UsedRegs, 0,
sizeof(UsedRegs));
350 memset(&DefinedRegs, 0,
sizeof(DefinedRegs));
359 Changes |= insertWait(MBB, I, handleOperands(*I));
mop_iterator operands_end()
MachineInstr * getParent()
bool mayStore() const
Return true if this instruction could possibly modify memory. Instructions with this flag set are not...
iterator getFirstTerminator()
const MCInstrDesc & getDesc() const
FunctionPass * createSIInsertWaits(TargetMachine &tm)
const HexagonInstrInfo * TII
bool isReg() const
isReg - Tests if this is a MO_Register operand.
ID
LLVM Calling Convention Representation.
unsigned getNumOperands() const
static void increaseCounters(Counters &Dst, const Counters &Src)
helper function for handleOperands
bundle_iterator< MachineInstr, instr_iterator > iterator
const MachineOperand & getOperand(unsigned i) const
MachineInstrBuilder BuildMI(MachineFunction &MF, DebugLoc DL, const MCInstrDesc &MCID)
virtual const TargetInstrInfo * getInstrInfo() const
Interface definition for SIInstrInfo.
MachineRegisterInfo & getRegInfo()
const TargetMachine & getTarget() const
virtual const TargetRegisterInfo * getRegisterInfo() const
unsigned getReg() const
getReg - Returns the register number.
LLVM Value Representation.
mop_iterator operands_begin()
BasicBlockListType::iterator iterator
const MCRegisterInfo & MRI
bool isIdenticalTo(const MachineOperand &Other) const