diff options
Diffstat (limited to 'llvm/lib/CodeGen/ModuloSchedule.cpp')
-rw-r--r-- | llvm/lib/CodeGen/ModuloSchedule.cpp | 75 |
1 files changed, 54 insertions, 21 deletions
diff --git a/llvm/lib/CodeGen/ModuloSchedule.cpp b/llvm/lib/CodeGen/ModuloSchedule.cpp index bff0b7a..d208a62 100644 --- a/llvm/lib/CodeGen/ModuloSchedule.cpp +++ b/llvm/lib/CodeGen/ModuloSchedule.cpp @@ -141,6 +141,7 @@ void ModuloScheduleExpander::generatePipelinedLoop() { MachineInstr *NewMI = cloneInstr(CI, MaxStageCount, StageNum); updateInstruction(NewMI, false, MaxStageCount, StageNum, VRMap); KernelBB->push_back(NewMI); + LIS.InsertMachineInstrInMaps(*NewMI); InstrMap[NewMI] = CI; } @@ -150,6 +151,7 @@ void ModuloScheduleExpander::generatePipelinedLoop() { MachineInstr *NewMI = MF.CloneMachineInstr(&MI); updateInstruction(NewMI, false, MaxStageCount, 0, VRMap); KernelBB->push_back(NewMI); + LIS.InsertMachineInstrInMaps(*NewMI); InstrMap[NewMI] = &MI; } @@ -179,6 +181,10 @@ void ModuloScheduleExpander::generatePipelinedLoop() { // Add branches between prolog and epilog blocks. addBranches(*Preheader, PrologBBs, KernelBB, EpilogBBs, VRMap); + // The intervals of newly created virtual registers are calculated after the + // kernel expansion. + calculateIntervals(); + delete[] VRMap; delete[] VRMapPhi; } @@ -226,6 +232,7 @@ void ModuloScheduleExpander::generateProlog(unsigned LastStage, cloneAndChangeInstr(&*BBI, i, (unsigned)StageNum); updateInstruction(NewMI, false, i, (unsigned)StageNum, VRMap); NewBB->push_back(NewMI); + LIS.InsertMachineInstrInMaps(*NewMI); InstrMap[NewMI] = &*BBI; } } @@ -303,6 +310,7 @@ void ModuloScheduleExpander::generateEpilog( MachineInstr *NewMI = cloneInstr(In, UINT_MAX, 0); updateInstruction(NewMI, i == 1, EpilogStage, 0, VRMap); NewBB->push_back(NewMI); + LIS.InsertMachineInstrInMaps(*NewMI); InstrMap[NewMI] = In; } } @@ -343,14 +351,11 @@ void ModuloScheduleExpander::generateEpilog( /// basic block with ToReg. static void replaceRegUsesAfterLoop(Register FromReg, Register ToReg, MachineBasicBlock *MBB, - MachineRegisterInfo &MRI, - LiveIntervals &LIS) { + MachineRegisterInfo &MRI) { for (MachineOperand &O : llvm::make_early_inc_range(MRI.use_operands(FromReg))) if (O.getParent()->getParent() != MBB) O.setReg(ToReg); - if (!LIS.hasInterval(ToReg)) - LIS.createEmptyInterval(ToReg); } /// Return true if the register has a use that occurs outside the @@ -544,8 +549,10 @@ void ModuloScheduleExpander::generateExistingPhis( if (VRMap[LastStageNum - np - 1].count(LoopVal)) PhiOp2 = VRMap[LastStageNum - np - 1][LoopVal]; - if (IsLast && np == NumPhis - 1) - replaceRegUsesAfterLoop(Def, NewReg, BB, MRI, LIS); + if (IsLast && np == NumPhis - 1) { + replaceRegUsesAfterLoop(Def, NewReg, BB, MRI); + NoIntervalRegs.push_back(NewReg); + } continue; } } @@ -563,6 +570,7 @@ void ModuloScheduleExpander::generateExistingPhis( TII->get(TargetOpcode::PHI), NewReg); NewPhi.addReg(PhiOp1).addMBB(BB1); NewPhi.addReg(PhiOp2).addMBB(BB2); + LIS.InsertMachineInstrInMaps(*NewPhi); if (np == 0) InstrMap[NewPhi] = &*BBI; @@ -584,8 +592,10 @@ void ModuloScheduleExpander::generateExistingPhis( // Check if we need to rename any uses that occurs after the loop. The // register to replace depends on whether the Phi is scheduled in the // epilog. - if (IsLast && np == NumPhis - 1) - replaceRegUsesAfterLoop(Def, NewReg, BB, MRI, LIS); + if (IsLast && np == NumPhis - 1) { + replaceRegUsesAfterLoop(Def, NewReg, BB, MRI); + NoIntervalRegs.push_back(NewReg); + } // In the kernel, a dependent Phi uses the value from this Phi. if (InKernel) @@ -603,9 +613,12 @@ void ModuloScheduleExpander::generateExistingPhis( // Check if we need to rename a Phi that has been eliminated due to // scheduling. if (NumStages == 0 && IsLast) { - auto It = VRMap[CurStageNum].find(LoopVal); - if (It != VRMap[CurStageNum].end()) - replaceRegUsesAfterLoop(Def, It->second, BB, MRI, LIS); + auto &CurStageMap = VRMap[CurStageNum]; + auto It = CurStageMap.find(LoopVal); + if (It != CurStageMap.end()) { + replaceRegUsesAfterLoop(Def, It->second, BB, MRI); + NoIntervalRegs.push_back(It->second); + } } } } @@ -705,6 +718,7 @@ void ModuloScheduleExpander::generatePhis( TII->get(TargetOpcode::PHI), NewReg); NewPhi.addReg(PhiOp1).addMBB(BB1); NewPhi.addReg(PhiOp2).addMBB(BB2); + LIS.InsertMachineInstrInMaps(*NewPhi); if (np == 0) InstrMap[NewPhi] = &*BBI; @@ -724,8 +738,10 @@ void ModuloScheduleExpander::generatePhis( rewriteScheduledInstr(NewBB, InstrMap, CurStageNum, np, &*BBI, Def, NewReg); } - if (IsLast && np == NumPhis - 1) - replaceRegUsesAfterLoop(Def, NewReg, BB, MRI, LIS); + if (IsLast && np == NumPhis - 1) { + replaceRegUsesAfterLoop(Def, NewReg, BB, MRI); + NoIntervalRegs.push_back(NewReg); + } } } } @@ -834,9 +850,11 @@ void ModuloScheduleExpander::splitLifetimes(MachineBasicBlock *KernelBB, // We split the lifetime when we find the first use. if (!SplitReg) { SplitReg = MRI.createVirtualRegister(MRI.getRegClass(Def)); - BuildMI(*KernelBB, MI, MI->getDebugLoc(), - TII->get(TargetOpcode::COPY), SplitReg) - .addReg(Def); + MachineInstr *newCopy = + BuildMI(*KernelBB, MI, MI->getDebugLoc(), + TII->get(TargetOpcode::COPY), SplitReg) + .addReg(Def); + LIS.InsertMachineInstrInMaps(*newCopy); } BBJ.substituteRegister(Def, SplitReg, 0, *TRI); } @@ -904,6 +922,8 @@ void ModuloScheduleExpander::addBranches(MachineBasicBlock &PreheaderBB, removePhis(Epilog, LastEpi); // Remove the blocks that are no longer referenced. if (LastPro != LastEpi) { + for (auto &MI : *LastEpi) + LIS.RemoveMachineInstrFromMaps(MI); LastEpi->clear(); LastEpi->eraseFromParent(); } @@ -911,6 +931,8 @@ void ModuloScheduleExpander::addBranches(MachineBasicBlock &PreheaderBB, LoopInfo->disposed(&LIS); NewKernel = nullptr; } + for (auto &MI : *LastPro) + LIS.RemoveMachineInstrFromMaps(MI); LastPro->clear(); LastPro->eraseFromParent(); } else { @@ -931,6 +953,14 @@ void ModuloScheduleExpander::addBranches(MachineBasicBlock &PreheaderBB, } } +/// Some registers are generated during the kernel expansion. We calculate the +/// live intervals of these registers after the expansion. +void ModuloScheduleExpander::calculateIntervals() { + for (Register Reg : NoIntervalRegs) + LIS.createAndComputeVirtRegInterval(Reg); + NoIntervalRegs.clear(); +} + /// Return true if we can compute the amount the instruction changes /// during each iteration. Set Delta to the amount of the change. bool ModuloScheduleExpander::computeDelta(MachineInstr &MI, unsigned &Delta) { @@ -1051,8 +1081,10 @@ void ModuloScheduleExpander::updateInstruction(MachineInstr *NewMI, Register NewReg = MRI.createVirtualRegister(RC); MO.setReg(NewReg); VRMap[CurStageNum][reg] = NewReg; - if (LastDef) - replaceRegUsesAfterLoop(reg, NewReg, BB, MRI, LIS); + if (LastDef) { + replaceRegUsesAfterLoop(reg, NewReg, BB, MRI); + NoIntervalRegs.push_back(NewReg); + } } else if (MO.isUse()) { MachineInstr *Def = MRI.getVRegDef(reg); // Compute the stage that contains the last definition for instruction. @@ -1201,10 +1233,11 @@ void ModuloScheduleExpander::rewriteScheduledInstr( UseOp.setReg(ReplaceReg); else { Register SplitReg = MRI.createVirtualRegister(MRI.getRegClass(OldReg)); - BuildMI(*BB, UseMI, UseMI->getDebugLoc(), TII->get(TargetOpcode::COPY), - SplitReg) - .addReg(ReplaceReg); + MachineInstr *newCopy = BuildMI(*BB, UseMI, UseMI->getDebugLoc(), + TII->get(TargetOpcode::COPY), SplitReg) + .addReg(ReplaceReg); UseOp.setReg(SplitReg); + LIS.InsertMachineInstrInMaps(*newCopy); } } } |