Skip to content

Commit 2c29b4a

Browse files
committed
[Loads] Respect UseDerefAtPointSemantics in isDerefAndAlignedPointer.
If a pointer gets freed, it may not be dereferenceable any longer, even though there is a dominating dereferenceable assumption. As first step, only consider assumptions if the function doesn't free memory if UseDerefAtPointSemantics is used.
1 parent 77803e4 commit 2c29b4a

File tree

3 files changed

+23
-7
lines changed

3 files changed

+23
-7
lines changed

llvm/lib/Analysis/Loads.cpp

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,8 @@
2525

2626
using namespace llvm;
2727

28+
extern cl::opt<unsigned> UseDerefAtPointSemantics;
29+
2830
static bool isAligned(const Value *Base, Align Alignment,
2931
const DataLayout &DL) {
3032
return Base->getPointerAlignment(DL) >= Alignment;
@@ -168,7 +170,8 @@ static bool isDereferenceableAndAlignedPointer(
168170
Size, DL, CtxI, AC, DT, TLI,
169171
Visited, MaxDepth);
170172

171-
if (CtxI) {
173+
if (CtxI &&
174+
(!UseDerefAtPointSemantics || CtxI->getFunction()->doesNotFreeMemory())) {
172175
/// Look through assumes to see if both dereferencability and alignment can
173176
/// be proven by an assume if needed.
174177
RetainedKnowledge AlignRK;

llvm/lib/IR/Value.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@
3636

3737
using namespace llvm;
3838

39-
static cl::opt<bool> UseDerefAtPointSemantics(
39+
cl::opt<bool> UseDerefAtPointSemantics(
4040
"use-dereferenceable-at-point-semantics", cl::Hidden, cl::init(false),
4141
cl::desc("Deref attributes and metadata infer facts at definition only"));
4242

llvm/test/Transforms/LoopVectorize/dereferenceable-info-from-assumption-constant-size.ll

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1411,7 +1411,7 @@ exit:
14111411
}
14121412

14131413
; %a may be freeed between the dereferenceable assumption and accesses.
1414-
; FIXME: It is not safe to use with -use-dereferenceable-at-point-semantics.
1414+
; It is not safe to use with -use-dereferenceable-at-point-semantics.
14151415
define void @may_free_align_deref_assumption_in_header_constant_trip_count_loop_invariant_ptr(ptr noalias %a, ptr noalias %b, ptr noalias %c) {
14161416
; CHECK-LABEL: define void @may_free_align_deref_assumption_in_header_constant_trip_count_loop_invariant_ptr(
14171417
; CHECK-SAME: ptr noalias [[A:%.*]], ptr noalias [[B:%.*]], ptr noalias [[C:%.*]]) {
@@ -1422,16 +1422,29 @@ define void @may_free_align_deref_assumption_in_header_constant_trip_count_loop_
14221422
; CHECK: [[VECTOR_PH]]:
14231423
; CHECK-NEXT: br label %[[VECTOR_BODY:.*]]
14241424
; CHECK: [[VECTOR_BODY]]:
1425-
; CHECK-NEXT: [[INDEX:%.*]] = phi i64 [ 0, %[[VECTOR_PH]] ], [ [[INDEX_NEXT:%.*]], %[[VECTOR_BODY]] ]
1425+
; CHECK-NEXT: [[INDEX:%.*]] = phi i64 [ 0, %[[VECTOR_PH]] ], [ [[INDEX_NEXT:%.*]], %[[PRED_LOAD_CONTINUE2:.*]] ]
14261426
; CHECK-NEXT: [[TMP0:%.*]] = add i64 [[INDEX]], 0
14271427
; CHECK-NEXT: [[TMP1:%.*]] = getelementptr inbounds i32, ptr [[B]], i64 [[TMP0]]
14281428
; CHECK-NEXT: [[TMP2:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i32 0
14291429
; CHECK-NEXT: [[WIDE_LOAD:%.*]] = load <2 x i32>, ptr [[TMP2]], align 4
14301430
; CHECK-NEXT: [[TMP3:%.*]] = icmp sge <2 x i32> [[WIDE_LOAD]], zeroinitializer
1431-
; CHECK-NEXT: [[TMP5:%.*]] = load i32, ptr [[A]], align 4
1431+
; CHECK-NEXT: [[TMP4:%.*]] = xor <2 x i1> [[TMP3]], splat (i1 true)
1432+
; CHECK-NEXT: [[TMP5:%.*]] = extractelement <2 x i1> [[TMP4]], i32 0
1433+
; CHECK-NEXT: br i1 [[TMP5]], label %[[PRED_LOAD_IF:.*]], label %[[PRED_LOAD_CONTINUE:.*]]
1434+
; CHECK: [[PRED_LOAD_IF]]:
14321435
; CHECK-NEXT: [[TMP15:%.*]] = load i32, ptr [[A]], align 4
1433-
; CHECK-NEXT: [[TMP13:%.*]] = insertelement <2 x i32> poison, i32 [[TMP5]], i32 0
1434-
; CHECK-NEXT: [[TMP11:%.*]] = insertelement <2 x i32> [[TMP13]], i32 [[TMP15]], i32 1
1436+
; CHECK-NEXT: [[TMP7:%.*]] = insertelement <2 x i32> poison, i32 [[TMP15]], i32 0
1437+
; CHECK-NEXT: br label %[[PRED_LOAD_CONTINUE]]
1438+
; CHECK: [[PRED_LOAD_CONTINUE]]:
1439+
; CHECK-NEXT: [[TMP12:%.*]] = phi <2 x i32> [ poison, %[[VECTOR_BODY]] ], [ [[TMP7]], %[[PRED_LOAD_IF]] ]
1440+
; CHECK-NEXT: [[TMP13:%.*]] = extractelement <2 x i1> [[TMP4]], i32 1
1441+
; CHECK-NEXT: br i1 [[TMP13]], label %[[PRED_LOAD_IF1:.*]], label %[[PRED_LOAD_CONTINUE2]]
1442+
; CHECK: [[PRED_LOAD_IF1]]:
1443+
; CHECK-NEXT: [[TMP14:%.*]] = load i32, ptr [[A]], align 4
1444+
; CHECK-NEXT: [[TMP16:%.*]] = insertelement <2 x i32> [[TMP12]], i32 [[TMP14]], i32 1
1445+
; CHECK-NEXT: br label %[[PRED_LOAD_CONTINUE2]]
1446+
; CHECK: [[PRED_LOAD_CONTINUE2]]:
1447+
; CHECK-NEXT: [[TMP11:%.*]] = phi <2 x i32> [ [[TMP12]], %[[PRED_LOAD_CONTINUE]] ], [ [[TMP16]], %[[PRED_LOAD_IF1]] ]
14351448
; CHECK-NEXT: [[PREDPHI:%.*]] = select <2 x i1> [[TMP3]], <2 x i32> [[WIDE_LOAD]], <2 x i32> [[TMP11]]
14361449
; CHECK-NEXT: [[TMP8:%.*]] = getelementptr inbounds i32, ptr [[C]], i64 [[TMP0]]
14371450
; CHECK-NEXT: [[TMP9:%.*]] = getelementptr inbounds i32, ptr [[TMP8]], i32 0

0 commit comments

Comments
 (0)