mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-26 04:32:44 +01:00
[LazyValueInfo] Let getEdgeValueLocal look into freeze instructions
This patch makes getEdgeValueLocal more precise when a freeze instruction is given, by adding support for freeze into constantFoldUser Reviewed By: efriedma Differential Revision: https://reviews.llvm.org/D84629
This commit is contained in:
parent
80212c2c9a
commit
6e8034136f
@ -1221,11 +1221,11 @@ static bool usesOperand(User *Usr, Value *Op) {
|
||||
}
|
||||
|
||||
// Return true if the instruction type of Val is supported by
|
||||
// constantFoldUser(). Currently CastInst and BinaryOperator only. Call this
|
||||
// before calling constantFoldUser() to find out if it's even worth attempting
|
||||
// to call it.
|
||||
// constantFoldUser(). Currently CastInst, BinaryOperator and FreezeInst only.
|
||||
// Call this before calling constantFoldUser() to find out if it's even worth
|
||||
// attempting to call it.
|
||||
static bool isOperationFoldable(User *Usr) {
|
||||
return isa<CastInst>(Usr) || isa<BinaryOperator>(Usr);
|
||||
return isa<CastInst>(Usr) || isa<BinaryOperator>(Usr) || isa<FreezeInst>(Usr);
|
||||
}
|
||||
|
||||
// Check if Usr can be simplified to an integer constant when the value of one
|
||||
@ -1256,6 +1256,9 @@ static ValueLatticeElement constantFoldUser(User *Usr, Value *Op,
|
||||
SimplifyBinOp(BO->getOpcode(), LHS, RHS, DL))) {
|
||||
return ValueLatticeElement::getRange(ConstantRange(C->getValue()));
|
||||
}
|
||||
} else if (auto *FI = dyn_cast<FreezeInst>(Usr)) {
|
||||
assert(FI->getOperand(0) == Op && "Operand 0 isn't Op");
|
||||
return ValueLatticeElement::getRange(ConstantRange(OpConstVal));
|
||||
}
|
||||
return ValueLatticeElement::getOverdefined();
|
||||
}
|
||||
|
@ -9,10 +9,7 @@ declare void @f3()
|
||||
define i32 @simple(i1 %cond) {
|
||||
; CHECK-LABEL: @simple(
|
||||
; CHECK-NEXT: ENTRY:
|
||||
; CHECK-NEXT: [[COND_FR:%.*]] = freeze i1 [[COND:%.*]]
|
||||
; CHECK-NEXT: br i1 [[COND]], label [[A:%.*]], label [[EXIT:%.*]]
|
||||
; CHECK: A:
|
||||
; CHECK-NEXT: br i1 [[COND_FR]], label [[B:%.*]], label [[EXIT]]
|
||||
; CHECK-NEXT: br i1 [[COND:%.*]], label [[B:%.*]], label [[EXIT:%.*]]
|
||||
; CHECK: B:
|
||||
; CHECK-NEXT: call void @f()
|
||||
; CHECK-NEXT: ret i32 1
|
||||
@ -36,8 +33,8 @@ define void @switch(i32 %cond) {
|
||||
; CHECK-NEXT: ENTRY:
|
||||
; CHECK-NEXT: [[COND_FR:%.*]] = freeze i32 [[COND:%.*]]
|
||||
; CHECK-NEXT: switch i32 [[COND]], label [[DEFAULT:%.*]] [
|
||||
; CHECK-NEXT: i32 0, label [[A:%.*]]
|
||||
; CHECK-NEXT: i32 1, label [[B:%.*]]
|
||||
; CHECK-NEXT: i32 0, label [[A_TAKEN:%.*]]
|
||||
; CHECK-NEXT: i32 1, label [[B_TAKEN:%.*]]
|
||||
; CHECK-NEXT: ]
|
||||
; CHECK: DEFAULT:
|
||||
; CHECK-NEXT: switch i32 [[COND_FR]], label [[PRESERVED1:%.*]] [
|
||||
@ -49,26 +46,12 @@ define void @switch(i32 %cond) {
|
||||
; CHECK: PRESERVED2:
|
||||
; CHECK-NEXT: call void @f2()
|
||||
; CHECK-NEXT: ret void
|
||||
; CHECK: A:
|
||||
; CHECK-NEXT: switch i32 [[COND_FR]], label [[A_NOTTAKEN:%.*]] [
|
||||
; CHECK-NEXT: i32 0, label [[A_TAKEN:%.*]]
|
||||
; CHECK-NEXT: ]
|
||||
; CHECK: A_TAKEN:
|
||||
; CHECK-NEXT: call void @f()
|
||||
; CHECK-NEXT: ret void
|
||||
; CHECK: A_NOTTAKEN:
|
||||
; CHECK-NEXT: call void @f2()
|
||||
; CHECK-NEXT: ret void
|
||||
; CHECK: B:
|
||||
; CHECK-NEXT: switch i32 [[COND_FR]], label [[B_TAKEN:%.*]] [
|
||||
; CHECK-NEXT: i32 0, label [[B_NOTTAKEN:%.*]]
|
||||
; CHECK-NEXT: ]
|
||||
; CHECK: B_TAKEN:
|
||||
; CHECK-NEXT: call void @f()
|
||||
; CHECK-NEXT: ret void
|
||||
; CHECK: B_NOTTAKEN:
|
||||
; CHECK-NEXT: call void @f2()
|
||||
; CHECK-NEXT: ret void
|
||||
;
|
||||
ENTRY:
|
||||
%cond.fr = freeze i32 %cond
|
||||
|
Loading…
Reference in New Issue
Block a user