Index: lib/Analysis/ScalarEvolution.cpp =================================================================== --- lib/Analysis/ScalarEvolution.cpp +++ lib/Analysis/ScalarEvolution.cpp @@ -211,6 +211,11 @@ cl::desc("Max coefficients in AddRec during evolving"), cl::init(8)); +static cl::opt + HugeExprThreshold("scalar-evolution-huge-expr-threshold", cl::Hidden, + cl::desc("Size of the expression which is considered huge"), + cl::init(4096)); + //===----------------------------------------------------------------------===// // SCEV class definitions //===----------------------------------------------------------------------===// @@ -845,6 +850,17 @@ return F.Size; } +/// Returns true if the subtree of \p S contains more than HugeExprThreshold +/// nodes. +static bool isHugeExpression(const SCEV *S) { + return S->getExpressionSize() >= HugeExprThreshold; +} + +/// Returns true of \p Ops contains a huge SCEV (see definition above). +static bool hasHugeExpression(SmallVectorImpl &Ops) { + return any_of(Ops, isHugeExpression); +} + namespace { struct SCEVDivision : public SCEVVisitor { @@ -2404,7 +2420,7 @@ } // Limit recursion calls depth. - if (Depth > MaxArithDepth) + if (Depth > MaxArithDepth || hasHugeExpression(Ops)) return getOrCreateAddExpr(Ops, Flags); // Okay, check to see if the same value occurs in the operand list more than @@ -2883,7 +2899,7 @@ Flags = StrengthenNoWrapFlags(this, scMulExpr, Ops, Flags); // Limit recursion calls depth. - if (Depth > MaxArithDepth) + if (Depth > MaxArithDepth || hasHugeExpression(Ops)) return getOrCreateMulExpr(Ops, Flags); // If there are any constants, fold them together. @@ -3056,7 +3072,8 @@ // Limit max number of arguments to avoid creation of unreasonably big // SCEVAddRecs with very complex operands. if (AddRec->getNumOperands() + OtherAddRec->getNumOperands() - 1 > - MaxAddRecSize) + MaxAddRecSize || isHugeExpression(AddRec) || + isHugeExpression(OtherAddRec)) continue; bool Overflow = false; Index: test/Transforms/LoopStrengthReduce/X86/bin_power.ll =================================================================== --- test/Transforms/LoopStrengthReduce/X86/bin_power.ll +++ test/Transforms/LoopStrengthReduce/X86/bin_power.ll @@ -1,4 +1,4 @@ -; RUN: opt < %s -loop-reduce -S | FileCheck %s +; RUN: opt < %s -scalar-evolution-huge-expr-threshold=1000000 -loop-reduce -S | FileCheck %s target datalayout = "e-m:e-i32:64-f80:128-n8:16:32:64-S128" target triple = "x86_64-unknown-linux-gnu"