[llvm] 430ad96 - [InstCombine] enhance bitwise select matching
Sanjay Patel via llvm-commits
llvm-commits at lists.llvm.org
Tue Nov 23 07:05:04 PST 2021
Author: Sanjay Patel
Date: 2021-11-23T09:57:44-05:00
New Revision: 430ad9697d143b4c408acf0d0d01c17830ac2bb3
URL: https://github.com/llvm/llvm-project/commit/430ad9697d143b4c408acf0d0d01c17830ac2bb3
DIFF: https://github.com/llvm/llvm-project/commit/430ad9697d143b4c408acf0d0d01c17830ac2bb3.diff
LOG: [InstCombine] enhance bitwise select matching
I noticed that adding a seemingly unrelated fold for xor caused
regressions on similar patterns, and this is one of the
underlying causes.
This could also be a variation for code as seen in:
https://llvm.org/PR34047
...although that exact example should be fixed after:
D113035 / c36b7e21bd8f
The vector test shows that we are actually missing a potential
canonicalization for bitcast-of-sext-of-not or the inverse.
The scalar test shows that even if we had that canonicalization,
it would still be possible to see this pattern due to extra uses.
https://alive2.llvm.org/ce/z/y2BAgi
Added:
Modified:
llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
llvm/test/Transforms/InstCombine/logical-select.ll
Removed:
################################################################################
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
index 1e09766831613..5af453c972596 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp
@@ -2353,11 +2353,20 @@ Value *InstCombinerImpl::getSelectCondition(Value *A, Value *B) {
Value *Cond;
Value *NotB;
if (match(A, m_SExt(m_Value(Cond))) &&
- Cond->getType()->isIntOrIntVectorTy(1) &&
- match(B, m_OneUse(m_Not(m_Value(NotB))))) {
- NotB = peekThroughBitcast(NotB, true);
- if (match(NotB, m_SExt(m_Specific(Cond))))
+ Cond->getType()->isIntOrIntVectorTy(1)) {
+ // A = sext i1 Cond; B = sext (not (i1 Cond))
+ if (match(B, m_SExt(m_Not(m_Specific(Cond)))))
return Cond;
+
+ // A = sext i1 Cond; B = not ({bitcast} (sext (i1 Cond)))
+ // TODO: The one-use checks are unnecessary or misplaced. If the caller
+ // checked for uses on logic ops/casts, that should be enough to
+ // make this transform worthwhile.
+ if (match(B, m_OneUse(m_Not(m_Value(NotB))))) {
+ NotB = peekThroughBitcast(NotB, true);
+ if (match(NotB, m_SExt(m_Specific(Cond))))
+ return Cond;
+ }
}
// All scalar (and most vector) possibilities should be handled now.
diff --git a/llvm/test/Transforms/InstCombine/logical-select.ll b/llvm/test/Transforms/InstCombine/logical-select.ll
index 459e1b155453e..5093f20cba0c4 100644
--- a/llvm/test/Transforms/InstCombine/logical-select.ll
+++ b/llvm/test/Transforms/InstCombine/logical-select.ll
@@ -829,20 +829,15 @@ define i64 @bitcast_int_scalar_cond(<2 x i1> %b, i64 %c, i64 %d) {
ret i64 %r
}
-; TODO:
; Peek through bitcasts and sexts to find negated bool condition.
define <1 x i6> @bitcast_sext_cond(<2 x i1> %cmp, <1 x i6> %a, <1 x i6> %b) {
; CHECK-LABEL: @bitcast_sext_cond(
-; CHECK-NEXT: [[SEXT:%.*]] = sext <2 x i1> [[CMP:%.*]] to <2 x i3>
-; CHECK-NEXT: [[BC1:%.*]] = bitcast <2 x i3> [[SEXT]] to <1 x i6>
-; CHECK-NEXT: [[NEG:%.*]] = xor <2 x i1> [[CMP]], <i1 true, i1 true>
-; CHECK-NEXT: [[SEXT2:%.*]] = sext <2 x i1> [[NEG]] to <2 x i3>
-; CHECK-NEXT: [[BC2:%.*]] = bitcast <2 x i3> [[SEXT2]] to <1 x i6>
-; CHECK-NEXT: [[AND1:%.*]] = and <1 x i6> [[BC1]], [[A:%.*]]
-; CHECK-NEXT: [[AND2:%.*]] = and <1 x i6> [[BC2]], [[B:%.*]]
-; CHECK-NEXT: [[OR:%.*]] = or <1 x i6> [[AND1]], [[AND2]]
-; CHECK-NEXT: ret <1 x i6> [[OR]]
+; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i6> [[A:%.*]] to <2 x i3>
+; CHECK-NEXT: [[TMP2:%.*]] = bitcast <1 x i6> [[B:%.*]] to <2 x i3>
+; CHECK-NEXT: [[TMP3:%.*]] = select <2 x i1> [[CMP:%.*]], <2 x i3> [[TMP1]], <2 x i3> [[TMP2]]
+; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i3> [[TMP3]] to <1 x i6>
+; CHECK-NEXT: ret <1 x i6> [[TMP4]]
;
%sext = sext <2 x i1> %cmp to <2 x i3>
%bc1 = bitcast <2 x i3> %sext to <1 x i6>
@@ -855,7 +850,6 @@ define <1 x i6> @bitcast_sext_cond(<2 x i1> %cmp, <1 x i6> %a, <1 x i6> %b) {
ret <1 x i6> %or
}
-; TODO:
; Extra uses may prevent other transforms from creating the canonical patterns.
define i8 @sext_cond_extra_uses(i1 %cmp, i8 %a, i8 %b) {
@@ -865,10 +859,8 @@ define i8 @sext_cond_extra_uses(i1 %cmp, i8 %a, i8 %b) {
; CHECK-NEXT: call void @use(i8 [[SEXT1]])
; CHECK-NEXT: [[SEXT2:%.*]] = sext i1 [[NEG]] to i8
; CHECK-NEXT: call void @use(i8 [[SEXT2]])
-; CHECK-NEXT: [[AND1:%.*]] = and i8 [[SEXT1]], [[A:%.*]]
-; CHECK-NEXT: [[AND2:%.*]] = and i8 [[SEXT2]], [[B:%.*]]
-; CHECK-NEXT: [[OR:%.*]] = or i8 [[AND1]], [[AND2]]
-; CHECK-NEXT: ret i8 [[OR]]
+; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[CMP]], i8 [[A:%.*]], i8 [[B:%.*]]
+; CHECK-NEXT: ret i8 [[TMP1]]
;
%neg = xor i1 %cmp, -1
%sext1 = sext i1 %cmp to i8
More information about the llvm-commits
mailing list