[PATCH] D25794: [SCEV] Add a threshold to restrict number of mul operands to be inlined into SCEV
Li Huang via llvm-commits
llvm-commits at lists.llvm.org
Wed Oct 19 14:20:30 PDT 2016
lihuang created this revision.
lihuang added reviewers: sanjoy, mehdi_amini, mzolotukhin.
lihuang added a subscriber: llvm-commits.
[SCEV] Add a threshold to restrict number of mul operands to be inlined into SCEV
This is to solve the same slow-compile issue in SCEV that https://reviews.llvm.org/D3127 was trying to solve. But that patch is no longer active.
Without a threshold for mul ops inlining, getMulExpr could have exponential time complexity in the worst case. The case in PR18606 is an example that causes clang to hang.
However, this patch does not completely solve the slow-compile issue in SCEV. The reason is, not completely flattening the SCEV DAG will make SCEVRewriteVisitor another bottleneck, which visits the same SCEV multiple times and could take exponential time to finish. I will fix this in another patch.
https://reviews.llvm.org/D25794
Files:
lib/Analysis/ScalarEvolution.cpp
test/Analysis/ScalarEvolution/max-mulops-inline.ll
Index: lib/Analysis/ScalarEvolution.cpp
===================================================================
--- lib/Analysis/ScalarEvolution.cpp
+++ lib/Analysis/ScalarEvolution.cpp
@@ -121,6 +121,12 @@
cl::desc("Verify no dangling value in ScalarEvolution's "
"ExprValueMap (slow)"));
+static cl::opt<unsigned> MaxMulOpsToInline(
+ "scev-max-mulops-inline", cl::Hidden,
+ cl::desc("Maximum number of multiplication operands to be "
+ "inlined to current multiplication SCEV"),
+ cl::init(1000));
+
//===----------------------------------------------------------------------===//
// SCEV class definitions
//===----------------------------------------------------------------------===//
@@ -2505,6 +2511,8 @@
if (Idx < Ops.size()) {
bool DeletedMul = false;
while (const SCEVMulExpr *Mul = dyn_cast<SCEVMulExpr>(Ops[Idx])) {
+ if (Mul->getNumOperands() > MaxMulOpsToInline)
+ break;
// If we have an mul, expand the mul operands onto the end of the operands
// list.
Ops.erase(Ops.begin()+Idx);
Index: test/Analysis/ScalarEvolution/max-mulops-inline.ll
===================================================================
--- test/Analysis/ScalarEvolution/max-mulops-inline.ll
+++ test/Analysis/ScalarEvolution/max-mulops-inline.ll
@@ -0,0 +1,46 @@
+; RUN: opt -analyze -scalar-evolution -scev-max-mulops-inline=1 < %s | FileCheck --check-prefix=CHECK1 %s
+; RUN: opt -analyze -scalar-evolution -scev-max-mulops-inline=10 < %s | FileCheck --check-prefix=CHECK10 %s
+
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+target triple = "x86_64-unknown-linux-gnu"
+
+ at a = local_unnamed_addr global i32 0, align 4
+ at b = local_unnamed_addr global i32 0, align 4
+ at c = local_unnamed_addr global i32 0, align 4
+
+; Function Attrs: norecurse nounwind uwtable
+define i32 @main() local_unnamed_addr {
+
+; CHECK1: %mul.1 = mul nsw i32 %mul, %mul
+; CHECK1: --> ((%mul.lcssa5 * %mul.lcssa5) * (%mul.lcssa5 * %mul.lcssa5))
+
+; CHECK10: %mul.1 = mul nsw i32 %mul, %mul
+; CHECK10: --> (%mul.lcssa5 * %mul.lcssa5 * %mul.lcssa5 * %mul.lcssa5)
+
+entry:
+ %a.promoted4 = load i32, i32* @a, align 4
+ br label %for.cond1.preheader
+
+for.cond1.preheader: ; preds = %for.body3, %entry
+ %mul.lcssa5 = phi i32 [ %a.promoted4, %entry ], [ %mul.5, %for.body3 ]
+ %i.03 = phi i32 [ 0, %entry ], [ %inc5, %for.body3 ]
+ br label %for.body3
+
+for.body3: ; preds = %for.cond1.preheader
+ %mul = mul nsw i32 %mul.lcssa5, %mul.lcssa5
+ %mul.1 = mul nsw i32 %mul, %mul
+ %mul.2 = mul nsw i32 %mul.1, %mul.1
+ %mul.3 = mul nsw i32 %mul.2, %mul.2
+ %mul.4 = mul nsw i32 %mul.3, %mul.3
+ %mul.5 = mul nsw i32 %mul.4, %mul.4
+ %inc5 = add nsw i32 %i.03, 1
+ %cmp = icmp slt i32 %inc5, 10
+ br i1 %cmp, label %for.cond1.preheader, label %for.end6
+
+for.end6: ; preds = %for.body3
+ %mul.lcssa.lcssa = phi i32 [ %mul.5, %for.body3 ]
+ %inc.lcssa.lcssa = phi i32 [ 6, %for.body3 ]
+ store i32 %mul.lcssa.lcssa, i32* @a, align 4
+ store i32 %inc.lcssa.lcssa, i32* @b, align 4
+ ret i32 0
+}
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D25794.75216.patch
Type: text/x-patch
Size: 3244 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20161019/4a0b06a0/attachment.bin>
More information about the llvm-commits
mailing list