mirror of
https://github.com/RPCSX/llvm.git
synced 2025-01-22 20:26:31 +00:00
Revert r246232 and r246304.
This reverts isSafeToSpeculativelyExecute's use of ReadNone until we split ReadNone into two pieces: one attribute which reasons about how the function reasons about memory and another attribute which determines how it may be speculated, CSE'd, trap, etc. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@246331 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
df2dbd7b15
commit
c13175f52f
@ -3147,11 +3147,46 @@ bool llvm::isSafeToSpeculativelyExecute(const Value *V,
|
||||
LI->getPointerOperand(), LI->getAlignment(), DL, CtxI, DT, TLI);
|
||||
}
|
||||
case Instruction::Call: {
|
||||
auto *CI = cast<CallInst>(Inst);
|
||||
if (CI->doesNotAccessMemory() && !CI->isMustTailCall())
|
||||
return true;
|
||||
if (const IntrinsicInst *II = dyn_cast<IntrinsicInst>(Inst)) {
|
||||
switch (II->getIntrinsicID()) {
|
||||
// These synthetic intrinsics have no side-effects and just mark
|
||||
// information about their operands.
|
||||
// FIXME: There are other no-op synthetic instructions that potentially
|
||||
// should be considered at least *safe* to speculate...
|
||||
case Intrinsic::dbg_declare:
|
||||
case Intrinsic::dbg_value:
|
||||
return true;
|
||||
|
||||
case Intrinsic::bswap:
|
||||
case Intrinsic::ctlz:
|
||||
case Intrinsic::ctpop:
|
||||
case Intrinsic::cttz:
|
||||
case Intrinsic::objectsize:
|
||||
case Intrinsic::sadd_with_overflow:
|
||||
case Intrinsic::smul_with_overflow:
|
||||
case Intrinsic::ssub_with_overflow:
|
||||
case Intrinsic::uadd_with_overflow:
|
||||
case Intrinsic::umul_with_overflow:
|
||||
case Intrinsic::usub_with_overflow:
|
||||
return true;
|
||||
// Sqrt should be OK, since the llvm sqrt intrinsic isn't defined to set
|
||||
// errno like libm sqrt would.
|
||||
case Intrinsic::sqrt:
|
||||
case Intrinsic::fma:
|
||||
case Intrinsic::fmuladd:
|
||||
case Intrinsic::fabs:
|
||||
case Intrinsic::minnum:
|
||||
case Intrinsic::maxnum:
|
||||
return true;
|
||||
// TODO: some fp intrinsics are marked as having the same error handling
|
||||
// as libm. They're safe to speculate when they won't error.
|
||||
// TODO: are convert_{from,to}_fp16 safe?
|
||||
// TODO: can we list target-specific intrinsics here?
|
||||
default: break;
|
||||
}
|
||||
}
|
||||
return false; // The called function could have undefined behavior or
|
||||
// side-effects.
|
||||
// side-effects, even if marked readnone nounwind.
|
||||
}
|
||||
case Instruction::VAArg:
|
||||
case Instruction::Alloca:
|
||||
|
@ -506,16 +506,18 @@ bool llvm::isInTailCallPosition(ImmutableCallSite CS, const TargetMachine &TM) {
|
||||
|
||||
// If I will have a chain, make sure no other instruction that will have a
|
||||
// chain interposes between I and the return.
|
||||
for (BasicBlock::const_iterator BBI = std::prev(ExitBB->end(), 2);; --BBI) {
|
||||
if (&*BBI == I)
|
||||
break;
|
||||
// Debug info intrinsics do not get in the way of tail call optimization.
|
||||
if (isa<DbgInfoIntrinsic>(BBI))
|
||||
continue;
|
||||
if (BBI->mayHaveSideEffects() || BBI->mayReadFromMemory() ||
|
||||
!isSafeToSpeculativelyExecute(BBI))
|
||||
return false;
|
||||
}
|
||||
if (I->mayHaveSideEffects() || I->mayReadFromMemory() ||
|
||||
!isSafeToSpeculativelyExecute(I))
|
||||
for (BasicBlock::const_iterator BBI = std::prev(ExitBB->end(), 2);; --BBI) {
|
||||
if (&*BBI == I)
|
||||
break;
|
||||
// Debug info intrinsics do not get in the way of tail call optimization.
|
||||
if (isa<DbgInfoIntrinsic>(BBI))
|
||||
continue;
|
||||
if (BBI->mayHaveSideEffects() || BBI->mayReadFromMemory() ||
|
||||
!isSafeToSpeculativelyExecute(BBI))
|
||||
return false;
|
||||
}
|
||||
|
||||
const Function *F = ExitBB->getParent();
|
||||
return returnTypeIsEligibleForTailCall(
|
||||
|
@ -6,7 +6,6 @@ declare float @llvm.fmuladd.f32(float, float, float) nounwind readonly
|
||||
declare float @llvm.fabs.f32(float) nounwind readonly
|
||||
declare float @llvm.minnum.f32(float, float) nounwind readonly
|
||||
declare float @llvm.maxnum.f32(float, float) nounwind readonly
|
||||
declare float @llvm.copysign.f32(float, float) nounwind readonly
|
||||
|
||||
; CHECK-LABEL: @sqrt_test(
|
||||
; CHECK: select
|
||||
@ -109,20 +108,3 @@ test_maxnum.exit: ; preds = %cond.else.i, %ent
|
||||
store float %cond.i, float addrspace(1)* %out, align 4
|
||||
ret void
|
||||
}
|
||||
|
||||
; CHECK-LABEL: @copysign_test(
|
||||
; CHECK: select
|
||||
define void @copysign_test(float addrspace(1)* noalias nocapture %out, float %a, float %b) nounwind {
|
||||
entry:
|
||||
%cmp.i = fcmp olt float %a, 0.000000e+00
|
||||
br i1 %cmp.i, label %test_copysign.exit, label %cond.else.i
|
||||
|
||||
cond.else.i: ; preds = %entry
|
||||
%0 = tail call float @llvm.copysign.f32(float %a, float %b) nounwind readnone
|
||||
br label %test_copysign.exit
|
||||
|
||||
test_copysign.exit: ; preds = %cond.else.i, %entry
|
||||
%cond.i = phi float [ %0, %cond.else.i ], [ 0x7FF8000000000000, %entry ]
|
||||
store float %cond.i, float addrspace(1)* %out, align 4
|
||||
ret void
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user