[PATCH] D84629: [LazyValueInfo] Let getEdgeValueLocal look into freeze instructions

Juneyoung Lee via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Mon Jul 27 03:19:46 PDT 2020


aqjune created this revision.
aqjune added reviewers: fhahn, nikic, efriedma.
Herald added subscribers: llvm-commits, hiraditya.
Herald added a project: LLVM.

This patch makes getEdgeValueLocal more precise when a freeze instruction is
given, by

- Exploting the fact that a branch condition cannot be undef or poison
- Adding support for freeze into constantFoldUser


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D84629

Files:
  llvm/lib/Analysis/LazyValueInfo.cpp
  llvm/test/Transforms/JumpThreading/freeze-lvi-edgevaluelocal.ll


Index: llvm/test/Transforms/JumpThreading/freeze-lvi-edgevaluelocal.ll
===================================================================
--- llvm/test/Transforms/JumpThreading/freeze-lvi-edgevaluelocal.ll
+++ llvm/test/Transforms/JumpThreading/freeze-lvi-edgevaluelocal.ll
@@ -9,10 +9,7 @@
 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 @@
 ; 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 @@
 ; 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
Index: llvm/lib/Analysis/LazyValueInfo.cpp
===================================================================
--- llvm/lib/Analysis/LazyValueInfo.cpp
+++ llvm/lib/Analysis/LazyValueInfo.cpp
@@ -1247,11 +1247,11 @@
 }
 
 // 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
@@ -1282,6 +1282,9 @@
             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();
 }
@@ -1306,7 +1309,11 @@
 
       // If V is the condition of the branch itself, then we know exactly what
       // it is.
-      if (Condition == Val)
+      // Since it is used as a branch conditional, Condition cannot be undef
+      // or poison. Exploit this to strip freeze from Val.
+      if (Condition == Val ||
+          (isa<FreezeInst>(Val) &&
+           Condition == cast<FreezeInst>(Val)->getOperand(0)))
         return ValueLatticeElement::get(ConstantInt::get(
                               Type::getInt1Ty(Val->getContext()), isTrueDest));
 


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D84629.280837.patch
Type: text/x-patch
Size: 3892 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20200727/6f683668/attachment.bin>


More information about the llvm-commits mailing list