forked from OSchip/llvm-project
[ValueTracking,VectorCombine] Allow passing DT to computeConstantRange.
isValidAssumeForContext can provide better results with access to the dominator tree in some cases. This patch adjusts computeConstantRange to allow passing through a dominator tree. The use VectorCombine is updated to pass through the DT to enable additional scalarization. Note that similar APIs like computeKnownBits already accept optional dominator tree arguments. Reviewed By: lebedev.ri Differential Revision: https://reviews.llvm.org/D110175
This commit is contained in:
parent
5fb3ae525f
commit
5131037ea9
|
@ -549,6 +549,7 @@ constexpr unsigned MaxAnalysisRecursionDepth = 6;
|
|||
ConstantRange computeConstantRange(const Value *V, bool UseInstrInfo = true,
|
||||
AssumptionCache *AC = nullptr,
|
||||
const Instruction *CtxI = nullptr,
|
||||
const DominatorTree *DT = nullptr,
|
||||
unsigned Depth = 0);
|
||||
|
||||
/// Return true if this function can prove that the instruction I will
|
||||
|
|
|
@ -7031,6 +7031,7 @@ static void setLimitsForSelectPattern(const SelectInst &SI, APInt &Lower,
|
|||
ConstantRange llvm::computeConstantRange(const Value *V, bool UseInstrInfo,
|
||||
AssumptionCache *AC,
|
||||
const Instruction *CtxI,
|
||||
const DominatorTree *DT,
|
||||
unsigned Depth) {
|
||||
assert(V->getType()->isIntOrIntVectorTy() && "Expected integer instruction");
|
||||
|
||||
|
@ -7069,7 +7070,7 @@ ConstantRange llvm::computeConstantRange(const Value *V, bool UseInstrInfo,
|
|||
assert(I->getCalledFunction()->getIntrinsicID() == Intrinsic::assume &&
|
||||
"must be an assume intrinsic");
|
||||
|
||||
if (!isValidAssumeForContext(I, CtxI, nullptr))
|
||||
if (!isValidAssumeForContext(I, CtxI, DT))
|
||||
continue;
|
||||
Value *Arg = I->getArgOperand(0);
|
||||
ICmpInst *Cmp = dyn_cast<ICmpInst>(Arg);
|
||||
|
@ -7077,7 +7078,7 @@ ConstantRange llvm::computeConstantRange(const Value *V, bool UseInstrInfo,
|
|||
if (!Cmp || Cmp->getOperand(0) != V)
|
||||
continue;
|
||||
ConstantRange RHS = computeConstantRange(Cmp->getOperand(1), UseInstrInfo,
|
||||
AC, I, Depth + 1);
|
||||
AC, I, DT, Depth + 1);
|
||||
CR = CR.intersectWith(
|
||||
ConstantRange::makeAllowedICmpRegion(Cmp->getPredicate(), RHS));
|
||||
}
|
||||
|
|
|
@ -827,7 +827,8 @@ public:
|
|||
/// Idx. \p Idx must access a valid vector element.
|
||||
static ScalarizationResult canScalarizeAccess(FixedVectorType *VecTy,
|
||||
Value *Idx, Instruction *CtxI,
|
||||
AssumptionCache &AC) {
|
||||
AssumptionCache &AC,
|
||||
const DominatorTree &DT) {
|
||||
if (auto *C = dyn_cast<ConstantInt>(Idx)) {
|
||||
if (C->getValue().ult(VecTy->getNumElements()))
|
||||
return ScalarizationResult::safe();
|
||||
|
@ -841,7 +842,7 @@ static ScalarizationResult canScalarizeAccess(FixedVectorType *VecTy,
|
|||
ConstantRange IdxRange(IntWidth, true);
|
||||
|
||||
if (isGuaranteedNotToBePoison(Idx, &AC)) {
|
||||
if (ValidIndices.contains(computeConstantRange(Idx, true, &AC, CtxI, 0)))
|
||||
if (ValidIndices.contains(computeConstantRange(Idx, true, &AC, CtxI, &DT)))
|
||||
return ScalarizationResult::safe();
|
||||
return ScalarizationResult::unsafe();
|
||||
}
|
||||
|
@ -909,7 +910,7 @@ bool VectorCombine::foldSingleElementStore(Instruction &I) {
|
|||
SrcAddr != SI->getPointerOperand()->stripPointerCasts())
|
||||
return false;
|
||||
|
||||
auto ScalarizableIdx = canScalarizeAccess(VecTy, Idx, Load, AC);
|
||||
auto ScalarizableIdx = canScalarizeAccess(VecTy, Idx, Load, AC, DT);
|
||||
if (ScalarizableIdx.isUnsafe() ||
|
||||
isMemModifiedBetween(Load->getIterator(), SI->getIterator(),
|
||||
MemoryLocation::get(SI), AA))
|
||||
|
@ -987,7 +988,7 @@ bool VectorCombine::scalarizeLoadExtract(Instruction &I) {
|
|||
else if (LastCheckedInst->comesBefore(UI))
|
||||
LastCheckedInst = UI;
|
||||
|
||||
auto ScalarIdx = canScalarizeAccess(FixedVT, UI->getOperand(1), &I, AC);
|
||||
auto ScalarIdx = canScalarizeAccess(FixedVT, UI->getOperand(1), &I, AC, DT);
|
||||
if (!ScalarIdx.isSafe()) {
|
||||
// TODO: Freeze index if it is safe to do so.
|
||||
return false;
|
||||
|
|
|
@ -74,8 +74,8 @@ define void @load_extract_insert_store_var_idx_assume_valid_in_dominating_block(
|
|||
; CHECK-NEXT: [[MUL:%.*]] = fmul double 2.000000e+01, [[EXT_0]]
|
||||
; CHECK-NEXT: [[EXT_1:%.*]] = extractelement <225 x double> [[LV]], i64 [[IDX_2]]
|
||||
; CHECK-NEXT: [[SUB:%.*]] = fsub double [[EXT_1]], [[MUL]]
|
||||
; CHECK-NEXT: [[INS:%.*]] = insertelement <225 x double> [[LV]], double [[SUB]], i64 [[IDX_1]]
|
||||
; CHECK-NEXT: store <225 x double> [[INS]], <225 x double>* [[A]], align 8
|
||||
; CHECK-NEXT: [[TMP0:%.*]] = getelementptr inbounds <225 x double>, <225 x double>* [[A]], i64 0, i64 [[IDX_1]]
|
||||
; CHECK-NEXT: store double [[SUB]], double* [[TMP0]], align 8
|
||||
; CHECK-NEXT: [[C_2:%.*]] = call i1 @cond()
|
||||
; CHECK-NEXT: br i1 [[C_2]], label [[LOOP]], label [[EXIT]]
|
||||
; CHECK: exit:
|
||||
|
|
|
@ -114,9 +114,9 @@ define i32 @load_extract_idx_var_i64_known_valid_by_assume_in_dominating_block(<
|
|||
; CHECK-NEXT: call void @llvm.assume(i1 [[CMP]])
|
||||
; CHECK-NEXT: br i1 [[C_1:%.*]], label [[LOOP:%.*]], label [[EXIT:%.*]]
|
||||
; CHECK: loop:
|
||||
; CHECK-NEXT: [[LV:%.*]] = load <4 x i32>, <4 x i32>* [[X:%.*]], align 16
|
||||
; CHECK-NEXT: call void @maythrow()
|
||||
; CHECK-NEXT: [[R:%.*]] = extractelement <4 x i32> [[LV]], i64 [[IDX]]
|
||||
; CHECK-NEXT: [[TMP0:%.*]] = getelementptr inbounds <4 x i32>, <4 x i32>* [[X:%.*]], i32 0, i64 [[IDX]]
|
||||
; CHECK-NEXT: [[R:%.*]] = load i32, i32* [[TMP0]], align 4
|
||||
; CHECK-NEXT: [[C_2:%.*]] = call i1 @cond()
|
||||
; CHECK-NEXT: br i1 [[C_2]], label [[LOOP]], label [[EXIT]]
|
||||
; CHECK: exit:
|
||||
|
|
|
@ -2103,7 +2103,7 @@ TEST_F(ValueTrackingTest, ComputeConstantRange) {
|
|||
|
||||
// Check the depth cutoff results in a conservative result (full set) by
|
||||
// passing Depth == MaxDepth == 6.
|
||||
ConstantRange CR3 = computeConstantRange(X2, true, &AC, I, 6);
|
||||
ConstantRange CR3 = computeConstantRange(X2, true, &AC, I, nullptr, 6);
|
||||
EXPECT_TRUE(CR3.isFullSet());
|
||||
}
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue