26 #define DEBUG_TYPE "packets"
45 StringRef getPassName()
const override {
return "R600 Packetizer"; }
55 bool ConsideredInstUsesAlreadyWrittenVectorElement;
58 return TRI.getHWRegChan(
MI.getOperand(0).getReg());
67 if (!
TII->isALUInstr(
I->getOpcode()) && !
I->isBundle())
75 int BISlot = getSlot(*BI);
76 if (LastDstChan >= BISlot)
82 if (OperandIdx > -1 && BI->getOperand(OperandIdx).getImm() == 0)
84 int DstIdx =
TII->getOperandIdx(BI->getOpcode(), R600::OpName::dst);
88 Register Dst = BI->getOperand(DstIdx).getReg();
89 if (isTrans ||
TII->isTransOnly(*BI)) {
90 Result[Dst] = R600::PS;
93 if (BI->getOpcode() == R600::DOT4_r600 ||
94 BI->getOpcode() == R600::DOT4_eg) {
95 Result[Dst] = R600::PV_X;
98 if (Dst == R600::OQAP) {
102 switch (
TRI.getHWRegChan(Dst)) {
119 }
while ((++BI)->isBundledWithPred());
130 for (
unsigned Op : Ops) {
131 int OperandIdx =
TII->getOperandIdx(
MI.getOpcode(),
Op);
134 Register Src =
MI.getOperand(OperandIdx).getReg();
137 MI.getOperand(OperandIdx).setReg(It->second);
145 TII(
ST.getInstrInfo()),
146 TRI(
TII->getRegisterInfo()) {
147 VLIW5 = !
ST.hasCaymanISA();
151 void initPacketizerState()
override {
152 ConsideredInstUsesAlreadyWrittenVectorElement =
false;
164 if (
TII->isVector(
MI))
166 if (!
TII->isALUInstr(
MI.getOpcode()))
168 if (
MI.getOpcode() == R600::GROUP_BARRIER)
172 return TII->isLDSInstr(
MI.getOpcode());
177 bool isLegalToPacketizeTogether(
SUnit *SUI,
SUnit *SUJ)
override {
179 if (getSlot(*MII) == getSlot(*MIJ))
180 ConsideredInstUsesAlreadyWrittenVectorElement =
true;
182 int OpI =
TII->getOperandIdx(MII->
getOpcode(), R600::OpName::pred_sel),
183 OpJ =
TII->getOperandIdx(MIJ->getOpcode(), R600::OpName::pred_sel);
185 PredJ = (OpJ > -1)?MIJ->getOperand(OpJ).getReg() :
Register();
189 for (
unsigned i = 0,
e = SUJ->
Succs.size();
i <
e; ++
i) {
203 TII->definesAddressRegister(*MII) ||
TII->definesAddressRegister(*MIJ);
205 TII->usesAddressRegister(*MII) ||
TII->usesAddressRegister(*MIJ);
207 return !ARDef || !ARUse;
212 bool isLegalToPruneDependencies(
SUnit *SUI,
SUnit *SUJ)
override {
218 MI->getOperand(LastOp).setImm(
Bit);
223 std::vector<R600InstrInfo::BankSwizzle> &BS,
225 isTransSlot =
TII->isTransOnly(
MI);
226 assert (!isTransSlot || VLIW5);
229 if (!isTransSlot && !CurrentPacketMIs.empty()) {
230 if (getSlot(
MI) <= getSlot(*CurrentPacketMIs.back())) {
231 if (ConsideredInstUsesAlreadyWrittenVectorElement &&
232 !
TII->isVectorOnly(
MI) && VLIW5) {
235 dbgs() <<
"Considering as Trans Inst :";
245 CurrentPacketMIs.push_back(&
MI);
246 if (!
TII->fitsConstReadLimitations(CurrentPacketMIs)) {
248 dbgs() <<
"Couldn't pack :\n";
250 dbgs() <<
"with the following packets :\n";
251 for (
unsigned i = 0,
e = CurrentPacketMIs.size() - 1;
i <
e;
i++) {
252 CurrentPacketMIs[
i]->dump();
255 dbgs() <<
"because of Consts read limitations\n";
257 CurrentPacketMIs.pop_back();
262 if (!
TII->fitsReadPortLimitations(CurrentPacketMIs,
263 PV, BS, isTransSlot)) {
265 dbgs() <<
"Couldn't pack :\n";
267 dbgs() <<
"with the following packets :\n";
268 for (
unsigned i = 0,
e = CurrentPacketMIs.size() - 1;
i <
e;
i++) {
269 CurrentPacketMIs[
i]->dump();
272 dbgs() <<
"because of Read port limitations\n";
274 CurrentPacketMIs.pop_back();
279 if (isTransSlot &&
TII->readsLDSSrcReg(
MI))
282 CurrentPacketMIs.pop_back();
288 CurrentPacketMIs.empty() ? &
MI : CurrentPacketMIs.front();
290 getPreviousVector(FirstInBundle);
291 std::vector<R600InstrInfo::BankSwizzle> BS;
294 if (isBundlableWithCurrentPMI(
MI, PV, BS, isTransSlot)) {
295 for (
unsigned i = 0,
e = CurrentPacketMIs.size();
i <
e;
i++) {
297 unsigned Op =
TII->getOperandIdx(
MI->getOpcode(),
298 R600::OpName::bank_swizzle);
299 MI->getOperand(
Op).setImm(BS[
i]);
302 TII->getOperandIdx(
MI.getOpcode(), R600::OpName::bank_swizzle);
303 MI.getOperand(
Op).setImm(BS.back());
304 if (!CurrentPacketMIs.empty())
305 setIsLastBit(CurrentPacketMIs.back(), 0);
306 substitutePV(
MI, PV);
309 endPacket(std::next(It)->
getParent(), std::next(It));
313 endPacket(
MI.getParent(),
MI);
314 if (
TII->isTransOnly(
MI))
333 if (
Packetizer.getResourceTracker()->getInstrItins()->isEmpty())
348 if (
MI.isKill() ||
MI.getOpcode() == R600::IMPLICIT_DEF ||
349 (
MI.getOpcode() == R600::CF_ALU && !
MI.getOperand(8).getImm()))
358 unsigned RemainingCount =
MBB->
size();
364 for(;
I !=
MBB->
begin(); --
I, --RemainingCount) {
371 if (
I == RegionEnd) {
372 RegionEnd = std::prev(RegionEnd);
377 if (
I == std::prev(RegionEnd)) {
378 RegionEnd = std::prev(RegionEnd);
394 "R600 Packetizer",
false,
false)
398 char R600Packetizer::
ID = 0;
403 return new R600Packetizer();