[Sink] Fix predicate in legality check

Summary:
isSafeToSpeculativelyExecute is the wrong predicate to use here.
All that checks for is whether it is safe to hoist a value due to
unaligned/un-dereferencable accesses. However, not only are we doing
sinking rather than hoisting, our concern is that the location
we're loading from may have been modified. Instead forbid sinking
any load across a critical edge.

Reviewers: majnemer

Subscribers: davide, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@305102 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Keno Fischer 2017-06-09 19:31:10 +00:00
parent a69f40df77
commit 5d860d251e
2 changed files with 19 additions and 1 deletions

View File

@ -114,7 +114,7 @@ static bool IsAcceptableTarget(Instruction *Inst, BasicBlock *SuccToSinkTo,
if (SuccToSinkTo->getUniquePredecessor() != Inst->getParent()) {
// We cannot sink a load across a critical edge - there may be stores in
// other code paths.
if (!isSafeToSpeculativelyExecute(Inst))
if (isa<LoadInst>(Inst))
return false;
// We don't want to sink across a critical edge if we don't dominate the

View File

@ -0,0 +1,18 @@
; RUN: opt < %s -basicaa -sink -S | FileCheck %s
declare void @foo(i64 *)
define i64 @sinkload(i1 %cmp) {
; CHECK-LABEL: @sinkload
top:
%a = alloca i64
; CHECK: call void @foo(i64* %a)
; CHECK-NEXT: %x = load i64, i64* %a
call void @foo(i64* %a)
%x = load i64, i64* %a
br i1 %cmp, label %A, label %B
A:
store i64 0, i64 *%a
br label %B
B:
; CHECK-NOT: load i64, i64 *%a
ret i64 %x
}