Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 9a38d58

Browse files
author
git apple-llvm automerger
committed
Merge commit '8e45eaf1da56' from llvm.org/master into apple/master
2 parents b376e1f + 8e45eaf commit 9a38d58

File tree

1 file changed

+105
-96
lines changed

1 file changed

+105
-96
lines changed

llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp

+105-96
Original file line numberDiff line numberDiff line change
@@ -14229,118 +14229,127 @@ bool DAGCombiner::CombineToPreIndexedLoadStore(SDNode *N) {
1422914229
return true;
1423014230
}
1423114231

14232-
/// Try to combine a load/store with a add/sub of the base pointer node into a
14233-
/// post-indexed load/store. The transformation folded the add/subtract into the
14234-
/// new indexed load/store effectively and all of its uses are redirected to the
14235-
/// new load/store.
14236-
bool DAGCombiner::CombineToPostIndexedLoadStore(SDNode *N) {
14237-
if (Level < AfterLegalizeDAG)
14232+
static bool shouldCombineToPostInc(SDNode *N, SDValue Ptr, SDNode *PtrUse,
14233+
SDValue &BasePtr, SDValue &Offset,
14234+
ISD::MemIndexedMode &AM,
14235+
SelectionDAG &DAG,
14236+
const TargetLowering &TLI) {
14237+
if (PtrUse == N ||
14238+
(PtrUse->getOpcode() != ISD::ADD && PtrUse->getOpcode() != ISD::SUB))
1423814239
return false;
1423914240

14240-
bool IsLoad = true;
14241-
bool IsMasked = false;
14242-
SDValue Ptr;
14243-
if (!getCombineLoadStoreParts(N, ISD::POST_INC, ISD::POST_DEC, IsLoad, IsMasked,
14244-
Ptr, TLI))
14241+
if (!TLI.getPostIndexedAddressParts(N, PtrUse, BasePtr, Offset, AM, DAG))
1424514242
return false;
1424614243

14247-
if (Ptr.getNode()->hasOneUse())
14244+
// Don't create a indexed load / store with zero offset.
14245+
if (isNullConstant(Offset))
1424814246
return false;
1424914247

14250-
for (SDNode *Op : Ptr.getNode()->uses()) {
14251-
if (Op == N ||
14252-
(Op->getOpcode() != ISD::ADD && Op->getOpcode() != ISD::SUB))
14253-
continue;
14254-
14255-
SDValue BasePtr;
14256-
SDValue Offset;
14257-
ISD::MemIndexedMode AM = ISD::UNINDEXED;
14258-
if (TLI.getPostIndexedAddressParts(N, Op, BasePtr, Offset, AM, DAG)) {
14259-
// Don't create a indexed load / store with zero offset.
14260-
if (isNullConstant(Offset))
14261-
continue;
14248+
if (isa<FrameIndexSDNode>(BasePtr) || isa<RegisterSDNode>(BasePtr))
14249+
return false;
1426214250

14263-
// Try turning it into a post-indexed load / store except when
14264-
// 1) All uses are load / store ops that use it as base ptr (and
14265-
// it may be folded as addressing mmode).
14266-
// 2) Op must be independent of N, i.e. Op is neither a predecessor
14267-
// nor a successor of N. Otherwise, if Op is folded that would
14268-
// create a cycle.
14251+
for (SDNode *Use : BasePtr.getNode()->uses()) {
14252+
if (Use == Ptr.getNode())
14253+
continue;
1426914254

14270-
if (isa<FrameIndexSDNode>(BasePtr) || isa<RegisterSDNode>(BasePtr))
14271-
continue;
14255+
// If all the uses are load / store addresses, then don't do the
14256+
// transformation.
14257+
if (Use->getOpcode() == ISD::ADD || Use->getOpcode() == ISD::SUB) {
14258+
for (SDNode *UseUse : Use->uses())
14259+
if (canFoldInAddressingMode(Use, UseUse, DAG, TLI))
14260+
return false;
14261+
}
14262+
}
14263+
return true;
14264+
}
1427214265

14273-
// Check for #1.
14274-
bool TryNext = false;
14275-
for (SDNode *Use : BasePtr.getNode()->uses()) {
14276-
if (Use == Ptr.getNode())
14277-
continue;
14266+
static SDNode *getPostIndexedLoadStoreOp(SDNode *N, bool &IsLoad,
14267+
bool &IsMasked, SDValue &Ptr,
14268+
SDValue &BasePtr, SDValue &Offset,
14269+
ISD::MemIndexedMode &AM,
14270+
SelectionDAG &DAG,
14271+
const TargetLowering &TLI) {
14272+
if (!getCombineLoadStoreParts(N, ISD::POST_INC, ISD::POST_DEC, IsLoad,
14273+
IsMasked, Ptr, TLI) ||
14274+
Ptr.getNode()->hasOneUse())
14275+
return nullptr;
14276+
14277+
// Try turning it into a post-indexed load / store except when
14278+
// 1) All uses are load / store ops that use it as base ptr (and
14279+
// it may be folded as addressing mmode).
14280+
// 2) Op must be independent of N, i.e. Op is neither a predecessor
14281+
// nor a successor of N. Otherwise, if Op is folded that would
14282+
// create a cycle.
14283+
for (SDNode *Op : Ptr->uses()) {
14284+
// Check for #1.
14285+
if (!shouldCombineToPostInc(N, Ptr, Op, BasePtr, Offset, AM, DAG, TLI))
14286+
continue;
1427814287

14279-
// If all the uses are load / store addresses, then don't do the
14280-
// transformation.
14281-
if (Use->getOpcode() == ISD::ADD || Use->getOpcode() == ISD::SUB) {
14282-
bool RealUse = false;
14283-
for (SDNode *UseUse : Use->uses()) {
14284-
if (!canFoldInAddressingMode(Use, UseUse, DAG, TLI))
14285-
RealUse = true;
14286-
}
14288+
// Check for #2.
14289+
SmallPtrSet<const SDNode *, 32> Visited;
14290+
SmallVector<const SDNode *, 8> Worklist;
14291+
// Ptr is predecessor to both N and Op.
14292+
Visited.insert(Ptr.getNode());
14293+
Worklist.push_back(N);
14294+
Worklist.push_back(Op);
14295+
if (!SDNode::hasPredecessorHelper(N, Visited, Worklist) &&
14296+
!SDNode::hasPredecessorHelper(Op, Visited, Worklist))
14297+
return Op;
14298+
}
14299+
return nullptr;
14300+
}
1428714301

14288-
if (!RealUse) {
14289-
TryNext = true;
14290-
break;
14291-
}
14292-
}
14293-
}
14302+
/// Try to combine a load/store with a add/sub of the base pointer node into a
14303+
/// post-indexed load/store. The transformation folded the add/subtract into the
14304+
/// new indexed load/store effectively and all of its uses are redirected to the
14305+
/// new load/store.
14306+
bool DAGCombiner::CombineToPostIndexedLoadStore(SDNode *N) {
14307+
if (Level < AfterLegalizeDAG)
14308+
return false;
1429414309

14295-
if (TryNext)
14296-
continue;
14310+
bool IsLoad = true;
14311+
bool IsMasked = false;
14312+
SDValue Ptr;
14313+
SDValue BasePtr;
14314+
SDValue Offset;
14315+
ISD::MemIndexedMode AM = ISD::UNINDEXED;
14316+
SDNode *Op = getPostIndexedLoadStoreOp(N, IsLoad, IsMasked, Ptr, BasePtr,
14317+
Offset, AM, DAG, TLI);
14318+
if (!Op)
14319+
return false;
1429714320

14298-
// Check for #2.
14299-
SmallPtrSet<const SDNode *, 32> Visited;
14300-
SmallVector<const SDNode *, 8> Worklist;
14301-
// Ptr is predecessor to both N and Op.
14302-
Visited.insert(Ptr.getNode());
14303-
Worklist.push_back(N);
14304-
Worklist.push_back(Op);
14305-
if (!SDNode::hasPredecessorHelper(N, Visited, Worklist) &&
14306-
!SDNode::hasPredecessorHelper(Op, Visited, Worklist)) {
14307-
SDValue Result;
14308-
if (!IsMasked)
14309-
Result = IsLoad ? DAG.getIndexedLoad(SDValue(N, 0), SDLoc(N), BasePtr,
14310-
Offset, AM)
14311-
: DAG.getIndexedStore(SDValue(N, 0), SDLoc(N),
14321+
SDValue Result;
14322+
if (!IsMasked)
14323+
Result = IsLoad ? DAG.getIndexedLoad(SDValue(N, 0), SDLoc(N), BasePtr,
14324+
Offset, AM)
14325+
: DAG.getIndexedStore(SDValue(N, 0), SDLoc(N),
14326+
BasePtr, Offset, AM);
14327+
else
14328+
Result = IsLoad ? DAG.getIndexedMaskedLoad(SDValue(N, 0), SDLoc(N),
14329+
BasePtr, Offset, AM)
14330+
: DAG.getIndexedMaskedStore(SDValue(N, 0), SDLoc(N),
1431214331
BasePtr, Offset, AM);
14313-
else
14314-
Result = IsLoad ? DAG.getIndexedMaskedLoad(SDValue(N, 0), SDLoc(N),
14315-
BasePtr, Offset, AM)
14316-
: DAG.getIndexedMaskedStore(SDValue(N, 0), SDLoc(N),
14317-
BasePtr, Offset, AM);
14318-
++PostIndexedNodes;
14319-
++NodesCombined;
14320-
LLVM_DEBUG(dbgs() << "\nReplacing.5 "; N->dump(&DAG);
14321-
dbgs() << "\nWith: "; Result.getNode()->dump(&DAG);
14322-
dbgs() << '\n');
14323-
WorklistRemover DeadNodes(*this);
14324-
if (IsLoad) {
14325-
DAG.ReplaceAllUsesOfValueWith(SDValue(N, 0), Result.getValue(0));
14326-
DAG.ReplaceAllUsesOfValueWith(SDValue(N, 1), Result.getValue(2));
14327-
} else {
14328-
DAG.ReplaceAllUsesOfValueWith(SDValue(N, 0), Result.getValue(1));
14329-
}
14330-
14331-
// Finally, since the node is now dead, remove it from the graph.
14332-
deleteAndRecombine(N);
14333-
14334-
// Replace the uses of Use with uses of the updated base value.
14335-
DAG.ReplaceAllUsesOfValueWith(SDValue(Op, 0),
14336-
Result.getValue(IsLoad ? 1 : 0));
14337-
deleteAndRecombine(Op);
14338-
return true;
14339-
}
14340-
}
14332+
++PostIndexedNodes;
14333+
++NodesCombined;
14334+
LLVM_DEBUG(dbgs() << "\nReplacing.5 "; N->dump(&DAG);
14335+
dbgs() << "\nWith: "; Result.getNode()->dump(&DAG);
14336+
dbgs() << '\n');
14337+
WorklistRemover DeadNodes(*this);
14338+
if (IsLoad) {
14339+
DAG.ReplaceAllUsesOfValueWith(SDValue(N, 0), Result.getValue(0));
14340+
DAG.ReplaceAllUsesOfValueWith(SDValue(N, 1), Result.getValue(2));
14341+
} else {
14342+
DAG.ReplaceAllUsesOfValueWith(SDValue(N, 0), Result.getValue(1));
1434114343
}
1434214344

14343-
return false;
14345+
// Finally, since the node is now dead, remove it from the graph.
14346+
deleteAndRecombine(N);
14347+
14348+
// Replace the uses of Use with uses of the updated base value.
14349+
DAG.ReplaceAllUsesOfValueWith(SDValue(Op, 0),
14350+
Result.getValue(IsLoad ? 1 : 0));
14351+
deleteAndRecombine(Op);
14352+
return true;
1434414353
}
1434514354

1434614355
/// Return the base-pointer arithmetic from an indexed \p LD.

0 commit comments

Comments
 (0)