forked from OSchip/llvm-project
[DAGCombiner] Split SDIV/UDIV optimization expansions from the rest of the combines. NFCI.
As suggested by @efriedma on D48975, this patch separates the BuildDiv/Pow2 style optimizations from the rest of the visitSDIV/visitUDIV to make it easier to reuse the combines and will allow us to avoid some rather nasty node recursive combining in visitREM. llvm-svn: 336656
This commit is contained in:
parent
006bffe25a
commit
ce5c19b623
|
@ -298,7 +298,9 @@ namespace {
|
|||
SDValue visitMUL(SDNode *N);
|
||||
SDValue useDivRem(SDNode *N);
|
||||
SDValue visitSDIV(SDNode *N);
|
||||
SDValue visitSDIVLike(SDValue N0, SDValue N1, SDNode *N);
|
||||
SDValue visitUDIV(SDNode *N);
|
||||
SDValue visitUDIVLike(SDValue N0, SDValue N1, SDNode *N);
|
||||
SDValue visitREM(SDNode *N);
|
||||
SDValue visitMULHU(SDNode *N);
|
||||
SDValue visitMULHS(SDNode *N);
|
||||
|
@ -3010,7 +3012,6 @@ SDValue DAGCombiner::visitSDIV(SDNode *N) {
|
|||
SDValue N1 = N->getOperand(1);
|
||||
EVT VT = N->getValueType(0);
|
||||
EVT CCVT = getSetCCResultType(VT);
|
||||
unsigned BitWidth = VT.getScalarSizeInBits();
|
||||
|
||||
// fold vector ops
|
||||
if (VT.isVector())
|
||||
|
@ -3047,6 +3048,28 @@ SDValue DAGCombiner::visitSDIV(SDNode *N) {
|
|||
if (DAG.SignBitIsZero(N1) && DAG.SignBitIsZero(N0))
|
||||
return DAG.getNode(ISD::UDIV, DL, N1.getValueType(), N0, N1);
|
||||
|
||||
if (SDValue V = visitSDIVLike(N0, N1, N))
|
||||
return V;
|
||||
|
||||
// sdiv, srem -> sdivrem
|
||||
// If the divisor is constant, then return DIVREM only if isIntDivCheap() is
|
||||
// true. Otherwise, we break the simplification logic in visitREM().
|
||||
AttributeList Attr = DAG.getMachineFunction().getFunction().getAttributes();
|
||||
if (!N1C || TLI.isIntDivCheap(N->getValueType(0), Attr))
|
||||
if (SDValue DivRem = useDivRem(N))
|
||||
return DivRem;
|
||||
|
||||
return SDValue();
|
||||
}
|
||||
|
||||
SDValue DAGCombiner::visitSDIVLike(SDValue N0, SDValue N1, SDNode *N) {
|
||||
SDLoc DL(N);
|
||||
EVT VT = N->getValueType(0);
|
||||
EVT CCVT = getSetCCResultType(VT);
|
||||
unsigned BitWidth = VT.getScalarSizeInBits();
|
||||
|
||||
ConstantSDNode *N1C = isConstOrConstSplat(N1);
|
||||
|
||||
// Helper for determining whether a value is a power-2 constant scalar or a
|
||||
// vector of such elements.
|
||||
auto IsPowerOfTwo = [](ConstantSDNode *C) {
|
||||
|
@ -3119,13 +3142,6 @@ SDValue DAGCombiner::visitSDIV(SDNode *N) {
|
|||
if (SDValue Op = BuildSDIV(N))
|
||||
return Op;
|
||||
|
||||
// sdiv, srem -> sdivrem
|
||||
// If the divisor is constant, then return DIVREM only if isIntDivCheap() is
|
||||
// true. Otherwise, we break the simplification logic in visitREM().
|
||||
if (!N1C || TLI.isIntDivCheap(N->getValueType(0), Attr))
|
||||
if (SDValue DivRem = useDivRem(N))
|
||||
return DivRem;
|
||||
|
||||
return SDValue();
|
||||
}
|
||||
|
||||
|
@ -3155,6 +3171,26 @@ SDValue DAGCombiner::visitUDIV(SDNode *N) {
|
|||
if (SDValue NewSel = foldBinOpIntoSelect(N))
|
||||
return NewSel;
|
||||
|
||||
if (SDValue V = visitUDIVLike(N0, N1, N))
|
||||
return V;
|
||||
|
||||
// sdiv, srem -> sdivrem
|
||||
// If the divisor is constant, then return DIVREM only if isIntDivCheap() is
|
||||
// true. Otherwise, we break the simplification logic in visitREM().
|
||||
AttributeList Attr = DAG.getMachineFunction().getFunction().getAttributes();
|
||||
if (!N1C || TLI.isIntDivCheap(N->getValueType(0), Attr))
|
||||
if (SDValue DivRem = useDivRem(N))
|
||||
return DivRem;
|
||||
|
||||
return SDValue();
|
||||
}
|
||||
|
||||
SDValue DAGCombiner::visitUDIVLike(SDValue N0, SDValue N1, SDNode *N) {
|
||||
SDLoc DL(N);
|
||||
EVT VT = N->getValueType(0);
|
||||
|
||||
ConstantSDNode *N1C = isConstOrConstSplat(N1);
|
||||
|
||||
// fold (udiv x, (1 << c)) -> x >>u c
|
||||
if (isConstantOrConstantVector(N1, /*NoOpaques*/ true) &&
|
||||
DAG.isKnownToBeAPowerOfTwo(N1)) {
|
||||
|
@ -3190,13 +3226,6 @@ SDValue DAGCombiner::visitUDIV(SDNode *N) {
|
|||
if (SDValue Op = BuildUDIV(N))
|
||||
return Op;
|
||||
|
||||
// sdiv, srem -> sdivrem
|
||||
// If the divisor is constant, then return DIVREM only if isIntDivCheap() is
|
||||
// true. Otherwise, we break the simplification logic in visitREM().
|
||||
if (!N1C || TLI.isIntDivCheap(N->getValueType(0), Attr))
|
||||
if (SDValue DivRem = useDivRem(N))
|
||||
return DivRem;
|
||||
|
||||
return SDValue();
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue