@@ -503,11 +503,9 @@ rewriteLoopHeaderPredecessors(LoopTy *SubLoop, RegionTy *SubLoopRegion) {
503
503
return SubLoopHeaderRegion;
504
504
}
505
505
506
- static void
507
- getExitingRegions (LoopRegionFunctionInfo *LRFI,
508
- SILLoop *Loop,
509
- LoopRegion *LRegion,
510
- llvm::SmallVectorImpl<LoopRegion *> &ExitingRegions) {
506
+ static void getExitingRegions (LoopRegionFunctionInfo *LRFI, SILLoop *Loop,
507
+ LoopRegion *LRegion,
508
+ llvm::SmallVectorImpl<unsigned > &ExitingRegions) {
511
509
llvm::SmallVector<SILBasicBlock *, 8 > ExitingBlocks;
512
510
Loop->getExitingBlocks (ExitingBlocks);
513
511
@@ -520,7 +518,7 @@ getExitingRegions(LoopRegionFunctionInfo *LRFI,
520
518
Region = LRFI->getRegion (RegionParentID);
521
519
RegionParentID = Region->getParentID ();
522
520
}
523
- ExitingRegions.push_back (Region);
521
+ ExitingRegions.push_back (Region-> getID () );
524
522
}
525
523
526
524
// We can have a loop subregion that has multiple exiting edges from the
@@ -530,9 +528,7 @@ getExitingRegions(LoopRegionFunctionInfo *LRFI,
530
528
// In order to make sure we have a deterministic ordering when we visiting
531
529
// exiting subregions, we need to sort our exiting regions by ID, not pointer
532
530
// value.
533
- sortUnique (ExitingRegions, [](LoopRegion *R1, LoopRegion *R2) -> bool {
534
- return R1->getID () < R2->getID ();
535
- });
531
+ sortUnique (ExitingRegions);
536
532
}
537
533
538
534
// / For each exiting block:
@@ -561,17 +557,18 @@ rewriteLoopExitingBlockSuccessors(LoopTy *Loop, RegionTy *LRegion) {
561
557
// region which the block is a subregion of. Since we initialize our data
562
558
// structure by processing the loop nest bottom up, this should always give us
563
559
// the correct region for the level of the loop we are processing.
564
- llvm::SmallVector<RegionTy *, 8 > ExitingRegions ;
565
- getExitingRegions (this , Loop, LRegion, ExitingRegions );
560
+ auto &ExitingSubregions = LRegion-> getSubregionData (). ExitingSubregions ;
561
+ getExitingRegions (this , Loop, LRegion, ExitingSubregions );
566
562
567
563
// Then for each exiting region ER of the Loop L...
568
564
DEBUG (llvm::dbgs () << " Visiting Exit Blocks...\n " );
569
- for (auto *ExitingRegion : ExitingRegions) {
565
+ for (unsigned ExitingSubregionID : ExitingSubregions) {
566
+ auto *ExitingSubregion = getRegion (ExitingSubregionID);
570
567
DEBUG (llvm::dbgs () << " Exiting Region: "
571
- << ExitingRegion ->getID () << " \n " );
568
+ << ExitingSubregion ->getID () << " \n " );
572
569
573
570
// For each successor region S of ER...
574
- for (auto SuccID : ExitingRegion ->getSuccs ()) {
571
+ for (auto SuccID : ExitingSubregion ->getSuccs ()) {
575
572
DEBUG (llvm::dbgs () << " Succ: " << SuccID.ID
576
573
<< " . IsNonLocal: "
577
574
<< (SuccID.IsNonLocal ? " true" : " false" ) << " \n " );
@@ -588,22 +585,22 @@ rewriteLoopExitingBlockSuccessors(LoopTy *Loop, RegionTy *LRegion) {
588
585
auto *SuccRegion = getRegion (SuccID.ID );
589
586
if (!LRegion->containsSubregion (SuccRegion)) {
590
587
DEBUG (llvm::dbgs () << " Is not a subregion, replacing.\n " );
591
- SuccRegion->replacePred (ExitingRegion ->ID , LRegion->ID );
592
- if (ExitingRegion ->IsUnknownControlFlowEdgeTail )
588
+ SuccRegion->replacePred (ExitingSubregion ->ID , LRegion->ID );
589
+ if (ExitingSubregion ->IsUnknownControlFlowEdgeTail )
593
590
LRegion->IsUnknownControlFlowEdgeTail = true ;
594
591
// If the successor region is already in this LRegion this returns that
595
592
// regions index. Otherwise it returns a new index.
596
593
unsigned Index = LRegion->addSucc (SuccRegion);
597
- ExitingRegion ->replaceSucc (SuccID,
598
- LoopRegion::SuccessorID (Index, true ));
599
- propagateLivenessDownNonLocalSuccessorEdges (ExitingRegion );
594
+ ExitingSubregion ->replaceSucc (SuccID,
595
+ LoopRegion::SuccessorID (Index, true ));
596
+ propagateLivenessDownNonLocalSuccessorEdges (ExitingSubregion );
600
597
continue ;
601
598
}
602
599
603
600
// Otherwise, we know S is in L. If the RPO number of S is less than the
604
601
// RPO number of ER, then we know that the edge in between them is not a
605
602
// backedge and thus we do not want to clip the edge.
606
- if (SuccRegion->getRPONumber () > ExitingRegion ->getRPONumber ()) {
603
+ if (SuccRegion->getRPONumber () > ExitingSubregion ->getRPONumber ()) {
607
604
DEBUG (llvm::dbgs () << " Is a subregion, but not a "
608
605
" backedge, not removing.\n " );
609
606
continue ;
@@ -613,8 +610,8 @@ rewriteLoopExitingBlockSuccessors(LoopTy *Loop, RegionTy *LRegion) {
613
610
DEBUG (llvm::dbgs () << " Is a subregion and a backedge, "
614
611
" removing.\n " );
615
612
auto Iter =
616
- std::remove (SuccRegion->Preds .begin (), SuccRegion->Preds .end (),
617
- ExitingRegion ->getID ());
613
+ std::remove (SuccRegion->Preds .begin (), SuccRegion->Preds .end (),
614
+ ExitingSubregion ->getID ());
618
615
SuccRegion->Preds .erase (Iter);
619
616
}
620
617
}
@@ -688,9 +685,17 @@ propagateLivenessDownNonLocalSuccessorEdges(LoopRegion *Parent) {
688
685
689
686
while (Worklist.size ()) {
690
687
LoopRegion *R = Worklist.pop_back_val ();
688
+
691
689
for (unsigned SubregionID : R->getSubregions ()) {
692
690
LoopRegion *Subregion = getRegion (SubregionID);
693
691
bool ShouldVisit = false ;
692
+
693
+ // Make sure we can identify when the subregion has at least one dead
694
+ // non-local edge and no remaining live edges. In such a case, we need to
695
+ // remove the subregion from the exiting subregion array of R after the
696
+ // loop.
697
+ bool HasDeadNonLocalEdge = false ;
698
+ bool HasNoLiveLocalEdges = true ;
694
699
for (auto &SuccID : Subregion->Succs ) {
695
700
// If the successor is already dead, skip it. We should have visited all
696
701
// its children when we marked it as dead.
@@ -703,18 +708,31 @@ propagateLivenessDownNonLocalSuccessorEdges(LoopRegion *Parent) {
703
708
704
709
// If the non-local successor edge points to a parent successor that is
705
710
// not dead continue.
706
- if (R->Succs [SuccID->ID ].hasValue ())
711
+ if (R->Succs [SuccID->ID ].hasValue ()) {
712
+ HasNoLiveLocalEdges = false ;
707
713
continue ;
714
+ }
708
715
709
- // Ok, we found a target! Mark is as dead and make sure that we visit
710
- // the subregion's children.
716
+ // Ok, we found a target! Mark it as dead and make sure that we visit
717
+ // the subregion's children if it is not a block.
718
+ HasDeadNonLocalEdge = true ;
711
719
ShouldVisit = true ;
712
720
713
721
// This is safe to do since when erasing in a BlotSetVector, we do not
714
722
// invalidate the iterators.
715
723
Subregion->Succs .erase (*SuccID);
716
724
}
717
725
726
+ // Remove Subregion from R's exiting subregion array if Subregion no
727
+ // longer has /any/ non-local successors.
728
+ if (HasDeadNonLocalEdge && HasNoLiveLocalEdges) {
729
+ auto &ExitingSubregions = R->getSubregionData ().ExitingSubregions ;
730
+ auto Iter =
731
+ std::remove (ExitingSubregions.begin (), ExitingSubregions.end (),
732
+ Subregion->getID ());
733
+ ExitingSubregions.erase (Iter);
734
+ }
735
+
718
736
if (ShouldVisit)
719
737
Worklist.push_back (Subregion);
720
738
}
@@ -816,6 +834,21 @@ void LoopRegionFunctionInfo::print(raw_ostream &os) const {
816
834
for (unsigned I : SortedSuccs) {
817
835
os << " \n (parentindex:" << I << " )" ;
818
836
}
837
+ os << " )\n " ;
838
+
839
+ os << " (exiting-subregs" ;
840
+ if (!R->isBlock ()) {
841
+ llvm::SmallVector<unsigned , 4 > ExitingSubregions;
842
+ auto ExitingSubRegs = R->getExitingSubregions ();
843
+ std::copy (ExitingSubRegs.begin (), ExitingSubRegs.end (),
844
+ std::back_inserter (ExitingSubregions));
845
+ std::sort (ExitingSubregions.begin (), ExitingSubregions.begin ());
846
+ for (unsigned SubregionID : ExitingSubregions) {
847
+ os << " \n " ;
848
+ LoopRegion *Subregion = getRegion (SubregionID);
849
+ Subregion->print (os, true );
850
+ }
851
+ }
819
852
os << " ))\n " ;
820
853
}
821
854
}
0 commit comments