diff --git a/polly/include/polly/CodeGen/BlockGenerators.h b/polly/include/polly/CodeGen/BlockGenerators.h index 0e6d0cbdcdb1..d8f21d53d9a3 100644 --- a/polly/include/polly/CodeGen/BlockGenerators.h +++ b/polly/include/polly/CodeGen/BlockGenerators.h @@ -103,10 +103,11 @@ protected: /// @brief Get the new version of a value. /// /// Given an old value, we first check if a new version of this value is - /// available in the BBMap or GlobalMap. If the value is scop constant, we - /// assume it is a parameter and return the old value. In case it is not and - /// the value can be recomputed using SCEV, we do so. If the value can still - /// not be derived, this function will assert. + /// available in the BBMap or GlobalMap. In case it is not and the value can + /// be recomputed using SCEV, we do so. If we can not recompute a value + /// using SCEV, but we understand that the value is constant within the scop, + /// we return the old value. If the value can still not be derived, this + /// function will assert. /// /// @param Old The old Value. /// @param BBMap A mapping from old values to their new values diff --git a/polly/lib/CodeGen/BlockGenerators.cpp b/polly/lib/CodeGen/BlockGenerators.cpp index 8d1734c39485..8788151dccea 100644 --- a/polly/lib/CodeGen/BlockGenerators.cpp +++ b/polly/lib/CodeGen/BlockGenerators.cpp @@ -88,15 +88,6 @@ Value *BlockGenerator::getNewValue(const Value *Old, ValueMapT &BBMap, return New; } - // Or it is probably a scop-constant value defined as global, function - // parameter or an instruction not within the scop. - if (isa(Old) || isa(Old)) - return const_cast(Old); - - if (const Instruction *Inst = dyn_cast(Old)) - if (!Statement.getParent()->getRegion().contains(Inst->getParent())) - return const_cast(Old); - if (Value *New = BBMap.lookup(Old)) return New; @@ -117,8 +108,16 @@ Value *BlockGenerator::getNewValue(const Value *Old, ValueMapT &BBMap, } } - // Now the scalar dependence is neither available nor SCEVCodegenable, this - // should never happen in the current code generator. + // A scop-constant value defined by a global or a function parameter. + if (isa(Old) || isa(Old)) + return const_cast(Old); + + // A scop-constant value defined by an instruction executed outside the scop. + if (const Instruction *Inst = dyn_cast(Old)) + if (!Statement.getParent()->getRegion().contains(Inst->getParent())) + return const_cast(Old); + + // The scalar dependence is neither available nor SCEVCodegenable. llvm_unreachable("Unexpected scalar dependence in region!"); return nullptr; } diff --git a/polly/test/Isl/CodeGen/scalar-references-used-in-scop-compute.ll b/polly/test/Isl/CodeGen/scalar-references-used-in-scop-compute.ll new file mode 100644 index 000000000000..3ab7529c03f7 --- /dev/null +++ b/polly/test/Isl/CodeGen/scalar-references-used-in-scop-compute.ll @@ -0,0 +1,51 @@ +; RUN: opt %loadPolly -polly-codegen-isl -S -polly-codegen-scev < %s | FileCheck %s + +; Test the code generation in the presence of a scalar out-of-scop value being +; used from within the SCoP. + +; CHECH-LABEL: @scalar-function-argument +; CHECK: polly.split_new_and_old + + +target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +define void @scalar-function-argument(float* %A, float %sqrinv) { +entry: + br label %for.body + +for.body: + %indvar = phi i64 [ %indvar.next, %for.body ], [ 0, %entry ] + %mul104 = fmul float 1.0, %sqrinv + %rp107 = getelementptr float* %A, i64 %indvar + store float %mul104, float* %rp107, align 4 + %indvar.next = add nsw i64 %indvar, 1 + %cmp = icmp slt i64 1024, %indvar.next + br i1 %cmp, label %for.end, label %for.body + +for.end: + ret void +} + +; CHECH-LABEL: @scalar-outside-of-scop +; CHECK: polly.split_new_and_old + +define void @scalar-outside-of-scop(float* %A) { +entry: + %sqrinv = call float @getFloat() + br label %for.body + +for.body: + %indvar = phi i64 [ %indvar.next, %for.body ], [ 0, %entry ] + %mul104 = fmul float 1.0, %sqrinv + %rp107 = getelementptr float* %A, i64 %indvar + store float %mul104, float* %rp107, align 4 + %indvar.next = add nsw i64 %indvar, 1 + %cmp = icmp slt i64 1024, %indvar.next + br i1 %cmp, label %for.end, label %for.body + +for.end: + ret void +} + +declare float @getFloat()