]> granicus.if.org Git - llvm/commitdiff
[Attributor][Fix] Deal with "growing" dereferenceability
authorJohannes Doerfert <jdoerfert@anl.gov>
Fri, 23 Aug 2019 15:45:46 +0000 (15:45 +0000)
committerJohannes Doerfert <jdoerfert@anl.gov>
Fri, 23 Aug 2019 15:45:46 +0000 (15:45 +0000)
Summary:
If we have a negative inbounds offset dereferenceabily "grows". However,
until we do not handle the overflow that can occur in the
dereferenceable bytes and the problem with loops, we simply do not grow
the state.

Reviewers: sstefan1, uenoku

Subscribers: hiraditya, bollu, llvm-commits

Tags: #llvm

Differential Revision: https://reviews.llvm.org/D66557

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@369771 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Transforms/IPO/Attributor.cpp
test/Transforms/FunctionAttrs/dereferenceable.ll

index ea897d7e3610bb9da2bc31105a0157459a141441..e518994f1532d4c2af4f8260fca2ee8c1543e4bf 100644 (file)
@@ -1985,6 +1985,12 @@ struct AADereferenceableFloating : AADereferenceableImpl {
         T.GlobalState &= DS.GlobalState;
       }
 
+      // For now we do not try to "increase" dereferenceability due to negative
+      // indices as we first have to come up with code to deal with loops and
+      // for overflows of the dereferenceable bytes.
+      if (Offset.getSExtValue() < 0)
+        Offset = 0;
+
       T.takeAssumedDerefBytesMinimum(
           std::max(int64_t(0), DerefBytes - Offset.getSExtValue()));
 
index f75f9203e846fbc13c0112abdcc8964466ba8392..f61b62e9e2390d8c6ab7f315b443dbccfbfe41d0 100644 (file)
@@ -50,3 +50,33 @@ define dereferenceable(4) i32* @test4(i32* dereferenceable(8) %0) local_unnamed_
   ret i32* %0
 }
 
+; TEST 5
+; loop in which dereferenceabily "grows"
+declare void @deref_phi_user(i32* %a);
+define void @deref_phi(i32* dereferenceable(4000) %a) {
+entry:
+  br label %for.cond
+
+for.cond:                                         ; preds = %for.inc, %entry
+  %i.0 = phi i32 [ 0, %entry ], [ %inc, %for.inc ]
+  %a.addr.0 = phi i32* [ %a, %entry ], [ %incdec.ptr, %for.inc ]
+; CHECK: call void @deref_phi_user(i32* dereferenceable(4000) %a.addr.0)
+  call void @deref_phi_user(i32* %a.addr.0)
+  %tmp = load i32, i32* %a.addr.0, align 4
+  %cmp = icmp slt i32 %i.0, %tmp
+  br i1 %cmp, label %for.body, label %for.cond.cleanup
+
+for.cond.cleanup:                                 ; preds = %for.cond
+  br label %for.end
+
+for.body:                                         ; preds = %for.cond
+  br label %for.inc
+
+for.inc:                                          ; preds = %for.body
+  %incdec.ptr = getelementptr inbounds i32, i32* %a.addr.0, i64 -1
+  %inc = add nuw nsw i32 %i.0, 1
+  br label %for.cond
+
+for.end:                                          ; preds = %for.cond.cleanup
+  ret void
+}