Skip to content
This repository was archived by the owner on Mar 28, 2020. It is now read-only.

Commit dc27a09

Browse files
committed
[LVI] Refactor to use newly introduced intersect utility
This patch uses the newly introduced 'intersect' utility (from 259461: [LVI] Introduce an intersect operation on lattice values) to simplify existing code in LVI. While not introducing any new concepts, this change is probably not NFC. The common 'intersect' function is more powerful that the ad-hoc implementations we'd had in a couple of places. Given that, we may see optimizations triggering a bit more often. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@259583 91177308-0d34-0410-b5e6-96231b3b80d8
1 parent 4b23ca5 commit dc27a09

File tree

1 file changed

+19
-32
lines changed

1 file changed

+19
-32
lines changed

lib/Analysis/LazyValueInfo.cpp

Lines changed: 19 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -294,6 +294,8 @@ raw_ostream &operator<<(raw_ostream &OS, const LVILatticeVal &Val) {
294294
}
295295
}
296296

297+
static LVILatticeVal intersect(LVILatticeVal A, LVILatticeVal B);
298+
297299
//===----------------------------------------------------------------------===//
298300
// LazyValueInfoCache Decl
299301
//===----------------------------------------------------------------------===//
@@ -395,7 +397,7 @@ namespace {
395397
SelectInst *S, BasicBlock *BB);
396398
bool solveBlockValueConstantRange(LVILatticeVal &BBLV,
397399
Instruction *BBI, BasicBlock *BB);
398-
void mergeAssumeBlockValueConstantRange(Value *Val, LVILatticeVal &BBLV,
400+
void intersectAssumeBlockValueConstantRange(Value *Val, LVILatticeVal &BBLV,
399401
Instruction *BBI);
400402

401403
void solve();
@@ -554,10 +556,8 @@ static LVILatticeVal getFromRangeMetadata(Instruction *BBI) {
554556
}
555557
break;
556558
};
557-
// Nothing known - Note that we do not want overdefined here. We may know
558-
// something else about the value and not having range metadata shouldn't
559-
// cause us to throw away those facts.
560-
return LVILatticeVal();
559+
// Nothing known - will be intersected with other facts
560+
return LVILatticeVal::getOverdefined();
561561
}
562562

563563
bool LazyValueInfoCache::solveBlockValue(Value *Val, BasicBlock *BB) {
@@ -609,9 +609,9 @@ bool LazyValueInfoCache::solveBlockValue(Value *Val, BasicBlock *BB) {
609609
return true;
610610
}
611611

612-
// If this is an instruction which supports range metadata, return the
613-
// implied range. TODO: This should be an intersection, not a union.
614-
Res.mergeIn(getFromRangeMetadata(BBI), DL);
612+
// If this is an instruction which supports range metadata, intersect the
613+
// implied range.
614+
Res = intersect(Res, getFromRangeMetadata(BBI));
615615

616616
// We can only analyze the definitions of certain classes of instructions
617617
// (integral binops and casts at the moment), so bail if this isn't one.
@@ -793,10 +793,9 @@ static bool getValueFromFromCondition(Value *Val, ICmpInst *ICI,
793793
LVILatticeVal &Result,
794794
bool isTrueDest = true);
795795

796-
// If we can determine a constant range for the value Val in the context
797-
// provided by the instruction BBI, then merge it into BBLV. If we did find a
798-
// constant range, return true.
799-
void LazyValueInfoCache::mergeAssumeBlockValueConstantRange(Value *Val,
796+
// If we can determine a constraint on the value given conditions assumed by
797+
// the program, intersect those constraints with BBLV
798+
void LazyValueInfoCache::intersectAssumeBlockValueConstantRange(Value *Val,
800799
LVILatticeVal &BBLV,
801800
Instruction *BBI) {
802801
BBI = BBI ? BBI : dyn_cast<Instruction>(Val);
@@ -813,12 +812,8 @@ void LazyValueInfoCache::mergeAssumeBlockValueConstantRange(Value *Val,
813812
Value *C = I->getArgOperand(0);
814813
if (ICmpInst *ICI = dyn_cast<ICmpInst>(C)) {
815814
LVILatticeVal Result;
816-
if (getValueFromFromCondition(Val, ICI, Result)) {
817-
if (BBLV.isOverdefined())
818-
BBLV = Result;
819-
else
820-
BBLV.mergeIn(Result, DL);
821-
}
815+
if (getValueFromFromCondition(Val, ICI, Result))
816+
BBLV = intersect(BBLV, Result);
822817
}
823818
}
824819
}
@@ -874,7 +869,7 @@ bool LazyValueInfoCache::solveBlockValueConstantRange(LVILatticeVal &BBLV,
874869
}
875870

876871
LVILatticeVal LHSVal = getBlockValue(BBI->getOperand(0), BB);
877-
mergeAssumeBlockValueConstantRange(BBI->getOperand(0), LHSVal, BBI);
872+
intersectAssumeBlockValueConstantRange(BBI->getOperand(0), LHSVal, BBI);
878873
if (!LHSVal.isConstantRange()) {
879874
BBLV.markOverdefined();
880875
return true;
@@ -1141,7 +1136,7 @@ bool LazyValueInfoCache::getEdgeValue(Value *Val, BasicBlock *BBFrom,
11411136

11421137
// Try to intersect ranges of the BB and the constraint on the edge.
11431138
LVILatticeVal InBlock = getBlockValue(Val, BBFrom);
1144-
mergeAssumeBlockValueConstantRange(Val, InBlock, BBFrom->getTerminator());
1139+
intersectAssumeBlockValueConstantRange(Val, InBlock, BBFrom->getTerminator());
11451140
// We can use the context instruction (generically the ultimate instruction
11461141
// the calling pass is trying to simplify) here, even though the result of
11471142
// this function is generally cached when called from the solve* functions
@@ -1150,7 +1145,7 @@ bool LazyValueInfoCache::getEdgeValue(Value *Val, BasicBlock *BBFrom,
11501145
// functions, the context instruction is not provided. When called from
11511146
// LazyValueInfoCache::getValueOnEdge, the context instruction is provided,
11521147
// but then the result is not cached.
1153-
mergeAssumeBlockValueConstantRange(Val, InBlock, CxtI);
1148+
intersectAssumeBlockValueConstantRange(Val, InBlock, CxtI);
11541149

11551150
Result = intersect(LocalResult, InBlock);
11561151
return true;
@@ -1166,7 +1161,7 @@ LVILatticeVal LazyValueInfoCache::getValueInBlock(Value *V, BasicBlock *BB,
11661161

11671162
solve();
11681163
LVILatticeVal Result = getBlockValue(V, BB);
1169-
mergeAssumeBlockValueConstantRange(V, Result, CxtI);
1164+
intersectAssumeBlockValueConstantRange(V, Result, CxtI);
11701165

11711166
DEBUG(dbgs() << " Result = " << Result << "\n");
11721167
return Result;
@@ -1176,18 +1171,10 @@ LVILatticeVal LazyValueInfoCache::getValueAt(Value *V, Instruction *CxtI) {
11761171
DEBUG(dbgs() << "LVI Getting value " << *V << " at '"
11771172
<< CxtI->getName() << "'\n");
11781173

1179-
LVILatticeVal Result;
1174+
LVILatticeVal Result = LVILatticeVal::getOverdefined();
11801175
if (auto *I = dyn_cast<Instruction>(V))
11811176
Result = getFromRangeMetadata(I);
1182-
mergeAssumeBlockValueConstantRange(V, Result, CxtI);
1183-
1184-
// Note: What's actually happening here is that we're starting at overdefined
1185-
// and then intersecting two different types of facts. The code is not
1186-
// structured that way (FIXME), and we need to take particular care to not
1187-
// let the undefined state escape since we have *not* proven the particular
1188-
// value to be unreachable at the context instruction.
1189-
if (Result.isUndefined())
1190-
Result.markOverdefined();
1177+
intersectAssumeBlockValueConstantRange(V, Result, CxtI);
11911178

11921179
DEBUG(dbgs() << " Result = " << Result << "\n");
11931180
return Result;

0 commit comments

Comments
 (0)