OSDN Git Service

[SCCP] Drop unnecessary early exit for ExtractValueInst.
authorFlorian Hahn <florian_hahn@apple.com>
Wed, 22 Apr 2020 21:00:51 +0000 (22:00 +0100)
committerFlorian Hahn <florian_hahn@apple.com>
Wed, 22 Apr 2020 21:07:59 +0000 (22:07 +0100)
visitExtractValueInst uses mergeInValue, so it already can handle
constant ranges. Initially the early exit was using isOverdefined to
keep things as NFC during the initial move to ValueLatticeElement.
As the function already supports constant ranges, it can just use
ValueState[&I].isOverdefined.

Reviewers: efriedma, mssimpso, davide

Reviewed By: efriedma

Differential Revision: https://reviews.llvm.org/D78393

llvm/lib/Transforms/Scalar/SCCP.cpp
llvm/test/Transforms/SCCP/conditions-ranges.ll
llvm/test/Transforms/SCCP/constant-range-struct.ll

index 6d640fe..1b159dd 100644 (file)
@@ -810,16 +810,16 @@ void SCCPSolver::visitCastInst(CastInst &I) {
 }
 
 void SCCPSolver::visitExtractValueInst(ExtractValueInst &EVI) {
-  // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
-  // discover a concrete value later.
-  if (isOverdefined(ValueState[&EVI]))
-    return (void)markOverdefined(&EVI);
-
   // If this returns a struct, mark all elements over defined, we don't track
   // structs in structs.
   if (EVI.getType()->isStructTy())
     return (void)markOverdefined(&EVI);
 
+  // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
+  // discover a concrete value later.
+  if (ValueState[&EVI].isOverdefined())
+    return (void)markOverdefined(&EVI);
+
   // If this is extracting from more than one level of struct, we don't know.
   if (EVI.getNumIndices() != 1)
     return (void)markOverdefined(&EVI);
index 400c49e..baaf8cb 100644 (file)
@@ -989,6 +989,12 @@ define void @f18_conditions_chained_and(i32 %a, i32 %b) {
 ; CHECK-NEXT:    call void @use(i1 [[F_2]])
 ; CHECK-NEXT:    [[F_3:%.*]] = icmp ugt i32 [[A]], 100
 ; CHECK-NEXT:    call void @use(i1 [[F_3]])
+; CHECK-NEXT:    [[F_4:%.*]] = icmp eq i32 [[B]], 0
+; CHECK-NEXT:    call void @use(i1 [[F_3]])
+; CHECK-NEXT:    [[F_5:%.*]] = icmp eq i32 [[B]], 20
+; CHECK-NEXT:    call void @use(i1 [[F_5]])
+; CHECK-NEXT:    [[F_6:%.*]] = icmp ugt i32 [[B]], 100
+; CHECK-NEXT:    call void @use(i1 [[F_6]])
 ; CHECK-NEXT:    [[T_1:%.*]] = icmp ult i32 [[A]], 100
 ; CHECK-NEXT:    call void @use(i1 [[T_1]])
 ; CHECK-NEXT:    [[T_2:%.*]] = icmp ne i32 [[A]], 20
@@ -1001,8 +1007,8 @@ define void @f18_conditions_chained_and(i32 %a, i32 %b) {
 ; CHECK-NEXT:    call void @use(i1 [[C_3]])
 ; CHECK-NEXT:    ret void
 ; CHECK:       false:
-; CHECK-NEXT:    [[F_4:%.*]] = icmp eq i32 [[A]], 50
-; CHECK-NEXT:    call void @use(i1 [[F_4]])
+; CHECK-NEXT:    [[F_7:%.*]] = icmp eq i32 [[A]], 50
+; CHECK-NEXT:    call void @use(i1 [[F_7]])
 ; CHECK-NEXT:    [[T_3:%.*]] = icmp ne i32 [[A]], 50
 ; CHECK-NEXT:    call void @use(i1 [[T_3]])
 ; CHECK-NEXT:    [[C_4:%.*]] = icmp eq i32 [[A]], 10
@@ -1027,6 +1033,13 @@ true: ; %a in [21, 100)
   call void @use(i1 %f.2)
   %f.3 = icmp ugt i32 %a, 100
   call void @use(i1 %f.3)
+  %f.4 = icmp eq i32 %b, 0
+  call void @use(i1 %f.3)
+  %f.5 = icmp eq i32 %b, 20
+  call void @use(i1 %f.5)
+  %f.6 = icmp ugt i32 %b, 100
+  call void @use(i1 %f.6)
+
 
   ; Conditions below are true.
   %t.1 = icmp ult i32 %a, 100
@@ -1045,8 +1058,8 @@ true: ; %a in [21, 100)
 
 false:
   ; Conditions below are false;
-  %f.4 = icmp eq i32 %a, 50
-  call void @use(i1 %f.4)
+  %f.7 = icmp eq i32 %a, 50
+  call void @use(i1 %f.7)
 
   ; Conditions below are true;
   %t.3 = icmp ne i32 %a, 50
index d3c5e55..6a602fe 100644 (file)
@@ -159,6 +159,5 @@ define void @struct2_caller() {
   %c.4 = icmp ugt i64 %v2, 250
   call void @use(i1 %c.4)
 
-
   ret void
 }