[llvm] r305705 - [InstCombine] Cleanup some duplicated one use checks

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Mon Jun 19 09:23:50 PDT 2017


Author: ctopper
Date: Mon Jun 19 11:23:49 2017
New Revision: 305705

URL: http://llvm.org/viewvc/llvm-project?rev=305705&view=rev
Log:
[InstCombine] Cleanup some duplicated one use checks

Summary:
These 4 patterns have the same one use check repeated twice for each. Once without a cast and one with. But the cast has no effect on what method is called.

For the OR case I believe it is always profitable regardless of the number of uses since we'll never increase the instruction count.

For the AND case I believe it is profitable if the pair of xors has one use such that we'll get rid of it completely. Or if the C value is something freely invertible, in which case the not doesn't cost anything.

Reviewers: spatel, majnemer

Reviewed By: spatel

Subscribers: llvm-commits

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

Modified:
    llvm/trunk/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
    llvm/trunk/test/Transforms/InstCombine/or-xor.ll
    llvm/trunk/test/Transforms/InstCombine/xor2.ll

Modified: llvm/trunk/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp?rev=305705&r1=305704&r2=305705&view=diff
==============================================================================
--- llvm/trunk/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp (original)
+++ llvm/trunk/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp Mon Jun 19 11:23:49 2017
@@ -1442,13 +1442,13 @@ Instruction *InstCombiner::visitAnd(Bina
     // (A ^ B) & ((B ^ C) ^ A) -> (A ^ B) & ~C
     if (match(Op0, m_Xor(m_Value(A), m_Value(B))))
       if (match(Op1, m_Xor(m_Xor(m_Specific(B), m_Value(C)), m_Specific(A))))
-        if (Op1->hasOneUse() || cast<BinaryOperator>(Op1)->hasOneUse())
+        if (Op1->hasOneUse() || IsFreeToInvert(C, C->hasOneUse()))
           return BinaryOperator::CreateAnd(Op0, Builder->CreateNot(C));
 
     // ((A ^ C) ^ B) & (B ^ A) -> (B ^ A) & ~C
     if (match(Op0, m_Xor(m_Xor(m_Value(A), m_Value(C)), m_Value(B))))
       if (match(Op1, m_Xor(m_Specific(B), m_Specific(A))))
-        if (Op0->hasOneUse() || cast<BinaryOperator>(Op0)->hasOneUse())
+        if (Op0->hasOneUse() || IsFreeToInvert(C, C->hasOneUse()))
           return BinaryOperator::CreateAnd(Op1, Builder->CreateNot(C));
 
     // (A | B) & ((~A) ^ B) -> (A & B)
@@ -2138,20 +2138,14 @@ Instruction *InstCombiner::visitOr(Binar
   }
 
   // (A ^ B) | ((B ^ C) ^ A) -> (A ^ B) | C
-  // FIXME: The two hasOneUse calls here are the same call, maybe we were
-  // supposed to check Op1->operand(0)?
   if (match(Op0, m_Xor(m_Value(A), m_Value(B))))
     if (match(Op1, m_Xor(m_Xor(m_Specific(B), m_Value(C)), m_Specific(A))))
-      if (Op1->hasOneUse() || cast<BinaryOperator>(Op1)->hasOneUse())
-        return BinaryOperator::CreateOr(Op0, C);
+      return BinaryOperator::CreateOr(Op0, C);
 
   // ((A ^ C) ^ B) | (B ^ A) -> (B ^ A) | C
-  // FIXME: The two hasOneUse calls here are the same call, maybe we were
-  // supposed to check Op0->operand(0)?
   if (match(Op0, m_Xor(m_Xor(m_Value(A), m_Value(C)), m_Value(B))))
     if (match(Op1, m_Xor(m_Specific(B), m_Specific(A))))
-      if (Op0->hasOneUse() || cast<BinaryOperator>(Op0)->hasOneUse())
-        return BinaryOperator::CreateOr(Op1, C);
+      return BinaryOperator::CreateOr(Op1, C);
 
   // ((B | C) & A) | B -> B | (A & C)
   if (match(Op0, m_And(m_Or(m_Specific(Op1), m_Value(C)), m_Value(A))))

Modified: llvm/trunk/test/Transforms/InstCombine/or-xor.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/InstCombine/or-xor.ll?rev=305705&r1=305704&r2=305705&view=diff
==============================================================================
--- llvm/trunk/test/Transforms/InstCombine/or-xor.ll (original)
+++ llvm/trunk/test/Transforms/InstCombine/or-xor.ll Mon Jun 19 11:23:49 2017
@@ -316,7 +316,7 @@ define i8 @test17(i8 %A, i8 %B) {
 ; CHECK-NEXT:    [[XOR1:%.*]] = xor i8 [[B:%.*]], [[A:%.*]]
 ; CHECK-NEXT:    [[NOT:%.*]] = xor i8 [[A]], 33
 ; CHECK-NEXT:    [[XOR2:%.*]] = xor i8 [[NOT]], [[B]]
-; CHECK-NEXT:    [[OR:%.*]] = or i8 [[XOR1]], [[XOR2]]
+; CHECK-NEXT:    [[OR:%.*]] = or i8 [[XOR1]], 33
 ; CHECK-NEXT:    [[RES:%.*]] = mul i8 [[OR]], [[XOR2]]
 ; CHECK-NEXT:    ret i8 [[RES]]
 ;
@@ -333,7 +333,7 @@ define i8 @test18(i8 %A, i8 %B) {
 ; CHECK-NEXT:    [[XOR1:%.*]] = xor i8 [[B:%.*]], [[A:%.*]]
 ; CHECK-NEXT:    [[NOT:%.*]] = xor i8 [[A]], 33
 ; CHECK-NEXT:    [[XOR2:%.*]] = xor i8 [[NOT]], [[B]]
-; CHECK-NEXT:    [[OR:%.*]] = or i8 [[XOR2]], [[XOR1]]
+; CHECK-NEXT:    [[OR:%.*]] = or i8 [[XOR1]], 33
 ; CHECK-NEXT:    [[RES:%.*]] = mul i8 [[OR]], [[XOR2]]
 ; CHECK-NEXT:    ret i8 [[RES]]
 ;

Modified: llvm/trunk/test/Transforms/InstCombine/xor2.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/InstCombine/xor2.ll?rev=305705&r1=305704&r2=305705&view=diff
==============================================================================
--- llvm/trunk/test/Transforms/InstCombine/xor2.ll (original)
+++ llvm/trunk/test/Transforms/InstCombine/xor2.ll Mon Jun 19 11:23:49 2017
@@ -330,7 +330,7 @@ define i8 @test15(i8 %A, i8 %B) {
 ; CHECK-NEXT:    [[XOR1:%.*]] = xor i8 [[B:%.*]], [[A:%.*]]
 ; CHECK-NEXT:    [[NOT:%.*]] = xor i8 [[A]], 33
 ; CHECK-NEXT:    [[XOR2:%.*]] = xor i8 [[NOT]], [[B]]
-; CHECK-NEXT:    [[AND:%.*]] = and i8 [[XOR1]], [[XOR2]]
+; CHECK-NEXT:    [[AND:%.*]] = and i8 [[XOR1]], -34
 ; CHECK-NEXT:    [[RES:%.*]] = mul i8 [[AND]], [[XOR2]]
 ; CHECK-NEXT:    ret i8 [[RES]]
 ;
@@ -347,7 +347,7 @@ define i8 @test16(i8 %A, i8 %B) {
 ; CHECK-NEXT:    [[XOR1:%.*]] = xor i8 [[B:%.*]], [[A:%.*]]
 ; CHECK-NEXT:    [[NOT:%.*]] = xor i8 [[A]], 33
 ; CHECK-NEXT:    [[XOR2:%.*]] = xor i8 [[NOT]], [[B]]
-; CHECK-NEXT:    [[AND:%.*]] = and i8 [[XOR2]], [[XOR1]]
+; CHECK-NEXT:    [[AND:%.*]] = and i8 [[XOR1]], -34
 ; CHECK-NEXT:    [[RES:%.*]] = mul i8 [[AND]], [[XOR2]]
 ; CHECK-NEXT:    ret i8 [[RES]]
 ;




More information about the llvm-commits mailing list