[PATCH] D159380: [InstCombine] Fold ((A&B)^A)|((A&B)^B) to A^B

Marc Auberer via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Fri Sep 1 14:19:38 PDT 2023


marcauberer updated this revision to Diff 555509.
marcauberer added a comment.

Use lambda to avoid code duplication


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D159380/new/

https://reviews.llvm.org/D159380

Files:
  llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
  llvm/test/Transforms/InstCombine/or-xor-xor.ll


Index: llvm/test/Transforms/InstCombine/or-xor-xor.ll
===================================================================
--- llvm/test/Transforms/InstCombine/or-xor-xor.ll
+++ llvm/test/Transforms/InstCombine/or-xor-xor.ll
@@ -5,10 +5,7 @@
 
 define i1 @or_xor_xor_normal_variant1(i1 %a, i1 %b) {
 ; CHECK-LABEL: @or_xor_xor_normal_variant1(
-; CHECK-NEXT:    [[AND:%.*]] = and i1 [[A:%.*]], [[B:%.*]]
-; CHECK-NEXT:    [[XOR1:%.*]] = xor i1 [[AND]], [[A]]
-; CHECK-NEXT:    [[XOR2:%.*]] = xor i1 [[AND]], [[B]]
-; CHECK-NEXT:    [[OR:%.*]] = or i1 [[XOR1]], [[XOR2]]
+; CHECK-NEXT:    [[OR:%.*]] = xor i1 [[A:%.*]], [[B:%.*]]
 ; CHECK-NEXT:    ret i1 [[OR]]
 ;
   %and = and i1 %a, %b
@@ -20,10 +17,7 @@
 
 define i1 @or_xor_xor_normal_variant2(i1 %a, i1 %b) {
 ; CHECK-LABEL: @or_xor_xor_normal_variant2(
-; CHECK-NEXT:    [[AND:%.*]] = and i1 [[A:%.*]], [[B:%.*]]
-; CHECK-NEXT:    [[XOR1:%.*]] = xor i1 [[AND]], [[B]]
-; CHECK-NEXT:    [[XOR2:%.*]] = xor i1 [[AND]], [[A]]
-; CHECK-NEXT:    [[OR:%.*]] = or i1 [[XOR1]], [[XOR2]]
+; CHECK-NEXT:    [[OR:%.*]] = xor i1 [[A:%.*]], [[B:%.*]]
 ; CHECK-NEXT:    ret i1 [[OR]]
 ;
   %and = and i1 %a, %b
@@ -35,10 +29,7 @@
 
 define <3 x i1> @or_xor_xor_normal_vector(<3 x i1> %a, <3 x i1> %b) {
 ; CHECK-LABEL: @or_xor_xor_normal_vector(
-; CHECK-NEXT:    [[AND:%.*]] = and <3 x i1> [[A:%.*]], [[B:%.*]]
-; CHECK-NEXT:    [[XOR1:%.*]] = xor <3 x i1> [[AND]], [[B]]
-; CHECK-NEXT:    [[XOR2:%.*]] = xor <3 x i1> [[AND]], [[A]]
-; CHECK-NEXT:    [[OR:%.*]] = or <3 x i1> [[XOR1]], [[XOR2]]
+; CHECK-NEXT:    [[OR:%.*]] = xor <3 x i1> [[A:%.*]], [[B:%.*]]
 ; CHECK-NEXT:    ret <3 x i1> [[OR]]
 ;
   %and = and <3 x i1> %a, %b
@@ -52,9 +43,7 @@
 ; CHECK-LABEL: @or_xor_xor_normal_multiple_uses_and(
 ; CHECK-NEXT:    [[AND:%.*]] = and i1 [[A:%.*]], [[B:%.*]]
 ; CHECK-NEXT:    call void @use(i1 [[AND]])
-; CHECK-NEXT:    [[XOR1:%.*]] = xor i1 [[AND]], [[B]]
-; CHECK-NEXT:    [[XOR2:%.*]] = xor i1 [[AND]], [[A]]
-; CHECK-NEXT:    [[OR:%.*]] = or i1 [[XOR1]], [[XOR2]]
+; CHECK-NEXT:    [[OR:%.*]] = xor i1 [[A]], [[B]]
 ; CHECK-NEXT:    ret i1 [[OR]]
 ;
   %and = and i1 %a, %b
Index: llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
===================================================================
--- llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
+++ llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
@@ -3650,6 +3650,27 @@
     }
   }
 
+  {
+    // ((A & B) ^ A) | ((A & B) ^ B) -> A ^ B
+    // (A ^ (A & B)) | (B ^ (A & B)) -> A ^ B
+    // ((A & B) ^ B) | ((A & B) ^ A) -> A ^ B
+    // (B ^ (A & B)) | (A ^ (A & B)) -> A ^ B
+    const auto TryXorOpt = [&](Value *Lhs, Value *Rhs) -> Instruction * {
+      if (match(Lhs, m_OneUse(m_c_Xor(m_And(m_Value(A), m_Value(B)),
+                                      m_Deferred(A)))) &&
+          match(Rhs, m_OneUse(m_c_Xor(m_And(m_Specific(A), m_Specific(B)),
+                                      m_Deferred(B))))) {
+        return BinaryOperator::CreateXor(A, B);
+      }
+      return nullptr;
+    };
+
+    if (Instruction *Result = TryXorOpt(Op0, Op1); Result != nullptr)
+      return Result;
+    if (Instruction *Result = TryXorOpt(Op1, Op0); Result != nullptr)
+      return Result;
+  }
+
   if (Instruction *V =
           canonicalizeCondSignextOfHighBitExtractToSignextHighBitExtract(I))
     return V;


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D159380.555509.patch
Type: text/x-patch
Size: 3347 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20230901/99bfa78f/attachment.bin>


More information about the llvm-commits mailing list