@@ -62,13 +62,18 @@ namespace {
62
62
bool Changed = false ;
63
63
bool RunUnswitching = false ;
64
64
65
+ // When following the def-use chains, it can go outside the loop.
66
+ // Strict upper bound on number of traversed out-of-loop blocks.
67
+ unsigned MaxDepthOutOfLoop;
68
+
65
69
public:
66
70
SimplifyIndvar (Loop *Loop, ScalarEvolution *SE, DominatorTree *DT,
67
71
LoopInfo *LI, const TargetTransformInfo *TTI,
68
72
SCEVExpander &Rewriter,
69
- SmallVectorImpl<WeakTrackingVH> &Dead)
73
+ SmallVectorImpl<WeakTrackingVH> &Dead,
74
+ unsigned MaxDepthOutOfLoop = 1 )
70
75
: L(Loop), LI(LI), SE(SE), DT(DT), TTI(TTI), Rewriter(Rewriter),
71
- DeadInsts (Dead) {
76
+ DeadInsts (Dead), MaxDepthOutOfLoop(MaxDepthOutOfLoop) {
72
77
assert (LI && " IV simplification requires LoopInfo" );
73
78
}
74
79
@@ -509,8 +514,8 @@ bool SimplifyIndvar::eliminateTrunc(TruncInst *TI) {
509
514
!DT->isReachableFromEntry (cast<Instruction>(U)->getParent ()))
510
515
continue ;
511
516
ICmpInst *ICI = dyn_cast<ICmpInst>(U);
512
- if (!ICI) return false ;
513
- assert (L-> contains (ICI-> getParent ()) && " LCSSA form broken? " ) ;
517
+ if (!ICI)
518
+ return false ;
514
519
if (!(ICI->getOperand (0 ) == TI && L->isLoopInvariant (ICI->getOperand (1 ))) &&
515
520
!(ICI->getOperand (1 ) == TI && L->isLoopInvariant (ICI->getOperand (0 ))))
516
521
return false ;
@@ -839,10 +844,12 @@ bool SimplifyIndvar::strengthenRightShift(BinaryOperator *BO,
839
844
}
840
845
841
846
// / Add all uses of Def to the current IV's worklist.
842
- static void pushIVUsers (
843
- Instruction *Def, Loop *L,
844
- SmallPtrSet<Instruction*,16 > &Simplified,
845
- SmallVectorImpl< std::pair<Instruction*,Instruction*> > &SimpleIVUsers) {
847
+ static void
848
+ pushIVUsers (Instruction *Def, Loop *L, DominatorTree *DT,
849
+ SmallPtrSet<Instruction *, 16 > &Simplified,
850
+ SmallVectorImpl<std::tuple<Instruction *, Instruction *, unsigned >>
851
+ &SimpleIVUsers,
852
+ unsigned OutOfLoopChainCounter, unsigned MaxOutOfLoopChainCounter) {
846
853
847
854
for (User *U : Def->users ()) {
848
855
Instruction *UI = cast<Instruction>(U);
@@ -854,16 +861,23 @@ static void pushIVUsers(
854
861
if (UI == Def)
855
862
continue ;
856
863
857
- // Only change the current Loop, do not change the other parts ( e.g. other
858
- // Loops) .
859
- if (!L->contains (UI ))
864
+ // Avoid adding Defs that SCEV expand to themselves, e.g. the LoopPhis
865
+ // of the outter loops .
866
+ if (!DT-> dominates ( L->getHeader (), UI-> getParent () ))
860
867
continue ;
861
868
862
869
// Do not push the same instruction more than once.
863
870
if (!Simplified.insert (UI).second )
864
871
continue ;
865
872
866
- SimpleIVUsers.push_back (std::make_pair (UI, Def));
873
+ unsigned Counter =
874
+ L->contains (UI)
875
+ ? 0 // reset depth if we go back inside the loop.
876
+ : OutOfLoopChainCounter + (UI->getParent () != Def->getParent ());
877
+
878
+ if (!MaxOutOfLoopChainCounter || Counter < MaxOutOfLoopChainCounter) {
879
+ SimpleIVUsers.push_back (std::make_tuple (UI, Def, Counter));
880
+ }
867
881
}
868
882
}
869
883
@@ -908,17 +922,17 @@ void SimplifyIndvar::simplifyUsers(PHINode *CurrIV, IVVisitor *V) {
908
922
SmallPtrSet<Instruction*,16 > Simplified;
909
923
910
924
// Use-def pairs if IV users waiting to be processed for CurrIV.
911
- SmallVector<std::pair<Instruction*, Instruction*>, 8 > SimpleIVUsers;
925
+ SmallVector<std::tuple<Instruction *, Instruction *, unsigned >, 8 >
926
+ SimpleIVUsers;
912
927
913
928
// Push users of the current LoopPhi. In rare cases, pushIVUsers may be
914
929
// called multiple times for the same LoopPhi. This is the proper thing to
915
930
// do for loop header phis that use each other.
916
- pushIVUsers (CurrIV, L, Simplified, SimpleIVUsers);
931
+ pushIVUsers (CurrIV, L, DT, Simplified, SimpleIVUsers, 0 , MaxDepthOutOfLoop );
917
932
918
933
while (!SimpleIVUsers.empty ()) {
919
- std::pair<Instruction*, Instruction*> UseOper =
920
- SimpleIVUsers.pop_back_val ();
921
- Instruction *UseInst = UseOper.first ;
934
+ auto [UseInst, IVOperand, OutOfLoopChainCounter] =
935
+ SimpleIVUsers.pop_back_val ();
922
936
923
937
// If a user of the IndVar is trivially dead, we prefer just to mark it dead
924
938
// rather than try to do some complex analysis or transformation (such as
@@ -942,11 +956,11 @@ void SimplifyIndvar::simplifyUsers(PHINode *CurrIV, IVVisitor *V) {
942
956
if ((isa<PtrToIntInst>(UseInst)) || (isa<TruncInst>(UseInst)))
943
957
for (Use &U : UseInst->uses ()) {
944
958
Instruction *User = cast<Instruction>(U.getUser ());
945
- if (replaceIVUserWithLoopInvariant (User))
959
+ if (DT->dominates (L->getHeader (), User->getParent ()) &&
960
+ replaceIVUserWithLoopInvariant (User))
946
961
break ; // done replacing
947
962
}
948
963
949
- Instruction *IVOperand = UseOper.second ;
950
964
for (unsigned N = 0 ; IVOperand; ++N) {
951
965
assert (N <= Simplified.size () && " runaway iteration" );
952
966
(void ) N;
@@ -960,22 +974,25 @@ void SimplifyIndvar::simplifyUsers(PHINode *CurrIV, IVVisitor *V) {
960
974
continue ;
961
975
962
976
if (eliminateIVUser (UseInst, IVOperand)) {
963
- pushIVUsers (IVOperand, L, Simplified, SimpleIVUsers);
977
+ pushIVUsers (IVOperand, L, DT, Simplified, SimpleIVUsers,
978
+ OutOfLoopChainCounter, MaxDepthOutOfLoop);
964
979
continue ;
965
980
}
966
981
967
982
if (BinaryOperator *BO = dyn_cast<BinaryOperator>(UseInst)) {
968
983
if (strengthenBinaryOp (BO, IVOperand)) {
969
984
// re-queue uses of the now modified binary operator and fall
970
985
// through to the checks that remain.
971
- pushIVUsers (IVOperand, L, Simplified, SimpleIVUsers);
986
+ pushIVUsers (IVOperand, L, DT, Simplified, SimpleIVUsers,
987
+ OutOfLoopChainCounter, MaxDepthOutOfLoop);
972
988
}
973
989
}
974
990
975
991
// Try to use integer induction for FPToSI of float induction directly.
976
992
if (replaceFloatIVWithIntegerIV (UseInst)) {
977
993
// Re-queue the potentially new direct uses of IVOperand.
978
- pushIVUsers (IVOperand, L, Simplified, SimpleIVUsers);
994
+ pushIVUsers (IVOperand, L, DT, Simplified, SimpleIVUsers,
995
+ OutOfLoopChainCounter, MaxDepthOutOfLoop);
979
996
continue ;
980
997
}
981
998
@@ -985,7 +1002,8 @@ void SimplifyIndvar::simplifyUsers(PHINode *CurrIV, IVVisitor *V) {
985
1002
continue ;
986
1003
}
987
1004
if (isSimpleIVUser (UseInst, L, SE)) {
988
- pushIVUsers (UseInst, L, Simplified, SimpleIVUsers);
1005
+ pushIVUsers (UseInst, L, DT, Simplified, SimpleIVUsers,
1006
+ OutOfLoopChainCounter, MaxDepthOutOfLoop);
989
1007
}
990
1008
}
991
1009
}
@@ -999,13 +1017,13 @@ void IVVisitor::anchor() { }
999
1017
// / Returns a pair where the first entry indicates that the function makes
1000
1018
// / changes and the second entry indicates that it introduced new opportunities
1001
1019
// / for loop unswitching.
1002
- std::pair<bool , bool > simplifyUsersOfIV (PHINode *CurrIV, ScalarEvolution *SE,
1003
- DominatorTree *DT, LoopInfo *LI ,
1004
- const TargetTransformInfo *TTI,
1005
- SmallVectorImpl<WeakTrackingVH> &Dead,
1006
- SCEVExpander &Rewriter , IVVisitor *V) {
1020
+ std::pair<bool , bool >
1021
+ simplifyUsersOfIV (PHINode *CurrIV, ScalarEvolution *SE, DominatorTree *DT ,
1022
+ LoopInfo *LI, const TargetTransformInfo *TTI,
1023
+ SmallVectorImpl<WeakTrackingVH> &Dead, SCEVExpander &Rewriter ,
1024
+ unsigned MaxDepthOutOfLoop , IVVisitor *V) {
1007
1025
SimplifyIndvar SIV (LI->getLoopFor (CurrIV->getParent ()), SE, DT, LI, TTI,
1008
- Rewriter, Dead);
1026
+ Rewriter, Dead, MaxDepthOutOfLoop );
1009
1027
SIV.simplifyUsers (CurrIV, V);
1010
1028
return {SIV.hasChanged (), SIV.runUnswitching ()};
1011
1029
}
0 commit comments