diff --git a/llvm/include/llvm/Analysis/ScalarEvolution.h b/llvm/include/llvm/Analysis/ScalarEvolution.h --- a/llvm/include/llvm/Analysis/ScalarEvolution.h +++ b/llvm/include/llvm/Analysis/ScalarEvolution.h @@ -1032,6 +1032,9 @@ /// Test whether the given SCEV has Op as a direct or indirect operand. bool hasOperand(const SCEV *S, const SCEV *Op) const; + /// Test whether the given SCEV has a SCEVUnknown that has been nulled. + bool hasNulledUnknown(const SCEV *S) const; + /// Return the size of an element read or written by Inst. const SCEV *getElementSize(Instruction *Inst); diff --git a/llvm/lib/Analysis/ScalarEvolution.cpp b/llvm/lib/Analysis/ScalarEvolution.cpp --- a/llvm/lib/Analysis/ScalarEvolution.cpp +++ b/llvm/lib/Analysis/ScalarEvolution.cpp @@ -12461,6 +12461,13 @@ return SCEVExprContains(S, [&](const SCEV *Expr) { return Expr == Op; }); } +bool ScalarEvolution::hasNulledUnknown(const SCEV *S) const { + return SCEVExprContains(S, [&](const SCEV *Expr) { + auto U = dyn_cast(Expr); + return U && !U->getValPtr(); + }); +} + bool ScalarEvolution::ExitLimit::hasOperand(const SCEV *S) const { auto IsS = [&](const SCEV *X) { return S == X; }; auto ContainsS = [&](const SCEV *X) { diff --git a/llvm/lib/Transforms/Scalar/LoopStrengthReduce.cpp b/llvm/lib/Transforms/Scalar/LoopStrengthReduce.cpp --- a/llvm/lib/Transforms/Scalar/LoopStrengthReduce.cpp +++ b/llvm/lib/Transforms/Scalar/LoopStrengthReduce.cpp @@ -5843,6 +5843,8 @@ auto DbgDIExpr = std::get(D); if (!isa(DbgValue->getVariableLocation())) continue; + if (SE.hasNulledUnknown(DbgValueSCEV)) + continue; for (PHINode &Phi : L->getHeader()->phis()) { if (DbgValueType != Phi.getType()) continue;