[llvm] f688ae7 - [InstCombine] allow vector splats for add+xor with low-mask
Sanjay Patel via llvm-commits
llvm-commits at lists.llvm.org
Thu Oct 8 13:00:32 PDT 2020
Author: Sanjay Patel
Date: 2020-10-08T15:53:38-04:00
New Revision: f688ae7a0e91ccd6d4ba39103b68eef22534e51e
URL: https://github.com/llvm/llvm-project/commit/f688ae7a0e91ccd6d4ba39103b68eef22534e51e
DIFF: https://github.com/llvm/llvm-project/commit/f688ae7a0e91ccd6d4ba39103b68eef22534e51e.diff
LOG: [InstCombine] allow vector splats for add+xor with low-mask
This can be allowed with undef elements too, but that can be another step:
https://alive2.llvm.org/ce/z/hnC4Z-
Added:
Modified:
llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
llvm/test/Transforms/InstCombine/sub-xor.ll
Removed:
################################################################################
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
index c53e4bc0e015..446085a3bdb3 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
@@ -924,9 +924,19 @@ Instruction *InstCombinerImpl::foldAddWithConstant(BinaryOperator &Add) {
C2->isMinSignedValue() && C2->sext(Ty->getScalarSizeInBits()) == *C)
return CastInst::Create(Instruction::SExt, X, Ty);
- // (X ^ signmask) + C --> (X + (signmask ^ C))
- if (match(Op0, m_Xor(m_Value(X), m_APInt(C2))) && C2->isSignMask())
- return BinaryOperator::CreateAdd(X, ConstantInt::get(Ty, *C2 ^ *C));
+ if (match(Op0, m_Xor(m_Value(X), m_APInt(C2)))) {
+ // (X ^ signmask) + C --> (X + (signmask ^ C))
+ if (C2->isSignMask())
+ return BinaryOperator::CreateAdd(X, ConstantInt::get(Ty, *C2 ^ *C));
+
+ // If X has no high-bits set above an xor mask:
+ // add (xor X, LowMaskC), C --> sub (LowMaskC + C), X
+ if (C2->isMask()) {
+ KnownBits LHSKnown = computeKnownBits(X, 0, &Add);
+ if ((*C2 | LHSKnown.Zero).isAllOnesValue())
+ return BinaryOperator::CreateSub(ConstantInt::get(Ty, *C2 + *C), X);
+ }
+ }
if (C->isOneValue() && Op0->hasOneUse()) {
// add (sext i1 X), 1 --> zext (not X)
@@ -1295,15 +1305,6 @@ Instruction *InstCombinerImpl::visitAdd(BinaryOperator &I) {
Value *NewShl = Builder.CreateShl(XorLHS, ShAmt, "sext");
return BinaryOperator::CreateAShr(NewShl, ShAmt);
}
-
- // If X has no high-bits above the xor mask set:
- // add (xor X, LowMaskC), C --> sub (LowMaskC + C), X
- if ((XorRHS->getValue() + 1).isPowerOf2()) {
- KnownBits LHSKnown = computeKnownBits(XorLHS, 0, &I);
- if ((XorRHS->getValue() | LHSKnown.Zero).isAllOnesValue())
- return BinaryOperator::CreateSub(ConstantExpr::getAdd(XorRHS, CI),
- XorLHS);
- }
}
}
diff --git a/llvm/test/Transforms/InstCombine/sub-xor.ll b/llvm/test/Transforms/InstCombine/sub-xor.ll
index 583a32ee3e48..cae292b21ad1 100644
--- a/llvm/test/Transforms/InstCombine/sub-xor.ll
+++ b/llvm/test/Transforms/InstCombine/sub-xor.ll
@@ -68,8 +68,7 @@ define i32 @xor_add_extra_use(i32 %x) {
define <2 x i8> @xor_add_splat(<2 x i8> %x) {
; CHECK-LABEL: @xor_add_splat(
; CHECK-NEXT: [[AND:%.*]] = and <2 x i8> [[X:%.*]], <i8 24, i8 24>
-; CHECK-NEXT: [[XOR:%.*]] = xor <2 x i8> [[AND]], <i8 63, i8 63>
-; CHECK-NEXT: [[ADD:%.*]] = add nuw nsw <2 x i8> [[XOR]], <i8 42, i8 42>
+; CHECK-NEXT: [[ADD:%.*]] = sub nuw nsw <2 x i8> <i8 105, i8 105>, [[AND]]
; CHECK-NEXT: ret <2 x i8> [[ADD]]
;
%and = and <2 x i8> %x, <i8 24, i8 24>
More information about the llvm-commits
mailing list