From 9a6c6a373629fb5a3cc5afd08aafa51339df95df Mon Sep 17 00:00:00 2001 From: Nadav Rotem Date: Mon, 7 Jan 2013 21:54:51 +0000 Subject: [PATCH] LoopVectorizer: When we vectorizer and widen loops we process many elements at once. This is a good thing, except for small loops. On small loops post-loop that handles scalars (and runs slower) can take more time to execute than the rest of the loop. This patch disables widening of loops with a small static trip count. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@171798 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Transforms/Vectorize/LoopVectorize.cpp | 18 +++++-- .../LoopVectorize/X86/unroll-small-loops.ll | 50 +++++++++++++++++++ 2 files changed, 65 insertions(+), 3 deletions(-) create mode 100644 test/Transforms/LoopVectorize/X86/unroll-small-loops.ll diff --git a/lib/Transforms/Vectorize/LoopVectorize.cpp b/lib/Transforms/Vectorize/LoopVectorize.cpp index 2c1af1d8d23..b266d9dc09a 100644 --- a/lib/Transforms/Vectorize/LoopVectorize.cpp +++ b/lib/Transforms/Vectorize/LoopVectorize.cpp @@ -101,7 +101,13 @@ EnableIfConversion("enable-if-conversion", cl::init(true), cl::Hidden, cl::desc("Enable if-conversion during vectorization.")); /// We don't vectorize loops with a known constant trip count below this number. -static const unsigned TinyTripCountThreshold = 16; +static const unsigned TinyTripCountVectorThreshold = 16; + +/// We don't unroll loops with a known constant trip count below this number. +static const unsigned TinyTripCountUnrollThreshold = 128; + +/// We don't unroll loops that are larget than this threshold. +static const unsigned MaxLoopSizeThreshold = 32; /// When performing a runtime memory check, do not check more than this /// number of pointers. Notice that the check is quadratic! @@ -2016,7 +2022,7 @@ bool LoopVectorizationLegality::canVectorize() { // Do not loop-vectorize loops with a tiny trip count. unsigned TC = SE->getSmallConstantTripCount(TheLoop, Latch); - if (TC > 0u && TC < TinyTripCountThreshold) { + if (TC > 0u && TC < TinyTripCountVectorThreshold) { DEBUG(dbgs() << "LV: Found a loop with a very small trip count. " << "This loop is not worth vectorizing.\n"); return false; @@ -2678,6 +2684,12 @@ LoopVectorizationCostModel::selectUnrollFactor(bool OptForSize, if (OptForSize) return 1; + // Do not unroll loops with a relatively small trip count. + unsigned TC = SE->getSmallConstantTripCount(TheLoop, + TheLoop->getLoopLatch()); + if (TC > 1 && TC < TinyTripCountUnrollThreshold) + return 1; + unsigned TargetVectorRegisters = TTI.getNumberOfRegisters(true); DEBUG(dbgs() << "LV: The target has " << TargetVectorRegisters << " vector registers\n"); @@ -2698,7 +2710,7 @@ LoopVectorizationCostModel::selectUnrollFactor(bool OptForSize, // We don't want to unroll the loops to the point where they do not fit into // the decoded cache. Assume that we only allow 32 IR instructions. - UF = std::min(UF, (32 / R.NumInstructions)); + UF = std::min(UF, (MaxLoopSizeThreshold / R.NumInstructions)); // Clamp the unroll factor ranges to reasonable factors. if (UF > MaxUnrollSize) diff --git a/test/Transforms/LoopVectorize/X86/unroll-small-loops.ll b/test/Transforms/LoopVectorize/X86/unroll-small-loops.ll new file mode 100644 index 00000000000..207598636c1 --- /dev/null +++ b/test/Transforms/LoopVectorize/X86/unroll-small-loops.ll @@ -0,0 +1,50 @@ +; RUN: opt < %s -loop-vectorize -mtriple=x86_64-apple-macosx10.8.0 -mcpu=corei7-avx2 -force-vector-width=4 -force-vector-unroll=0 -dce -S | FileCheck %s + +target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128-n8:16:32:64-S128" +target triple = "x86_64-apple-macosx10.8.0" +;CHECK: @foo +;CHECK: load <4 x i32> +;CHECK-NOT: load <4 x i32> +;CHECK: store <4 x i32> +;CHECK-NOT: store <4 x i32> +;CHECK: ret +define i32 @foo(i32* nocapture %A) nounwind uwtable ssp { + br label %1 + +;