[llvm] 7b617ee - [DAG] Cleanup "and/or of cmp with single bit diff" fold to use ISD::matchBinaryPredicate
Simon Pilgrim via llvm-commits
llvm-commits at lists.llvm.org
Thu May 26 04:34:20 PDT 2022
Author: Simon Pilgrim
Date: 2022-05-26T12:34:09+01:00
New Revision: 7b617eef8018d4cd001b36ad28f014e21270fde5
URL: https://github.com/llvm/llvm-project/commit/7b617eef8018d4cd001b36ad28f014e21270fde5
DIFF: https://github.com/llvm/llvm-project/commit/7b617eef8018d4cd001b36ad28f014e21270fde5.diff
LOG: [DAG] Cleanup "and/or of cmp with single bit diff" fold to use ISD::matchBinaryPredicate
Prep work as I'm investigating some cases where TLI::convertSetCCLogicToBitwiseLogic should accept vectors.
Added:
Modified:
llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
Removed:
################################################################################
diff --git a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
index 61d23aeec06ea..2c1f7d990aadd 100644
--- a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
@@ -5418,29 +5418,27 @@ SDValue DAGCombiner::foldLogicOfSetCCs(bool IsAnd, SDValue N0, SDValue N1,
}
// Turn compare of constants whose
diff erence is 1 bit into add+and+setcc.
- // TODO - support non-uniform vector amounts.
if ((IsAnd && CC1 == ISD::SETNE) || (!IsAnd && CC1 == ISD::SETEQ)) {
// Match a shared variable operand and 2 non-opaque constant operands.
- ConstantSDNode *C0 = isConstOrConstSplat(LR);
- ConstantSDNode *C1 = isConstOrConstSplat(RR);
- if (LL == RL && C0 && C1 && !C0->isOpaque() && !C1->isOpaque()) {
+ auto MatchDiffPow2 = [&](ConstantSDNode *C0, ConstantSDNode *C1) {
+ // The
diff erence of the constants must be a single bit.
const APInt &CMax =
APIntOps::umax(C0->getAPIntValue(), C1->getAPIntValue());
const APInt &CMin =
APIntOps::umin(C0->getAPIntValue(), C1->getAPIntValue());
- // The
diff erence of the constants must be a single bit.
- if ((CMax - CMin).isPowerOf2()) {
- // and/or (setcc X, CMax, ne), (setcc X, CMin, ne/eq) -->
- // setcc ((sub X, CMin), ~(CMax - CMin)), 0, ne/eq
- SDValue Max = DAG.getNode(ISD::UMAX, DL, OpVT, LR, RR);
- SDValue Min = DAG.getNode(ISD::UMIN, DL, OpVT, LR, RR);
- SDValue Offset = DAG.getNode(ISD::SUB, DL, OpVT, LL, Min);
- SDValue Diff = DAG.getNode(ISD::SUB, DL, OpVT, Max, Min);
- SDValue Mask = DAG.getNOT(DL, Diff, OpVT);
- SDValue And = DAG.getNode(ISD::AND, DL, OpVT, Offset, Mask);
- SDValue Zero = DAG.getConstant(0, DL, OpVT);
- return DAG.getSetCC(DL, VT, And, Zero, CC0);
- }
+ return !C0->isOpaque() && !C1->isOpaque() && (CMax - CMin).isPowerOf2();
+ };
+ if (LL == RL && ISD::matchBinaryPredicate(LR, RR, MatchDiffPow2)) {
+ // and/or (setcc X, CMax, ne), (setcc X, CMin, ne/eq) -->
+ // setcc ((sub X, CMin), ~(CMax - CMin)), 0, ne/eq
+ SDValue Max = DAG.getNode(ISD::UMAX, DL, OpVT, LR, RR);
+ SDValue Min = DAG.getNode(ISD::UMIN, DL, OpVT, LR, RR);
+ SDValue Offset = DAG.getNode(ISD::SUB, DL, OpVT, LL, Min);
+ SDValue Diff = DAG.getNode(ISD::SUB, DL, OpVT, Max, Min);
+ SDValue Mask = DAG.getNOT(DL, Diff, OpVT);
+ SDValue And = DAG.getNode(ISD::AND, DL, OpVT, Offset, Mask);
+ SDValue Zero = DAG.getConstant(0, DL, OpVT);
+ return DAG.getSetCC(DL, VT, And, Zero, CC0);
}
}
}
More information about the llvm-commits
mailing list