summaryrefslogtreecommitdiffstats
path: root/polly
diff options
context:
space:
mode:
Diffstat (limited to 'polly')
-rw-r--r--polly/lib/Support/SCEVAffinator.cpp4
-rw-r--r--polly/lib/Support/SCEVValidator.cpp4
-rw-r--r--polly/lib/Support/ScopHelper.cpp29
-rw-r--r--polly/test/Isl/CodeGen/inner_scev_sdiv_2.ll5
-rw-r--r--polly/test/Isl/CodeGen/ptrtoint_as_parameter.ll34
-rw-r--r--polly/test/ScopInfo/int2ptr_ptr2int.ll71
-rw-r--r--polly/test/ScopInfo/int2ptr_ptr2int_2.ll72
7 files changed, 210 insertions, 9 deletions
diff --git a/polly/lib/Support/SCEVAffinator.cpp b/polly/lib/Support/SCEVAffinator.cpp
index bff074761e0..347c12f60fd 100644
--- a/polly/lib/Support/SCEVAffinator.cpp
+++ b/polly/lib/Support/SCEVAffinator.cpp
@@ -565,6 +565,10 @@ __isl_give PWACtx SCEVAffinator::visitSRemInstruction(Instruction *SRem) {
__isl_give PWACtx SCEVAffinator::visitUnknown(const SCEVUnknown *Expr) {
if (Instruction *I = dyn_cast<Instruction>(Expr->getValue())) {
switch (I->getOpcode()) {
+ case Instruction::IntToPtr:
+ return visit(SE.getSCEVAtScope(I->getOperand(0), getScope()));
+ case Instruction::PtrToInt:
+ return visit(SE.getSCEVAtScope(I->getOperand(0), getScope()));
case Instruction::SDiv:
return visitSDivInstruction(I);
case Instruction::SRem:
diff --git a/polly/lib/Support/SCEVValidator.cpp b/polly/lib/Support/SCEVValidator.cpp
index 85bf815a21d..4b8516338e6 100644
--- a/polly/lib/Support/SCEVValidator.cpp
+++ b/polly/lib/Support/SCEVValidator.cpp
@@ -368,6 +368,10 @@ public:
if (Instruction *I = dyn_cast<Instruction>(Expr->getValue())) {
switch (I->getOpcode()) {
+ case Instruction::IntToPtr:
+ return visit(SE.getSCEVAtScope(I->getOperand(0), Scope));
+ case Instruction::PtrToInt:
+ return visit(SE.getSCEVAtScope(I->getOperand(0), Scope));
case Instruction::Load:
return visitLoadInstruction(I, Expr);
case Instruction::SDiv:
diff --git a/polly/lib/Support/ScopHelper.cpp b/polly/lib/Support/ScopHelper.cpp
index 8e7fb1edfff..d2c544d098d 100644
--- a/polly/lib/Support/ScopHelper.cpp
+++ b/polly/lib/Support/ScopHelper.cpp
@@ -246,6 +246,27 @@ private:
const Region &R;
ValueMapT *VMap;
+ const SCEV *visitGenericInst(const SCEVUnknown *E, Instruction *Inst,
+ Instruction *IP) {
+ if (!Inst || !R.contains(Inst))
+ return E;
+
+ assert(!Inst->mayThrow() && !Inst->mayReadOrWriteMemory() &&
+ !isa<PHINode>(Inst));
+
+ auto *InstClone = Inst->clone();
+ for (auto &Op : Inst->operands()) {
+ assert(SE.isSCEVable(Op->getType()));
+ auto *OpSCEV = SE.getSCEV(Op);
+ auto *OpClone = expandCodeFor(OpSCEV, Op->getType(), IP);
+ InstClone->replaceUsesOfWith(Op, OpClone);
+ }
+
+ InstClone->setName(Name + Inst->getName());
+ InstClone->insertBefore(IP);
+ return SE.getSCEV(InstClone);
+ }
+
const SCEV *visitUnknown(const SCEVUnknown *E) {
// If a value mapping was given try if the underlying value is remapped.
@@ -259,15 +280,11 @@ private:
return visit(NewE);
}
+ Instruction *StartIP = R.getEnteringBlock()->getTerminator();
Instruction *Inst = dyn_cast<Instruction>(E->getValue());
if (!Inst || (Inst->getOpcode() != Instruction::SRem &&
Inst->getOpcode() != Instruction::SDiv))
- return E;
-
- if (!R.contains(Inst))
- return E;
-
- Instruction *StartIP = R.getEnteringBlock()->getTerminator();
+ return visitGenericInst(E, Inst, StartIP);
const SCEV *LHSScev = SE.getSCEV(Inst->getOperand(0));
const SCEV *RHSScev = SE.getSCEV(Inst->getOperand(1));
diff --git a/polly/test/Isl/CodeGen/inner_scev_sdiv_2.ll b/polly/test/Isl/CodeGen/inner_scev_sdiv_2.ll
index b98846a469e..9b925443300 100644
--- a/polly/test/Isl/CodeGen/inner_scev_sdiv_2.ll
+++ b/polly/test/Isl/CodeGen/inner_scev_sdiv_2.ll
@@ -3,10 +3,9 @@
; The SCEV expression in this test case refers to a sequence of sdiv
; instructions, which are part of different bbs in the SCoP. When code
; generating the parameter expressions, the code that is generated by the SCEV
-; expander has still references to the in-scop instructions, which is invalid.
+; expander has still references to the in-scop instructions, which was invalid.
;
-; CHECK: polly.split_new_and_old:
-; CHECK-NOT: = sdiv i64 0, -4
+; CHECK: polly.start
;
target triple = "x86_64-unknown-linux-gnu"
diff --git a/polly/test/Isl/CodeGen/ptrtoint_as_parameter.ll b/polly/test/Isl/CodeGen/ptrtoint_as_parameter.ll
new file mode 100644
index 00000000000..1bbb9dd27ff
--- /dev/null
+++ b/polly/test/Isl/CodeGen/ptrtoint_as_parameter.ll
@@ -0,0 +1,34 @@
+; RUN: opt %loadPolly -polly-codegen -S < %s | FileCheck %s
+;
+; CHECK: polly.split_new_and_old:
+; CHECK-NEXT: %pollysub.ptr.lhs.cast263 = ptrtoint i8* inttoptr (i64 1 to i8*) to i64
+;
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+
+; Function Attrs: nounwind uwtable
+define void @XS_MIME__QuotedPrint_encode_qp() {
+entry:
+ %Perl_sv_len = alloca i64, align 8
+ br label %if.end
+
+if.end: ; preds = %entry
+ br label %while.cond
+
+while.cond: ; preds = %cond.true270, %if.then260, %if.end
+ %p.0 = phi i8* [ null, %if.end ], [ %p.4, %if.then260 ], [ %p.4, %cond.true270 ]
+ br i1 undef, label %if.then260, label %while.body210
+
+while.body210: ; preds = %while.cond
+ unreachable
+
+if.then260: ; preds = %while.cond
+ %p.4 = getelementptr inbounds i8, i8* null, i64 1
+ %sub.ptr.lhs.cast263 = ptrtoint i8* %p.4 to i64
+ %sub.ptr.sub265 = sub i64 %sub.ptr.lhs.cast263, 0
+ %div = udiv i64 0, %sub.ptr.sub265
+ %cmp268 = icmp ult i64 0, %div
+ br i1 %cmp268, label %cond.true270, label %while.cond
+
+cond.true270: ; preds = %if.then260
+ br label %while.cond
+}
diff --git a/polly/test/ScopInfo/int2ptr_ptr2int.ll b/polly/test/ScopInfo/int2ptr_ptr2int.ll
new file mode 100644
index 00000000000..0979ebaebba
--- /dev/null
+++ b/polly/test/ScopInfo/int2ptr_ptr2int.ll
@@ -0,0 +1,71 @@
+; RUN: opt %loadPolly -analyze -polly-scops < %s | FileCheck %s
+; RUN: opt %loadPolly -S -polly-codegen < %s | FileCheck %s --check-prefix=IR
+;
+; void f(long *A, long *ptr, long val) {
+; for (long i = 0; i < 100; i++) {
+; long ptrV = ((long)(ptr + 1)) + 1;
+; long valP = (long)(((long *)(val + 1)) + 1);
+; A[ptrV] += A[valP];
+; }
+; }
+;
+; CHECK: ReadAccess := [Reduction Type: NONE] [Scalar: 0]
+; CHECK-NEXT: [val, ptr] -> { Stmt_for_body[i0] -> MemRef_A[9 + val] };
+; CHECK-NEXT: ReadAccess := [Reduction Type: +] [Scalar: 0]
+; CHECK-NEXT: [val, ptr] -> { Stmt_for_body[i0] -> MemRef_A[9 + ptr] };
+; CHECK-NEXT: MustWriteAccess := [Reduction Type: +] [Scalar: 0]
+; CHECK-NEXT: [val, ptr] -> { Stmt_for_body[i0] -> MemRef_A[9 + ptr] };
+;
+; IR: polly.stmt.for.body:
+; IR-NEXT: %p_tmp = ptrtoint i64* %scevgep to i64
+; IR-NEXT: %p_add = add nsw i64 %p_tmp, 1
+; IR-NEXT: %p_tmp1 = inttoptr i64 %10 to i64*
+; IR-NEXT: %p_add.ptr2 = getelementptr inbounds i64, i64* %p_tmp1, i64 1
+; IR-NEXT: %p_tmp2 = ptrtoint i64* %p_add.ptr2 to i64
+; IR-NEXT: %p_arrayidx = getelementptr inbounds i64, i64* %A, i64 %p_tmp2
+; IR-NEXT: %tmp3_p_scalar_ = load i64, i64* %p_arrayidx
+; IR-NEXT: %p_arrayidx3 = getelementptr inbounds i64, i64* %A, i64 %p_add
+; IR-NEXT: %tmp4_p_scalar_ = load i64, i64* %p_arrayidx3
+; IR-NEXT: %p_add4 = add nsw i64 %tmp4_p_scalar_, %tmp3_p_scalar_
+; IR-NEXT: store i64 %p_add4, i64* %p_arrayidx3
+;
+; IR: polly.loop_preheader:
+; IR-NEXT: %scevgep = getelementptr i64, i64* %ptr, i64 1
+; IR-NEXT: %10 = add i64 %val, 1
+; IR-NEXT: br label %polly.loop_header
+;
+;
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+
+define void @f(i64* %A, i64* %ptr, i64 %val) {
+entry:
+ br label %for.cond
+
+for.cond: ; preds = %for.inc, %entry
+ %i.0 = phi i64 [ 0, %entry ], [ %inc, %for.inc ]
+ %exitcond = icmp ne i64 %i.0, 100
+ br i1 %exitcond, label %for.body, label %for.end
+
+for.body: ; preds = %for.cond
+ %add.ptr = getelementptr inbounds i64, i64* %ptr, i64 1
+ %tmp = ptrtoint i64* %add.ptr to i64
+ %add = add nsw i64 %tmp, 1
+ %add1 = add nsw i64 %val, 1
+ %tmp1 = inttoptr i64 %add1 to i64*
+ %add.ptr2 = getelementptr inbounds i64, i64* %tmp1, i64 1
+ %tmp2 = ptrtoint i64* %add.ptr2 to i64
+ %arrayidx = getelementptr inbounds i64, i64* %A, i64 %tmp2
+ %tmp3 = load i64, i64* %arrayidx
+ %arrayidx3 = getelementptr inbounds i64, i64* %A, i64 %add
+ %tmp4 = load i64, i64* %arrayidx3
+ %add4 = add nsw i64 %tmp4, %tmp3
+ store i64 %add4, i64* %arrayidx3
+ br label %for.inc
+
+for.inc: ; preds = %for.body
+ %inc = add nuw nsw i64 %i.0, 1
+ br label %for.cond
+
+for.end: ; preds = %for.cond
+ ret void
+}
diff --git a/polly/test/ScopInfo/int2ptr_ptr2int_2.ll b/polly/test/ScopInfo/int2ptr_ptr2int_2.ll
new file mode 100644
index 00000000000..e47e181c97b
--- /dev/null
+++ b/polly/test/ScopInfo/int2ptr_ptr2int_2.ll
@@ -0,0 +1,72 @@
+; RUN: opt %loadPolly -analyze -polly-scops < %s | FileCheck %s
+; RUN: opt %loadPolly -S -polly-codegen < %s | FileCheck %s --check-prefix=IR
+;
+; void f(long *A, long *B, long *ptr, long val) {
+; for (long i = 0; i < 100; i++) {
+; long ptrV = ((long)(ptr + 1)) + 1;
+; long valP = (long)(((long *)(val + 1)) + 1);
+; A[ptrV] += B[valP];
+; }
+; }
+;
+; CHECK: ReadAccess := [Reduction Type: NONE] [Scalar: 0]
+; CHECK-NEXT: [val, ptr] -> { Stmt_for_body[i0] -> MemRef_B[9 + val] };
+; CHECK-NEXT: Execution Context: [val, ptr] -> { : val <= 9223372036854775806 }
+;
+; CHECK: ReadAccess := [Reduction Type: +] [Scalar: 0]
+; CHECK-NEXT: [val, ptr] -> { Stmt_for_body[i0] -> MemRef_A[9 + ptr] };
+; CHECK-NEXT: MustWriteAccess := [Reduction Type: +] [Scalar: 0]
+; CHECK-NEXT: [val, ptr] -> { Stmt_for_body[i0] -> MemRef_A[9 + ptr] };
+;
+; IR: polly.stmt.for.body:
+; IR-NEXT: %p_tmp = ptrtoint i64* %scevgep to i64
+; IR-NEXT: %p_add = add nsw i64 %p_tmp, 1
+; IR-NEXT: %p_tmp1 = inttoptr i64 %26 to i64*
+; IR-NEXT: %p_add.ptr2 = getelementptr inbounds i64, i64* %p_tmp1, i64 1
+; IR-NEXT: %p_tmp2 = ptrtoint i64* %p_add.ptr2 to i64
+; IR-NEXT: %p_arrayidx = getelementptr inbounds i64, i64* %B, i64 %p_tmp2
+; IR-NEXT: %p_arrayidx3 = getelementptr inbounds i64, i64* %A, i64 %p_add
+; IR-NEXT: %tmp4_p_scalar_ = load i64, i64* %p_arrayidx3
+; IR-NEXT: %p_add4 = add nsw i64 %tmp4_p_scalar_, %polly.preload.tmp3.merge
+; IR-NEXT: store i64 %p_add4, i64* %p_arrayidx3
+;
+; IR: polly.loop_preheader:
+; IR-NEXT: %scevgep = getelementptr i64, i64* %ptr, i64 1
+; IR-NEXT: %26 = add i64 %val, 1
+; IR-NEXT: br label %polly.loop_header
+;
+;
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+
+define void @f(i64* %A, i64* %B, i64* %ptr, i64 %val) {
+entry:
+ br label %for.cond
+
+for.cond: ; preds = %for.inc, %entry
+ %i.0 = phi i64 [ 0, %entry ], [ %inc, %for.inc ]
+ %exitcond = icmp ne i64 %i.0, 100
+ br i1 %exitcond, label %for.body, label %for.end
+
+for.body: ; preds = %for.cond
+ %add.ptr = getelementptr inbounds i64, i64* %ptr, i64 1
+ %tmp = ptrtoint i64* %add.ptr to i64
+ %add = add nsw i64 %tmp, 1
+ %add1 = add nsw i64 %val, 1
+ %tmp1 = inttoptr i64 %add1 to i64*
+ %add.ptr2 = getelementptr inbounds i64, i64* %tmp1, i64 1
+ %tmp2 = ptrtoint i64* %add.ptr2 to i64
+ %arrayidx = getelementptr inbounds i64, i64* %B, i64 %tmp2
+ %tmp3 = load i64, i64* %arrayidx
+ %arrayidx3 = getelementptr inbounds i64, i64* %A, i64 %add
+ %tmp4 = load i64, i64* %arrayidx3
+ %add4 = add nsw i64 %tmp4, %tmp3
+ store i64 %add4, i64* %arrayidx3
+ br label %for.inc
+
+for.inc: ; preds = %for.body
+ %inc = add nuw nsw i64 %i.0, 1
+ br label %for.cond
+
+for.end: ; preds = %for.cond
+ ret void
+}
OpenPOWER on IntegriCloud