40 #define DEBUG_TYPE "legalizedag"
55 class SelectionDAGLegalize {
67 EVT getSetCCResultType(
EVT VT)
const {
68 return TLI.getSetCCResultType(DAG.getDataLayout(), *DAG.getContext(), VT);
78 LegalizedNodes(LegalizedNodes), UpdatedNodes(UpdatedNodes) {}
81 void LegalizeOp(
SDNode *Node);
86 void LegalizeLoadOps(
SDNode *Node);
87 void LegalizeStoreOps(
SDNode *Node);
107 bool &NeedInvert,
SDLoc dl);
111 unsigned NumOps,
bool isSigned,
SDLoc dl);
114 SDNode *Node,
bool isSigned);
131 void ExpandDYNAMIC_STACKALLOC(
SDNode *Node,
150 std::pair<SDValue, SDValue> ExpandAtomic(
SDNode *Node);
152 void ExpandNode(
SDNode *Node);
153 void PromoteNode(
SDNode *Node);
158 LegalizedNodes.
erase(N);
160 UpdatedNodes->insert(N);
164 dbgs() <<
" with: "; New->
dump(&DAG));
167 "Replacing one node with another that produces a different number "
170 for (
unsigned i = 0, e = Old->
getNumValues(); i != e; ++i)
173 UpdatedNodes->insert(New);
178 dbgs() <<
" with: "; New->
dump(&DAG));
183 UpdatedNodes->insert(New.
getNode());
190 for (
unsigned i = 0, e = Old->
getNumValues(); i != e; ++i) {
196 UpdatedNodes->insert(New[i].getNode());
208 SelectionDAGLegalize::ShuffleWithNarrowerEltType(
EVT NVT,
EVT VT,
SDLoc dl,
213 unsigned NumEltsGrowth = NumDestElts / NumMaskElts;
215 assert(NumEltsGrowth &&
"Cannot promote to vector type with fewer elts!");
217 if (NumEltsGrowth == 1)
218 return DAG.getVectorShuffle(NVT, dl, N1, N2, &Mask[0]);
221 for (
unsigned i = 0; i != NumMaskElts; ++i) {
223 for (
unsigned j = 0; j != NumEltsGrowth; ++j) {
227 NewMask.
push_back(Idx * NumEltsGrowth + j);
230 assert(NewMask.
size() == NumDestElts &&
"Non-integer NumEltsGrowth?");
231 assert(TLI.isShuffleMaskLegal(NewMask, NVT) &&
"Shuffle not legal?");
232 return DAG.getVectorShuffle(NVT, dl, N1, N2, &NewMask[0]);
264 TLI.ShouldShrinkFPConstant(OrigVT)) {
273 DAG.getConstantPool(LLVMC, TLI.getPointerTy(DAG.getDataLayout()));
274 unsigned Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlignment();
280 VT,
false,
false,
false, Alignment);
284 DAG.getLoad(OrigVT, dl, DAG.getEntryNode(), CPIdx,
293 SelectionDAGLegalize *DAGLegalize) {
295 "unaligned indexed stores not implemented!");
314 DAGLegalize->ReplaceNode(
SDValue(ST, 0), Result);
326 unsigned NumRegs = (StoredBytes + RegBytes - 1) / RegBytes;
334 StoredVT,
false,
false, 0);
341 for (
unsigned i = 1; i < NumRegs; i++) {
345 false,
false,
false, 0);
362 8 * (StoredBytes - Offset));
367 MemVT,
false,
false,
false, 0);
378 DAGLegalize->ReplaceNode(
SDValue(ST, 0), Result);
383 "Unaligned store of unknown type.");
387 int IncrementSize = NumBits / 8;
406 Alignment =
MinAlign(Alignment, IncrementSize);
414 DAGLegalize->ReplaceNode(
SDValue(ST, 0), Result);
423 "unaligned indexed loads not implemented!");
451 unsigned NumRegs = (LoadedBytes + RegBytes - 1) / RegBytes;
463 for (
unsigned i = 1; i < NumRegs; i++) {
477 StackPtr = DAG.
getNode(
ISD::ADD, dl, StackPtr.getValueType(), StackPtr,
483 8 * (LoadedBytes - Offset));
512 "Unaligned load of unsupported type.");
522 unsigned IncrementSize = NumBits / 8;
538 Hi = DAG.
getExtLoad(HiExtType, dl, VT, Chain, Ptr,
591 EVT PtrVT = TLI.getPointerTy(DAG.getDataLayout());
592 SDValue StackPtr = DAG.CreateStackTemporary(VT);
594 int SPFI = cast<FrameIndexSDNode>(StackPtr.
getNode())->getIndex();
597 SDValue Ch = DAG.getStore(DAG.getEntryNode(), dl, Tmp1, StackPtr,
603 Tmp3 = DAG.
getNode(CastOpc, dl, PtrVT, Tmp3);
607 DAG.getConstant(EltSize, dl, IdxVT));
613 return DAG.getLoad(VT, dl, Ch, StackPtr,
636 for (
unsigned i = 0; i != NumElts; ++i)
637 ShufOps.
push_back(i != InsertPos->getZExtValue() ? i : NumElts);
639 return DAG.getVectorShuffle(Vec.
getValueType(), dl, Vec, ScVec,
643 return PerformInsertVectorEltInMemory(Vec, Val, Idx, dl);
665 bitcastToAPInt().zextOrTrunc(32),
668 isVolatile, isNonTemporal, Alignment, AAInfo);
677 isVolatile, isNonTemporal, Alignment, AAInfo);
687 if (DAG.getDataLayout().isBigEndian())
691 isNonTemporal, Alignment, AAInfo);
694 Hi = DAG.getStore(Chain, dl, Hi, Ptr,
706 void SelectionDAGLegalize::LegalizeStoreOps(
SDNode *Node) {
718 if (
SDNode *OptStore = OptimizeFloatStore(ST).getNode()) {
719 ReplaceNode(ST, OptStore);
726 switch (TLI.getOperationAction(
ISD::STORE, VT)) {
735 unsigned ABIAlignment = DAG.getDataLayout().getABITypeAlignment(Ty);
736 if (Align < ABIAlignment)
743 if (Res && Res !=
SDValue(Node, 0))
744 ReplaceNode(
SDValue(Node, 0), Res);
750 "Can only promote stores to same size type");
753 DAG.getStore(Chain, dl, Value, Ptr,
755 isNonTemporal, Alignment, AAInfo);
756 ReplaceNode(
SDValue(Node, 0), Result);
767 auto &
DL = DAG.getDataLayout();
775 Value = DAG.getZeroExtendInReg(Value, dl, StVT);
778 NVT,
isVolatile, isNonTemporal, Alignment, AAInfo);
779 ReplaceNode(
SDValue(Node, 0), Result);
780 }
else if (StWidth & (StWidth - 1)) {
782 assert(!StVT.
isVector() &&
"Unsupported truncstore!");
783 unsigned RoundWidth = 1 <<
Log2_32(StWidth);
784 assert(RoundWidth < StWidth);
785 unsigned ExtraWidth = StWidth - RoundWidth;
786 assert(ExtraWidth < RoundWidth);
787 assert(!(RoundWidth % 8) && !(ExtraWidth % 8) &&
788 "Store size not an integral number of bytes!");
792 unsigned IncrementSize;
794 if (
DL.isLittleEndian()) {
797 Lo = DAG.getTruncStore(Chain, dl, Value, Ptr, ST->
getPointerInfo(),
803 IncrementSize = RoundWidth / 8;
805 DAG.getConstant(IncrementSize, dl,
808 ISD::SRL, dl, Value.getValueType(), Value,
809 DAG.getConstant(RoundWidth, dl,
810 TLI.getShiftAmountTy(Value.getValueType(),
DL)));
811 Hi = DAG.getTruncStore(Chain, dl, Hi, Ptr,
814 MinAlign(Alignment, IncrementSize), AAInfo);
820 ISD::SRL, dl, Value.getValueType(), Value,
821 DAG.getConstant(ExtraWidth, dl,
822 TLI.getShiftAmountTy(Value.getValueType(),
DL)));
824 RoundVT,
isVolatile, isNonTemporal, Alignment,
828 IncrementSize = RoundWidth / 8;
830 DAG.getConstant(IncrementSize, dl,
832 Lo = DAG.getTruncStore(Chain, dl, Value, Ptr,
835 MinAlign(Alignment, IncrementSize), AAInfo);
840 ReplaceNode(
SDValue(Node, 0), Result);
852 unsigned ABIAlignment =
DL.getABITypeAlignment(Ty);
853 if (Align < ABIAlignment)
860 if (Res && Res !=
SDValue(Node, 0))
861 ReplaceNode(
SDValue(Node, 0), Res);
866 "Vector Stores are handled in LegalizeVectorOps");
869 assert(TLI.isTypeLegal(StVT) &&
870 "Do not know how to expand this store!");
874 isVolatile, isNonTemporal, Alignment, AAInfo);
875 ReplaceNode(
SDValue(Node, 0), Result);
882 void SelectionDAGLegalize::LegalizeLoadOps(
SDNode *Node) {
895 switch (TLI.getOperationAction(Node->
getOpcode(), VT)) {
904 unsigned ABIAlignment = DAG.getDataLayout().getABITypeAlignment(Ty);
905 if (Align < ABIAlignment){
912 SDValue Res = TLI.LowerOperation(RVal, DAG);
920 MVT NVT = TLI.getTypeToPromoteTo(Node->
getOpcode(), VT);
922 "Can only promote loads to same size type");
930 if (RChain.
getNode() != Node) {
931 assert(RVal.
getNode() != Node &&
"Load must be completely replaced");
932 DAG.ReplaceAllUsesOfValueWith(
SDValue(Node, 0), RVal);
933 DAG.ReplaceAllUsesOfValueWith(
SDValue(Node, 1), RChain);
935 UpdatedNodes->insert(RVal.
getNode());
936 UpdatedNodes->insert(RChain.
getNode());
977 NVT,
isVolatile, isNonTemporal, isInvariant, Alignment,
995 }
else if (SrcWidth & (SrcWidth - 1)) {
997 assert(!SrcVT.
isVector() &&
"Unsupported extload!");
998 unsigned RoundWidth = 1 <<
Log2_32(SrcWidth);
999 assert(RoundWidth < SrcWidth);
1000 unsigned ExtraWidth = SrcWidth - RoundWidth;
1001 assert(ExtraWidth < RoundWidth);
1002 assert(!(RoundWidth % 8) && !(ExtraWidth % 8) &&
1003 "Load size not an integral number of bytes!");
1007 unsigned IncrementSize;
1008 auto &
DL = DAG.getDataLayout();
1010 if (
DL.isLittleEndian()) {
1016 isNonTemporal, isInvariant, Alignment, AAInfo);
1019 IncrementSize = RoundWidth / 8;
1020 Ptr = DAG.getNode(
ISD::ADD, dl, Ptr.getValueType(), Ptr,
1021 DAG.getConstant(IncrementSize, dl,
1022 Ptr.getValueType()));
1023 Hi = DAG.getExtLoad(ExtType, dl, Node->
getValueType(0), Chain, Ptr,
1025 ExtraVT,
isVolatile, isNonTemporal, isInvariant,
1026 MinAlign(Alignment, IncrementSize), AAInfo);
1036 DAG.getConstant(RoundWidth, dl,
1037 TLI.getShiftAmountTy(Hi.getValueType(),
DL)));
1045 Hi = DAG.getExtLoad(ExtType, dl, Node->
getValueType(0), Chain, Ptr,
1047 isNonTemporal, isInvariant, Alignment, AAInfo);
1050 IncrementSize = RoundWidth / 8;
1051 Ptr = DAG.getNode(
ISD::ADD, dl, Ptr.getValueType(), Ptr,
1052 DAG.getConstant(IncrementSize, dl,
1053 Ptr.getValueType()));
1057 ExtraVT,
isVolatile, isNonTemporal, isInvariant,
1058 MinAlign(Alignment, IncrementSize), AAInfo);
1068 DAG.getConstant(ExtraWidth, dl,
1069 TLI.getShiftAmountTy(Hi.getValueType(),
DL)));
1077 bool isCustom =
false;
1078 switch (TLI.getLoadExtAction(ExtType, Node->
getValueType(0),
1100 if (!TLI.allowsMisalignedMemoryAccesses(MemVT, AS, Align)) {
1102 unsigned ABIAlignment = DAG.getDataLayout().getABITypeAlignment(Ty);
1103 if (Align < ABIAlignment){
1115 if (TLI.isTypeLegal(SrcVT) ||
1116 TLI.isLoadExtLegal(ExtType, LoadVT, SrcVT)) {
1122 SDValue Load = DAG.getExtLoad(MidExtType, dl, LoadVT, Chain, Ptr,
1133 "Vector Loads are handled in LegalizeVectorOps");
1140 "EXTLOAD should always be supported!");
1153 ValRes = DAG.getZeroExtendInReg(Result, dl, SrcVT.getScalarType());
1162 if (Chain.getNode() != Node) {
1163 assert(Value.getNode() != Node &&
"Load must be completely replaced");
1164 DAG.ReplaceAllUsesOfValueWith(
SDValue(Node, 0), Value);
1165 DAG.ReplaceAllUsesOfValueWith(
SDValue(Node, 1), Chain);
1167 UpdatedNodes->insert(Value.getNode());
1168 UpdatedNodes->insert(Chain.getNode());
1175 void SelectionDAGLegalize::LegalizeOp(
SDNode *Node) {
1182 for (
unsigned i = 0, e = Node->
getNumValues(); i != e; ++i)
1183 assert(TLI.getTypeAction(*DAG.getContext(), Node->
getValueType(i)) ==
1185 "Unexpected illegal type!");
1188 assert((TLI.getTypeAction(*DAG.getContext(),
1191 "Unexpected illegal type!");
1196 bool SimpleFinishLegalizing =
true;
1205 Action = TLI.getOperationAction(Node->
getOpcode(),
1214 Action = TLI.getOperationAction(Node->
getOpcode(),
1219 EVT InnerType = cast<VTSDNode>(Node->
getOperand(1))->getVT();
1220 Action = TLI.getOperationAction(Node->
getOpcode(), InnerType);
1224 Action = TLI.getOperationAction(Node->
getOpcode(),
1236 cast<CondCodeSDNode>(Node->
getOperand(CCOperand))->
get();
1237 Action = TLI.getCondCodeAction(CCCode, OpVT);
1240 Action = TLI.getOperationAction(Node->
getOpcode(),
1243 Action = TLI.getOperationAction(Node->
getOpcode(), OpVT);
1251 SimpleFinishLegalizing =
false;
1258 SimpleFinishLegalizing =
false;
1298 ReplaceNode(Node, NewVal.
getNode());
1313 if (SimpleFinishLegalizing) {
1330 NewNode = DAG.UpdateNodeOperands(Node, Node->
getOperand(0),
1345 NewNode = DAG.UpdateNodeOperands(Node, Node->
getOperand(0),
1352 if (NewNode != Node) {
1353 ReplaceNode(Node, NewNode);
1369 ReplaceNode(
SDValue(Node, 0), Res);
1374 for (
unsigned i = 0, e = Node->
getNumValues(); i != e; ++i)
1376 ReplaceNode(Node, ResultVals.
data());
1403 return LegalizeLoadOps(Node);
1406 return LegalizeStoreOps(Node);
1411 SDValue SelectionDAGLegalize::ExpandExtractFromVectorThroughStack(
SDValue Op) {
1426 if (
StoreSDNode *ST = dyn_cast<StoreSDNode>(User)) {
1444 StackPtr = DAG.CreateStackTemporary(Vec.
getValueType());
1445 Ch = DAG.getStore(DAG.getEntryNode(), dl, Vec, StackPtr,
1455 Idx = DAG.getZExtOrTrunc(Idx, dl, TLI.getPointerTy(DAG.getDataLayout()));
1461 NewLoad = DAG.getLoad(Op.
getValueType(), dl, Ch, StackPtr,
1464 NewLoad = DAG.getExtLoad(
1469 DAG.ReplaceAllUsesOfValueWith(Ch,
SDValue(NewLoad.
getNode(), 1));
1475 NewLoadOperands[0] = Ch;
1477 SDValue(DAG.UpdateNodeOperands(NewLoad.
getNode(), NewLoadOperands), 0);
1481 SDValue SelectionDAGLegalize::ExpandInsertToVectorThroughStack(
SDValue Op) {
1491 SDValue StackPtr = DAG.CreateStackTemporary(Vec.getValueType());
1492 int FI = cast<FrameIndexSDNode>(StackPtr.
getNode())->getIndex();
1496 SDValue Ch = DAG.getStore(DAG.getEntryNode(), dl, Vec, StackPtr, PtrInfo,
1503 Vec.getValueType().getVectorElementType().getSizeInBits()/8;
1507 Idx = DAG.getZExtOrTrunc(Idx, dl, TLI.getPointerTy(DAG.getDataLayout()));
1513 Ch = DAG.getStore(Ch, dl, Part, SubStackPtr,
1517 return DAG.getLoad(Op.
getValueType(), dl, Ch, StackPtr, PtrInfo,
1518 false,
false,
false, 0);
1521 SDValue SelectionDAGLegalize::ExpandVectorBuildThroughStack(
SDNode* Node) {
1529 SDValue FIPtr = DAG.CreateStackTemporary(VT);
1530 int FI = cast<FrameIndexSDNode>(FIPtr.
getNode())->getIndex();
1541 unsigned Offset = TypeByteSize*i;
1549 Stores.
push_back(DAG.getTruncStore(DAG.getEntryNode(), dl,
1552 EltVT,
false,
false, 0));
1554 Stores.
push_back(DAG.getStore(DAG.getEntryNode(), dl,
1561 if (!Stores.
empty())
1564 StoreChain = DAG.getEntryNode();
1567 return DAG.getLoad(VT, dl, StoreChain, FIPtr, PtrInfo,
1568 false,
false,
false, 0);
1571 SDValue SelectionDAGLegalize::ExpandFCOPYSIGN(
SDNode* Node) {
1581 if (TLI.isTypeLegal(IVT)) {
1585 auto &
DL = DAG.getDataLayout();
1587 MVT LoadTy = TLI.getPointerTy(DL);
1589 SDValue StackPtr = DAG.CreateStackTemporary(FloatVT, LoadTy);
1594 if (
DL.isBigEndian()) {
1595 assert(FloatVT.
isByteSized() &&
"Unsupported floating point type!");
1598 false,
false,
false, 0);
1604 unsigned ByteOffset = (Strides * LoadTy.
getSizeInBits()) / 8;
1606 DAG.getConstant(ByteOffset, dl,
1610 false,
false,
false, 0);
1614 assert(BitShift < LoadTy.
getSizeInBits() &&
"Pointer advanced wrong?");
1616 SignBit = DAG.getNode(
1618 DAG.getConstant(BitShift, dl,
1619 TLI.getShiftAmountTy(SignBit.getValueType(),
DL)));
1623 SignBit = DAG.getSetCC(dl, getSetCCResultType(SignBit.getValueType()),
1625 DAG.getConstant(0, dl, SignBit.getValueType()),
1631 return DAG.getSelect(dl, AbsVal.
getValueType(), SignBit,
1636 void SelectionDAGLegalize::ExpandDYNAMIC_STACKALLOC(
SDNode* Node,
1638 unsigned SPReg = TLI.getStackPointerRegisterToSaveRestore();
1639 assert(SPReg &&
"Target cannot require DYNAMIC_STACKALLOC expansion and"
1640 " not tell us which reg is the stack pointer!");
1650 Chain = DAG.getCALLSEQ_START(Chain, DAG.getIntPtrConstant(0, dl,
true), dl);
1653 SDValue SP = DAG.getCopyFromReg(Chain, dl, SPReg, VT);
1655 unsigned Align = cast<ConstantSDNode>(Tmp3)->getZExtValue();
1656 unsigned StackAlign =
1657 DAG.getSubtarget().getFrameLowering()->getStackAlignment();
1659 if (Align > StackAlign)
1661 DAG.getConstant(-(uint64_t)Align, dl, VT));
1662 Chain = DAG.getCopyToReg(Chain, dl, SPReg, Tmp1);
1664 Tmp2 = DAG.getCALLSEQ_END(Chain, DAG.getIntPtrConstant(0, dl,
true),
1665 DAG.getIntPtrConstant(0, dl,
true),
SDValue(), dl);
1689 bool SelectionDAGLegalize::LegalizeSetCCCondCode(
EVT VT,
1697 switch (TLI.getCondCodeAction(CCCode, OpVT)) {
1704 if (TLI.isCondCodeLegal(InvCC, OpVT)) {
1706 CC = DAG.getCondCode(InvCC);
1716 &&
"If SETO is expanded, SETOEQ must be legal!");
1721 &&
"If SETUO is expanded, SETUNE must be legal!");
1756 if (TLI.isCondCodeLegal(InvCC, OpVT)) {
1757 CC = DAG.getCondCode(InvCC);
1770 SetCC1 = DAG.getSetCC(dl, VT, LHS, RHS, CC1);
1771 SetCC2 = DAG.getSetCC(dl, VT, LHS, RHS, CC2);
1774 SetCC1 = DAG.getSetCC(dl, VT, LHS, LHS, CC1);
1775 SetCC2 = DAG.getSetCC(dl, VT, RHS, RHS, CC2);
1777 LHS = DAG.
getNode(Opc, dl, VT, SetCC1, SetCC2);
1795 unsigned SrcAlign = DAG.getDataLayout().getPrefTypeAlignment(
1797 SDValue FIPtr = DAG.CreateStackTemporary(SlotVT, SrcAlign);
1807 unsigned DestAlign = DAG.getDataLayout().getPrefTypeAlignment(DestType);
1813 if (SrcSize > SlotSize)
1814 Store = DAG.getTruncStore(DAG.getEntryNode(), dl, SrcOp, FIPtr,
1815 PtrInfo, SlotVT,
false,
false, SrcAlign);
1817 assert(SrcSize == SlotSize &&
"Invalid store");
1818 Store = DAG.getStore(DAG.getEntryNode(), dl, SrcOp, FIPtr,
1819 PtrInfo,
false,
false, SrcAlign);
1823 if (SlotSize == DestSize)
1824 return DAG.getLoad(DestVT, dl, Store, FIPtr, PtrInfo,
1825 false,
false,
false, DestAlign);
1827 assert(SlotSize < DestSize &&
"Unknown extension!");
1828 return DAG.getExtLoad(
ISD::EXTLOAD, dl, DestVT, Store, FIPtr,
1829 PtrInfo, SlotVT,
false,
false,
false, DestAlign);
1832 SDValue SelectionDAGLegalize::ExpandSCALAR_TO_VECTOR(
SDNode *Node) {
1846 return DAG.getLoad(Node->
getValueType(0), dl, Ch, StackPtr,
1848 false,
false,
false, 0);
1865 for (
int Phase = 0; Phase < 2; ++Phase) {
1868 for (
unsigned i = 0; i < NumElems; ++i) {
1879 while (IntermedVals.
size() > 2) {
1880 NewIntermedVals.
clear();
1881 for (
unsigned i = 0, e = (IntermedVals.
size() & ~1u); i < e; i += 2) {
1887 FinalIndices.
reserve(IntermedVals[i].second.
size() +
1888 IntermedVals[i+1].second.
size());
1891 for (
unsigned j = 0, f = IntermedVals[i].second.
size(); j != f;
1894 FinalIndices.
push_back(IntermedVals[i].second[j]);
1896 for (
unsigned j = 0, f = IntermedVals[i+1].second.
size(); j != f;
1898 ShuffleVec[k] = NumElems + j;
1899 FinalIndices.
push_back(IntermedVals[i+1].second[j]);
1905 IntermedVals[i+1].first,
1910 std::make_pair(Shuffle, std::move(FinalIndices)));
1915 if ((IntermedVals.
size() & 1) != 0)
1918 IntermedVals.
swap(NewIntermedVals);
1921 assert(IntermedVals.
size() <= 2 && IntermedVals.
size() > 0 &&
1922 "Invalid number of intermediate vectors");
1923 SDValue Vec1 = IntermedVals[0].first;
1925 if (IntermedVals.
size() > 1)
1926 Vec2 = IntermedVals[1].first;
1931 for (
unsigned i = 0, e = IntermedVals[0].second.
size(); i != e; ++i)
1932 ShuffleVec[IntermedVals[0].second[i]] = i;
1933 for (
unsigned i = 0, e = IntermedVals[1].second.
size(); i != e; ++i)
1934 ShuffleVec[IntermedVals[1].second[i]] = NumElems + i;
1947 SDValue SelectionDAGLegalize::ExpandBUILD_VECTOR(
SDNode *Node) {
1957 bool isOnlyLowElement =
true;
1958 bool MoreThanTwoValues =
false;
1959 bool isConstant =
true;
1960 for (
unsigned i = 0; i < NumElems; ++i) {
1965 isOnlyLowElement =
false;
1966 if (!isa<ConstantFPSDNode>(V) && !isa<ConstantSDNode>(V))
1971 }
else if (!Value2.
getNode()) {
1974 }
else if (V != Value1 && V != Value2) {
1975 MoreThanTwoValues =
true;
1980 return DAG.getUNDEF(VT);
1982 if (isOnlyLowElement)
1988 for (
unsigned i = 0, e = NumElems; i != e; ++i) {
1990 dyn_cast<ConstantFPSDNode>(Node->
getOperand(i))) {
1991 CV.
push_back(const_cast<ConstantFP *>(V->getConstantFPValue()));
1993 dyn_cast<ConstantSDNode>(Node->
getOperand(i))) {
1995 CV.
push_back(const_cast<ConstantInt *>(V->getConstantIntValue()));
2012 DAG.getConstantPool(CP, TLI.getPointerTy(DAG.getDataLayout()));
2013 unsigned Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlignment();
2014 return DAG.getLoad(VT, dl, DAG.getEntryNode(), CPIdx,
2016 false,
false,
false, Alignment);
2020 for (
unsigned i = 0; i < NumElems; ++i) {
2026 if (TLI.shouldExpandBuildVectorWithShuffles(VT, DefinedValues.
size())) {
2027 if (!MoreThanTwoValues) {
2029 for (
unsigned i = 0; i < NumElems; ++i) {
2033 ShuffleVec[i] = V == Value1 ? 0 : NumElems;
2035 if (TLI.isShuffleMaskLegal(ShuffleVec, Node->
getValueType(0))) {
2042 Vec2 = DAG.getUNDEF(VT);
2045 return DAG.getVectorShuffle(VT, dl, Vec1, Vec2, ShuffleVec.data());
2055 return ExpandVectorBuildThroughStack(Node);
2072 Entry.
isZExt = !isSigned;
2073 Args.push_back(Entry);
2075 SDValue Callee = DAG.getExternalSymbol(TLI.getLibcallName(LC),
2076 TLI.getPointerTy(DAG.getDataLayout()));
2084 SDValue InChain = DAG.getEntryNode();
2089 bool isTailCall = TLI.isInTailCallPosition(DAG, Node, TCChain);
2094 CLI.setDebugLoc(
SDLoc(Node)).setChain(InChain)
2095 .setCallee(TLI.getLibcallCallingConv(LC), RetTy, Callee, std::move(Args), 0)
2096 .setTailCall(isTailCall).setSExtResult(isSigned).setZExtResult(!isSigned);
2098 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2100 if (!CallInfo.second.getNode())
2102 return DAG.getRoot();
2104 return CallInfo.first;
2110 const SDValue *Ops,
unsigned NumOps,
2111 bool isSigned,
SDLoc dl) {
2113 Args.reserve(NumOps);
2116 for (
unsigned i = 0; i != NumOps; ++i) {
2117 Entry.
Node = Ops[i];
2120 Entry.
isZExt = !isSigned;
2121 Args.push_back(Entry);
2123 SDValue Callee = DAG.getExternalSymbol(TLI.getLibcallName(LC),
2124 TLI.getPointerTy(DAG.getDataLayout()));
2129 CLI.setDebugLoc(dl).setChain(DAG.getEntryNode())
2130 .setCallee(TLI.getLibcallCallingConv(LC), RetTy, Callee, std::move(Args), 0)
2131 .setSExtResult(isSigned).setZExtResult(!isSigned);
2133 std::pair<SDValue,SDValue> CallInfo = TLI.LowerCallTo(CLI);
2135 return CallInfo.first;
2140 std::pair<SDValue, SDValue>
2154 Entry.
isZExt = !isSigned;
2155 Args.push_back(Entry);
2157 SDValue Callee = DAG.getExternalSymbol(TLI.getLibcallName(LC),
2158 TLI.getPointerTy(DAG.getDataLayout()));
2163 CLI.setDebugLoc(
SDLoc(Node)).setChain(InChain)
2164 .setCallee(TLI.getLibcallCallingConv(LC), RetTy, Callee, std::move(Args), 0)
2165 .setSExtResult(isSigned).setZExtResult(!isSigned);
2167 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2181 case MVT::f32: LC = Call_F32;
break;
2182 case MVT::f64: LC = Call_F64;
break;
2183 case MVT::f80: LC = Call_F80;
break;
2187 return ExpandLibCall(LC, Node,
false);
2190 SDValue SelectionDAGLegalize::ExpandIntLibCall(
SDNode* Node,
bool isSigned,
2199 case MVT::i8: LC = Call_I8;
break;
2200 case MVT::i16: LC = Call_I16;
break;
2201 case MVT::i32: LC = Call_I32;
break;
2202 case MVT::i64: LC = Call_I64;
break;
2205 return ExpandLibCall(LC, Node, isSigned);
2228 unsigned OtherOpcode = 0;
2251 SelectionDAGLegalize::ExpandDivRemLibCall(
SDNode *Node,
2269 SDValue InChain = DAG.getEntryNode();
2282 Entry.
isZExt = !isSigned;
2283 Args.push_back(Entry);
2287 SDValue FIPtr = DAG.CreateStackTemporary(RetVT);
2291 Entry.
isZExt = !isSigned;
2292 Args.push_back(Entry);
2294 SDValue Callee = DAG.getExternalSymbol(TLI.getLibcallName(LC),
2295 TLI.getPointerTy(DAG.getDataLayout()));
2299 CLI.setDebugLoc(dl).setChain(InChain)
2300 .setCallee(TLI.getLibcallCallingConv(LC), RetTy, Callee, std::move(Args), 0)
2301 .setSExtResult(isSigned).setZExtResult(!isSigned);
2303 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2306 SDValue Rem = DAG.getLoad(RetVT, dl, CallInfo.second, FIPtr,
2360 SelectionDAGLegalize::ExpandSinCosLibCall(
SDNode *Node,
2375 SDValue InChain = DAG.getEntryNode();
2388 Args.push_back(Entry);
2391 SDValue SinPtr = DAG.CreateStackTemporary(RetVT);
2392 Entry.
Node = SinPtr;
2396 Args.push_back(Entry);
2399 SDValue CosPtr = DAG.CreateStackTemporary(RetVT);
2400 Entry.
Node = CosPtr;
2404 Args.push_back(Entry);
2406 SDValue Callee = DAG.getExternalSymbol(TLI.getLibcallName(LC),
2407 TLI.getPointerTy(DAG.getDataLayout()));
2411 CLI.setDebugLoc(dl).setChain(InChain)
2412 .setCallee(TLI.getLibcallCallingConv(LC),
2415 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2417 Results.
push_back(DAG.getLoad(RetVT, dl, CallInfo.second, SinPtr,
2419 Results.
push_back(DAG.getLoad(RetVT, dl, CallInfo.second, CosPtr,
2427 SDValue SelectionDAGLegalize::ExpandLegalINT_TO_FP(
bool isSigned,
2438 SDValue WordOff = DAG.getConstant(
sizeof(
int), dl,
2443 StackSlot, WordOff);
2444 if (DAG.getDataLayout().isLittleEndian())
2457 SDValue Store1 = DAG.getStore(DAG.getEntryNode(), dl,
2463 SDValue Store2 = DAG.getStore(Store1, dl, InitialHi, Hi,
2470 SDValue Bias = DAG.getConstantFP(isSigned ?
2484 DAG.getIntPtrConstant(0, dl));
2490 assert(!isSigned &&
"Legalize cannot Expand SINT_TO_FP for i64 yet");
2500 DAG.getConstant(UINT64_C(0x4330000000000000), dl,
MVT::i64);
2502 DAG.getConstantFP(
BitsToDouble(UINT64_C(0x4530000000100000)), dl,
2505 DAG.getConstant(UINT64_C(0x4530000000000000), dl,
MVT::i64);
2509 DAG.getConstant(32, dl,
MVT::i64));
2527 SDValue ShiftConst = DAG.getConstant(
2528 1, dl, TLI.getShiftAmountTy(Op0.
getValueType(), DAG.getDataLayout()));
2543 return DAG.getSelect(dl,
MVT::f32, SignBitTest, Slow, Fast);
2549 DAG.getConstant(UINT64_C(0xfffffffffffff800), dl,
MVT::i64));
2551 DAG.getConstant(UINT64_C(0x800), dl,
MVT::i64));
2553 DAG.getConstant(UINT64_C(0x7ff), dl,
MVT::i64));
2555 DAG.getConstant(UINT64_C(0), dl,
MVT::i64),
2559 DAG.getConstant(UINT64_C(0x0020000000000000), dl,
2563 EVT SHVT = TLI.getShiftAmountTy(Sel2.
getValueType(), DAG.getDataLayout());
2566 DAG.getConstant(32, dl, SHVT));
2570 DAG.getConstantFP(
BitsToDouble(UINT64_C(0x41f0000000000000)), dl,
2577 DAG.getIntPtrConstant(0, dl));
2586 SDValue Zero = DAG.getIntPtrConstant(0, dl),
2587 Four = DAG.getIntPtrConstant(4, dl);
2589 SignSet, Four, Zero);
2597 case MVT::i8 : FF = 0x43800000ULL;
break;
2598 case MVT::i16: FF = 0x47800000ULL;
break;
2599 case MVT::i32: FF = 0x4F800000ULL;
break;
2600 case MVT::i64: FF = 0x5F800000ULL;
break;
2602 if (DAG.getDataLayout().isLittleEndian())
2608 DAG.getConstantPool(FudgeFactor, TLI.getPointerTy(DAG.getDataLayout()));
2609 unsigned Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlignment();
2611 Alignment =
std::min(Alignment, 4u);
2614 FudgeInReg = DAG.getLoad(
MVT::f32, dl, DAG.getEntryNode(), CPIdx,
2616 false,
false,
false, Alignment);
2619 DAG.getEntryNode(), CPIdx,
2621 MVT::f32,
false,
false,
false, Alignment);
2635 SDValue SelectionDAGLegalize::PromoteLegalINT_TO_FP(
SDValue LegalOp,
2642 unsigned OpToUse = 0;
2647 assert(NewInTy.
isInteger() &&
"Ran out of possibilities!");
2654 if (isSigned)
continue;
2667 return DAG.getNode(OpToUse, dl, DestVT,
2669 dl, NewInTy, LegalOp));
2677 SDValue SelectionDAGLegalize::PromoteLegalFP_TO_INT(
SDValue LegalOp,
2682 EVT NewOutTy = DestVT;
2684 unsigned OpToUse = 0;
2689 assert(NewOutTy.
isInteger() &&
"Ran out of possibilities!");
2699 if (!isSigned && TLI.isOperationLegalOrCustom(
ISD::FP_TO_UINT, NewOutTy)) {
2719 EVT SHVT = TLI.getShiftAmountTy(VT, DAG.getDataLayout());
2720 SDValue Tmp1, Tmp2, Tmp3, Tmp4, Tmp5, Tmp6, Tmp7, Tmp8;
2724 Tmp2 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(8, dl, SHVT));
2725 Tmp1 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(8, dl, SHVT));
2726 return DAG.getNode(
ISD::OR, dl, VT, Tmp1, Tmp2);
2728 Tmp4 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(24, dl, SHVT));
2729 Tmp3 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(8, dl, SHVT));
2730 Tmp2 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(8, dl, SHVT));
2731 Tmp1 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(24, dl, SHVT));
2733 DAG.getConstant(0xFF0000, dl, VT));
2734 Tmp2 = DAG.
getNode(
ISD::AND, dl, VT, Tmp2, DAG.getConstant(0xFF00, dl, VT));
2737 return DAG.getNode(
ISD::OR, dl, VT, Tmp4, Tmp2);
2739 Tmp8 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(56, dl, SHVT));
2740 Tmp7 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(40, dl, SHVT));
2741 Tmp6 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(24, dl, SHVT));
2742 Tmp5 = DAG.
getNode(
ISD::SHL, dl, VT, Op, DAG.getConstant(8, dl, SHVT));
2743 Tmp4 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(8, dl, SHVT));
2744 Tmp3 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(24, dl, SHVT));
2745 Tmp2 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(40, dl, SHVT));
2746 Tmp1 = DAG.
getNode(
ISD::SRL, dl, VT, Op, DAG.getConstant(56, dl, SHVT));
2748 DAG.getConstant(255ULL<<48, dl, VT));
2750 DAG.getConstant(255ULL<<40, dl, VT));
2752 DAG.getConstant(255ULL<<32, dl, VT));
2754 DAG.getConstant(255ULL<<24, dl, VT));
2756 DAG.getConstant(255ULL<<16, dl, VT));
2758 DAG.getConstant(255ULL<<8 , dl, VT));
2765 return DAG.getNode(
ISD::OR, dl, VT, Tmp8, Tmp4);
2770 SDValue SelectionDAGLegalize::ExpandBitCount(
unsigned Opc,
SDValue Op,
2776 EVT ShVT = TLI.getShiftAmountTy(VT, DAG.getDataLayout());
2779 assert(VT.
isInteger() && Len <= 128 && Len % 8 == 0 &&
2780 "CTPOP not implemented for this type.");
2798 DAG.getConstant(1, dl, ShVT)),
2802 DAG.getNode(
ISD::AND, dl, VT, Op, Mask33),
2805 DAG.getConstant(2, dl, ShVT)),
2811 DAG.getConstant(4, dl, ShVT))),
2815 DAG.getNode(
ISD::MUL, dl, VT, Op, Mask01),
2816 DAG.getConstant(Len - 8, dl, ShVT));
2834 EVT ShVT = TLI.getShiftAmountTy(VT, DAG.getDataLayout());
2836 for (
unsigned i = 0; (1U << i) <= (len / 2); ++i) {
2837 SDValue Tmp3 = DAG.getConstant(1ULL << i, dl, ShVT);
2841 Op = DAG.getNOT(dl, Op, VT);
2854 DAG.getNOT(dl, Op, VT),
2856 DAG.getConstant(1, dl, VT)));
2858 if (!TLI.isOperationLegalOrCustom(
ISD::CTPOP, VT) &&
2859 TLI.isOperationLegalOrCustom(
ISD::CTLZ, VT))
2860 return DAG.getNode(
ISD::SUB, dl, VT,
2863 return DAG.getNode(
ISD::CTPOP, dl, VT, Tmp3);
2868 std::pair <SDValue, SDValue> SelectionDAGLegalize::ExpandAtomic(
SDNode *Node) {
2874 return ExpandChainLibCall(LC, Node,
false);
2877 void SelectionDAGLegalize::ExpandNode(
SDNode *Node) {
2880 SDValue Tmp1, Tmp2, Tmp3, Tmp4;
2926 DAG.getExternalSymbol(
"__sync_synchronize",
2927 TLI.getPointerTy(DAG.getDataLayout())),
2928 std::move(Args), 0);
2930 std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI);
2939 SDValue Swap = DAG.getAtomicCmpSwap(
2942 cast<AtomicSDNode>(Node)->getMemOperand(),
2943 cast<AtomicSDNode>(Node)->getOrdering(),
2944 cast<AtomicSDNode>(Node)->getOrdering(),
2945 cast<AtomicSDNode>(Node)->getSynchScope());
2953 cast<AtomicSDNode>(Node)->getMemoryVT(),
2956 cast<AtomicSDNode>(Node)->getMemOperand(),
2957 cast<AtomicSDNode>(Node)->getOrdering(),
2958 cast<AtomicSDNode>(Node)->getSynchScope());
2977 std::pair<SDValue, SDValue> Tmp = ExpandAtomic(Node);
2987 SDValue Res = DAG.getAtomicCmpSwap(
2990 Node->
getOperand(3), cast<MemSDNode>(Node)->getMemOperand(),
2991 cast<AtomicSDNode>(Node)->getSuccessOrdering(),
2992 cast<AtomicSDNode>(Node)->getFailureOrdering(),
2993 cast<AtomicSDNode>(Node)->getSynchScope());
3004 ExpandDYNAMIC_STACKALLOC(Node, Results);
3013 Results.
push_back(DAG.getConstant(0, dl, VT));
3016 Results.
push_back(DAG.getConstantFP(0, dl, VT));
3027 DAG.getExternalSymbol(
"abort",
3028 TLI.getPointerTy(DAG.getDataLayout())),
3029 std::move(Args), 0);
3030 std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI);
3052 EVT ShiftAmountTy = TLI.getShiftAmountTy(VT, DAG.getDataLayout());
3057 SDValue ShiftCst = DAG.getConstant(BitsDiff, dl, ShiftAmountTy);
3072 Tmp1 = EmitStackConvert(Node->
getOperand(0), ExtraVT,
3084 if (TLI.expandFP_TO_SINT(Node, Tmp1, DAG))
3091 APFloat apf(DAG.EVTToAPFloatSemantics(VT),
3095 Tmp1 = DAG.getConstantFP(apf, dl, VT);
3096 Tmp2 = DAG.getSetCC(dl, getSetCCResultType(VT),
3104 DAG.getConstant(x, dl, NVT));
3105 Tmp1 = DAG.getSelect(dl, NVT, Tmp2, True, False);
3110 const Value *V = cast<SrcValueSDNode>(Node->
getOperand(2))->getValue();
3117 DAG.getLoad(TLI.getPointerTy(DAG.getDataLayout()), dl, Tmp1, Tmp2,
3121 if (Align > TLI.getMinStackArgumentAlignment()) {
3122 assert(((Align & (Align-1)) == 0) &&
"Expected Align to be a power of 2");
3125 DAG.getConstant(Align - 1, dl,
3129 DAG.getConstant(-(int64_t)Align, dl,
3135 DAG.getConstant(DAG.getDataLayout().getTypeAllocSize(
3139 Tmp3 = DAG.getStore(VAListLoad.
getValue(1), dl, Tmp3, Tmp2,
3143 false,
false,
false, 0));
3144 Results.
push_back(Results[0].getValue(1));
3150 const Value *VD = cast<SrcValueSDNode>(Node->
getOperand(3))->getValue();
3151 const Value *
VS = cast<SrcValueSDNode>(Node->
getOperand(4))->getValue();
3152 Tmp1 = DAG.getLoad(TLI.getPointerTy(DAG.getDataLayout()), dl,
3166 Tmp1 = ExpandExtractFromVectorThroughStack(
SDValue(Node, 0));
3176 Results.
push_back(ExpandVectorBuildThroughStack(Node));
3180 Results.
push_back(ExpandSCALAR_TO_VECTOR(Node));
3189 ArrayRef<int> Mask = cast<ShuffleVectorSDNode>(Node)->getMask();
3195 if (!TLI.isTypeLegal(EltVT)) {
3197 EVT NewEltVT = TLI.getTypeToTransformTo(*DAG.getContext(), EltVT);
3202 if (NewEltVT.
bitsLT(EltVT)) {
3212 assert(NewVT.
bitsEq(VT));
3219 unsigned int factor =
3227 for (
unsigned fi = 0; fi < factor; ++fi)
3231 for (
unsigned fi = 0; fi < factor; ++fi)
3242 for (
unsigned i = 0; i != NumElems; ++i) {
3247 unsigned Idx = Mask[i];
3251 DAG.getConstant(Idx, dl, TLI.getVectorIdxTy(DAG.getDataLayout()))));
3255 DAG.getConstant(Idx - NumElems, dl,
3256 TLI.getVectorIdxTy(DAG.getDataLayout()))));
3267 if (cast<ConstantSDNode>(Node->
getOperand(1))->getZExtValue()) {
3271 TLI.getShiftAmountTy(
3273 DAG.getDataLayout())));
3286 if (
unsigned SP = TLI.getStackPointerRegisterToSaveRestore()) {
3289 Results.
push_back(Results[0].getValue(1));
3298 if (
unsigned SP = TLI.getStackPointerRegisterToSaveRestore()) {
3306 Results.
push_back(ExpandFCOPYSIGN(Node));
3310 Tmp1 = DAG.getConstantFP(-0.0, dl, Node->
getValueType(0));
3319 Tmp2 = DAG.getConstantFP(0.0, dl, VT);
3320 Tmp2 = DAG.getSetCC(dl, getSetCCResultType(Tmp1.getValueType()),
3323 Tmp1 = DAG.getSelect(dl, VT, Tmp2, Tmp1, Tmp3);
3342 Tmp1 = DAG.getSelectCC(dl, Tmp1, Tmp2, Tmp1, Tmp2, Pred);
3371 SDVTList VTs = DAG.getVTList(VT, VT);
3374 Tmp1 = Tmp1.getValue(1);
3389 ExpandSinCosLibCall(Node, Results);
3504 if (!TLI.useSoftFloat() &&
TM.Options.UnsafeFPMath) {
3512 DAG.getIntPtrConstant(0, dl));
3522 Results.
push_back(ExpandLibCall(LC, Node,
false));
3530 Results.
push_back(ExpandConstantFP(CFP,
true));
3535 if (TLI.isOperationLegalOrCustom(
ISD::FADD, VT) &&
3536 TLI.isOperationLegalOrCustom(
ISD::FNEG, VT)) {
3549 assert(TLI.isOperationLegalOrCustom(
ISD::ADD, VT) &&
3550 TLI.isOperationLegalOrCustom(
ISD::XOR, VT) &&
3551 "Don't know how to expand this subtraction!");
3555 Tmp1 = DAG.getNode(
ISD::ADD, dl, VT, Tmp1, DAG.getConstant(1, dl, VT));
3567 if (TLI.isOperationLegalOrCustom(DivRemOpc, VT) ||
3570 !TLI.isOperationLegalOrCustom(DivOpc, Node->
getValueType(0)) &&
3572 SDVTList VTs = DAG.getVTList(VT, VT);
3573 Tmp1 = DAG.getNode(DivRemOpc, dl, VTs, Tmp2, Tmp3).getValue(1);
3574 }
else if (TLI.isOperationLegalOrCustom(DivOpc, VT)) {
3576 Tmp1 = DAG.getNode(DivOpc, dl, VT, Tmp2, Tmp3);
3577 Tmp1 = DAG.getNode(
ISD::MUL, dl, VT, Tmp1, Tmp3);
3578 Tmp1 = DAG.getNode(
ISD::SUB, dl, VT, Tmp2, Tmp1);
3579 }
else if (isSigned)
3580 Tmp1 = ExpandIntLibCall(Node,
true,
3585 Tmp1 = ExpandIntLibCall(Node,
false,
3597 SDVTList VTs = DAG.getVTList(VT, VT);
3598 if (TLI.isOperationLegalOrCustom(DivRemOpc, VT) ||
3601 Tmp1 = DAG.getNode(DivRemOpc, dl, VTs, Node->
getOperand(0),
3604 Tmp1 = ExpandIntLibCall(Node,
true,
3609 Tmp1 = ExpandIntLibCall(Node,
false,
3621 SDVTList VTs = DAG.getVTList(VT, VT);
3622 assert(TLI.isOperationLegalOrCustom(ExpandOpcode, VT) &&
3623 "If this wasn't legal, it shouldn't have been created!");
3624 Tmp1 = DAG.getNode(ExpandOpcode, dl, VTs, Node->
getOperand(0),
3632 ExpandDivRemLibCall(Node, Results);
3636 SDVTList VTs = DAG.getVTList(VT, VT);
3642 bool HasSMUL_LOHI = TLI.isOperationLegalOrCustom(
ISD::SMUL_LOHI, VT);
3643 bool HasUMUL_LOHI = TLI.isOperationLegalOrCustom(
ISD::UMUL_LOHI, VT);
3644 bool HasMULHS = TLI.isOperationLegalOrCustom(
ISD::MULHS, VT);
3645 bool HasMULHU = TLI.isOperationLegalOrCustom(
ISD::MULHU, VT);
3646 unsigned OpToUse = 0;
3647 if (HasSMUL_LOHI && !HasMULHS) {
3649 }
else if (HasUMUL_LOHI && !HasMULHU) {
3651 }
else if (HasSMUL_LOHI) {
3653 }
else if (HasUMUL_LOHI) {
3666 TLI.isOperationLegalOrCustom(
ISD::SHL, VT) &&
3667 TLI.isOperationLegalOrCustom(
ISD::OR, VT) &&
3668 TLI.expandMUL(Node, Lo, Hi, HalfType, DAG)) {
3673 TLI.getShiftAmountTy(HalfType, DAG.getDataLayout()));
3679 Tmp1 = ExpandIntLibCall(Node,
false,
3710 SDValue SignsMatch = DAG.getSetCC(dl, OType, LHSSign, RHSSign,
3718 Results.
push_back(DAG.getBoolExtOrTrunc(Cmp, dl, ResultType, ResultType));
3734 SDValue SetCC = DAG.getSetCC(dl, SetCCType, Sum, LHS, CC);
3736 Results.
push_back(DAG.getBoolExtOrTrunc(SetCC, dl, ResultType, ResultType));
3747 static const unsigned Ops[2][3] =
3751 if (TLI.isOperationLegalOrCustom(Ops[isSigned][0], VT)) {
3753 TopHalf = DAG.
getNode(Ops[isSigned][0], dl, VT, LHS, RHS);
3754 }
else if (TLI.isOperationLegalOrCustom(Ops[isSigned][1], VT)) {
3755 BottomHalf = DAG.
getNode(Ops[isSigned][1], dl, DAG.getVTList(VT, VT), LHS,
3758 }
else if (TLI.isTypeLegal(WideVT)) {
3759 LHS = DAG.
getNode(Ops[isSigned][2], dl, WideVT, LHS);
3760 RHS = DAG.
getNode(Ops[isSigned][2], dl, WideVT, RHS);
3761 Tmp1 = DAG.getNode(
ISD::MUL, dl, WideVT, LHS, RHS);
3763 DAG.getIntPtrConstant(0, dl));
3765 DAG.getIntPtrConstant(1, dl));
3787 DAG.getConstant(LoSize - 1, dl,
3788 TLI.getPointerTy(DAG.getDataLayout())));
3791 DAG.getConstant(LoSize - 1, dl,
3792 TLI.getPointerTy(DAG.getDataLayout())));
3798 SDValue Args[] = { LHS, HiLHS, RHS, HiRHS };
3799 SDValue Ret = ExpandLibCall(LC, WideVT, Args, 4, isSigned, dl);
3801 DAG.getIntPtrConstant(0, dl));
3803 DAG.getIntPtrConstant(1, dl));
3809 "Unexpected uses of illegally type from expanded lib call.");
3813 Tmp1 = DAG.getConstant(
3815 TLI.getShiftAmountTy(BottomHalf.
getValueType(), DAG.getDataLayout()));
3816 Tmp1 = DAG.getNode(
ISD::SRA, dl, VT, BottomHalf, Tmp1);
3817 TopHalf = DAG.getSetCC(dl, getSetCCResultType(VT), TopHalf, Tmp1,
3820 TopHalf = DAG.getSetCC(dl, getSetCCResultType(VT), TopHalf,
3834 TLI.getShiftAmountTy(PairTy, DAG.getDataLayout())));
3843 Tmp1 = DAG.getSelectCC(dl, Tmp1.getOperand(0), Tmp1.getOperand(1),
3845 cast<CondCodeSDNode>(Tmp1.getOperand(2))->
get());
3847 Tmp1 = DAG.getSelectCC(dl, Tmp1,
3848 DAG.getConstant(0, dl, Tmp1.getValueType()),
3858 EVT PTy = TLI.getPointerTy(DAG.getDataLayout());
3861 unsigned EntrySize =
3862 DAG.getMachineFunction().getJumpTableInfo()->getEntrySize(TD);
3872 false,
false,
false, 0);
3879 TLI.getPICJumpTableRelocBase(Table, DAG));
3892 Tmp1, Tmp2.getOperand(2),
3893 Tmp2.getOperand(0), Tmp2.getOperand(1),
3897 Tmp3 = (Tmp2.getOpcode() ==
ISD::UNDEF) ? Tmp2 :
3898 DAG.getNode(
ISD::AND, dl, Tmp2.getValueType(), Tmp2,
3899 DAG.getConstant(1, dl, Tmp2.getValueType()));
3902 DAG.getConstant(0, dl, Tmp3.getValueType()),
3911 bool Legalized = LegalizeSetCCCondCode(Node->
getValueType(0), Tmp1, Tmp2,
3912 Tmp3, NeedInvert, dl);
3924 Tmp1 = DAG.getLogicalNOT(dl, Tmp1, Tmp1->getValueType(0));
3934 switch (TLI.getBooleanContents(Tmp1->getValueType(0))) {
3944 DAG.getConstant(TrueValue, dl, VT),
3945 DAG.getConstant(0, dl, VT),
3959 if (TLI.isCondCodeLegal(CCOp, Tmp1.getSimpleValueType())) {
3962 EVT CmpVT = Tmp1.getValueType();
3964 "Cannot expand ISD::SELECT_CC when ISD::SELECT also needs to be "
3967 TLI.getSetCCResultType(DAG.getDataLayout(), *DAG.getContext(), CmpVT);
3969 Results.
push_back(DAG.getSelect(dl, VT, Cond, Tmp3, Tmp4));
3974 bool Legalized =
false;
3979 Tmp1.getValueType().isInteger());
3980 if (TLI.isCondCodeLegal(InvCC, Tmp1.getSimpleValueType())) {
3983 Tmp1 = DAG.getSelectCC(dl, Tmp1, Tmp2, Tmp4, Tmp3, InvCC);
3988 if (TLI.isCondCodeLegal(SwapInvCC, Tmp1.getSimpleValueType())) {
3992 Tmp1 = DAG.getSelectCC(dl, Tmp2, Tmp1, Tmp4, Tmp3, SwapInvCC);
3997 Legalized = LegalizeSetCCCondCode(
3998 getSetCCResultType(Tmp1.getValueType()), Tmp1, Tmp2, CC, NeedInvert,
4001 assert(Legalized &&
"Can't legalize SELECT_CC with legal condition!");
4012 Tmp1, Tmp2, Tmp3, Tmp4, CC);
4014 Tmp2 = DAG.getConstant(0, dl, Tmp1.getValueType());
4017 Tmp2, Tmp3, Tmp4, CC);
4029 bool Legalized = LegalizeSetCCCondCode(getSetCCResultType(
4030 Tmp2.getValueType()), Tmp2, Tmp3, Tmp4, NeedInvert, dl);
4032 assert(Legalized &&
"Can't legalize BR_CC with legal condition!");
4045 Tmp3 = DAG.getConstant(0, dl, Tmp2.getValueType());
4054 Results.
push_back(ExpandBUILD_VECTOR(Node));
4061 assert(VT.
isVector() &&
"Unable to legalize non-vector shift");
4062 assert(TLI.isTypeLegal(VT.
getScalarType())&&
"Element type must be legal");
4066 for (
unsigned Idx = 0; Idx < NumElem; Idx++) {
4069 DAG.getConstant(Idx, dl, TLI.getVectorIdxTy(DAG.getDataLayout())));
4072 DAG.getConstant(Idx, dl, TLI.getVectorIdxTy(DAG.getDataLayout())));
4078 ReplaceNode(
SDValue(Node, 0), Result);
4095 if (!Results.
empty())
4096 ReplaceNode(Node, Results.
data());
4099 void SelectionDAGLegalize::PromoteNode(
SDNode *Node) {
4109 MVT NVT = TLI.getTypeToPromoteTo(Node->
getOpcode(), OVT);
4125 Tmp2 = DAG.getSetCC(dl, getSetCCResultType(NVT),
4126 Tmp1, DAG.getConstant(NVT.getSizeInBits(), dl, NVT),
4128 Tmp1 = DAG.getSelect(dl, NVT, Tmp2,
4134 DAG.getConstant(NVT.getSizeInBits() -
4140 unsigned DiffBits = NVT.getSizeInBits() - OVT.
getSizeInBits();
4145 DAG.getConstant(DiffBits, dl,
4146 TLI.getShiftAmountTy(NVT, DAG.getDataLayout())));
4171 &&
"VAARG promotion is supported only for vectors or integer types");
4176 Tmp1 = DAG.getVAArg(NVT, dl, Chain, Ptr, Node->
getOperand(2),
4180 Tmp2 = DAG.
getNode(TruncOp, dl, OVT, Tmp1);
4184 DAG.ReplaceAllUsesOfValueWith(
SDValue(Node, 0), Tmp2);
4185 DAG.ReplaceAllUsesOfValueWith(
SDValue(Node, 1), Chain);
4187 UpdatedNodes->insert(Tmp2.
getNode());
4188 UpdatedNodes->insert(Chain.
getNode());
4196 unsigned ExtOp, TruncOp;
4201 assert(OVT.
isInteger() &&
"Cannot promote logic operation");
4210 Results.
push_back(DAG.getNode(TruncOp, dl, OVT, Tmp1));
4214 unsigned ExtOp, TruncOp;
4231 Tmp1 = DAG.getSelect(dl, NVT, Tmp1, Tmp2, Tmp3);
4233 Tmp1 = DAG.getNode(TruncOp, dl, Node->
getValueType(0), Tmp1);
4235 Tmp1 = DAG.getNode(TruncOp, dl, Node->
getValueType(0), Tmp1,
4236 DAG.getIntPtrConstant(0, dl));
4241 ArrayRef<int> Mask = cast<ShuffleVectorSDNode>(Node)->getMask();
4248 Tmp1 = ShuffleWithNarrowerEltType(NVT, OVT, dl, Tmp1, Tmp2, Mask);
4255 if (NVT.isInteger()) {
4257 cast<CondCodeSDNode>(Node->
getOperand(2))->
get();
4260 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->
getOperand(0));
4268 if (NVT.isInteger()) {
4270 cast<CondCodeSDNode>(Node->
getOperand(1))->
get();
4273 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->
getOperand(2));
4274 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->
getOperand(3));
4293 Tmp3, DAG.getIntPtrConstant(0, dl)));
4302 DAG.getNode(Node->
getOpcode(), dl, NVT, Tmp1, Tmp2, Tmp3),
4303 DAG.getIntPtrConstant(0, dl)));
4311 Tmp3, DAG.getIntPtrConstant(0, dl)));
4331 Tmp2 = DAG.getNode(Node->
getOpcode(), dl, NVT, Tmp1);
4333 Tmp2, DAG.getIntPtrConstant(0, dl)));
4339 if (!Results.
empty())
4340 ReplaceNode(Node, Results.
data());
4348 SelectionDAGLegalize Legalizer(*
this, LegalizedNodes);
4355 bool AnyLegalized =
false;
4366 if (LegalizedNodes.
insert(N).second) {
4367 AnyLegalized =
true;
4368 Legalizer.LegalizeOp(N);
4388 SelectionDAGLegalize Legalizer(*
this, LegalizedNodes, &UpdatedNodes);
4392 LegalizedNodes.
insert(N);
4393 Legalizer.LegalizeOp(N);
4395 return LegalizedNodes.
count(N);
MVT getSimpleValueType() const
Return the simple ValueType of the referenced return value.
bool LegalizeOp(SDNode *N, SmallSetVector< SDNode *, 16 > &UpdatedNodes)
Transforms a SelectionDAG node and any operands to it into a node that is compatible with the target ...
SDValue getTruncStore(SDValue Chain, SDLoc dl, SDValue Val, SDValue Ptr, MachinePointerInfo PtrInfo, EVT TVT, bool isNonTemporal, bool isVolatile, unsigned Alignment, const AAMDNodes &AAInfo=AAMDNodes())
ADJUST_TRAMPOLINE - This corresponds to the adjust_trampoline intrinsic.
static Constant * getFPTrunc(Constant *C, Type *Ty, bool OnlyIfReduced=false)
BITCAST - This operator converts between integer, vector and FP values, as if the value was stored to...
X = FP_ROUND(Y, TRUNC) - Rounding 'Y' from a larger floating point type down to the precision of the ...
bool use_empty() const
Return true if there are no uses of this node.
void push_back(const T &Elt)
BUILTIN_OP_END - This must be the last enum value in this list.
A parsed version of the target data layout string in and methods for querying it. ...
SDValue getValue(unsigned R) const
static APInt getSignBit(unsigned BitWidth)
Get the SignBit for a specific bit width.
EXTRACT_ELEMENT - This is used to get the lower or upper (determined by a Constant, which is required to be operand #1) half of the integer or float value specified as operand #0.
static void ExpandUnalignedLoad(LoadSDNode *LD, SelectionDAG &DAG, const TargetLowering &TLI, SDValue &ValResult, SDValue &ChainResult)
Expands an unaligned load to 2 half-size loads.
static APInt getAllOnesValue(unsigned numBits)
Get the all-ones value.
LLVMContext * getContext() const
void dump() const
Dump this node, for debugging.
NodeType getExtForLoadExtType(bool IsFP, LoadExtType)
EXTRACT_SUBVECTOR(VECTOR, IDX) - Returns a subvector from VECTOR (an vector value) starting with the ...
BR_CC - Conditional branch.
VECTOR_SHUFFLE(VEC1, VEC2) - Returns a vector, of the same type as VEC1/VEC2.
static MachinePointerInfo getJumpTable()
getJumpTable - Return a MachinePointerInfo record that refers to a jump table entry.
SDVTList getVTList() const
const TargetMachine & getTarget() const
STACKRESTORE has two operands, an input chain and a pointer to restore to it returns an output chain...
size_type count(PtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
static bool isDivRemLibcallAvailable(SDNode *Node, bool isSigned, const TargetLowering &TLI)
Return true if divmod libcall is available.
Libcall
RTLIB::Libcall enum - This enum defines all of the runtime library calls the backend can emit...
RESULT, BOOL = [SU]ADDO(LHS, RHS) - Overflow-aware nodes for addition.
unsigned getOpcode() const
Return the SelectionDAG opcode value for this node.
Type * getTypeForEVT(LLVMContext &Context) const
getTypeForEVT - This method returns an LLVM type corresponding to the specified EVT.
unsigned getSizeInBits() const
SDValue getLoad(EVT VT, SDLoc dl, SDValue Chain, SDValue Ptr, MachinePointerInfo PtrInfo, bool isVolatile, bool isNonTemporal, bool isInvariant, unsigned Alignment, const AAMDNodes &AAInfo=AAMDNodes(), const MDNode *Ranges=nullptr)
Loads are not normal binary operators: their result type is not determined by their operands...
Val, Success, OUTCHAIN = ATOMIC_CMP_SWAP_WITH_SUCCESS(INCHAIN, ptr, cmp, swap) N.b.
unsigned getNumOperands() const
Return the number of values used by this operation.
const SDValue & getOperand(unsigned Num) const
static MachinePointerInfo getConstantPool()
getConstantPool - Return a MachinePointerInfo record that refers to the constant pool.
static IntegerType * getInt64Ty(LLVMContext &C)
[US]{MIN/MAX} - Binary minimum or maximum or signed or unsigned integers.
void reserve(size_type N)
void DeleteNode(SDNode *N)
Remove the specified node from the system.
const SDValue & getBasePtr() const
INSERT_SUBVECTOR(VECTOR1, VECTOR2, IDX) - Returns a vector with VECTOR2 inserted into VECTOR1 at the ...
OUTCHAIN = ATOMIC_FENCE(INCHAIN, ordering, scope) This corresponds to the fence instruction.
Select with condition operator - This selects between a true value and a false value (ops #2 and #3) ...
unsigned getResNo() const
get the index which selects a specific result in the SDNode
Libcall getFPROUND(EVT OpVT, EVT RetVT)
getFPROUND - Return the FPROUND_*_* value for the given types, or UNKNOWN_LIBCALL if there is none...
bool bitsLT(EVT VT) const
bitsLT - Return true if this has less bits than VT.
static MachinePointerInfo getFixedStack(int FI, int64_t offset=0)
getFixedStack - Return a MachinePointerInfo record that refers to the the specified FrameIndex...
RESULT,OUTCHAIN = INTRINSIC_W_CHAIN(INCHAIN, INTRINSICID, arg1, ...) This node represents a target in...
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
const Triple & getTargetTriple() const
OUTCHAIN = EH_SJLJ_LONGJMP(INCHAIN, buffer) This corresponds to the eh.sjlj.longjmp intrinsic...
SDIVREM/UDIVREM - Divide two integers and produce both a quotient and remainder result.
SHL_PARTS/SRA_PARTS/SRL_PARTS - These operators are used for expanded integer shift operations...
bool isVector() const
isVector - Return true if this is a vector value type.
SDValue getStore(SDValue Chain, SDLoc dl, SDValue Val, SDValue Ptr, MachinePointerInfo PtrInfo, bool isVolatile, bool isNonTemporal, unsigned Alignment, const AAMDNodes &AAInfo=AAMDNodes())
Helper function to build ISD::STORE nodes.
Shift and rotation operations.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
EVT getValueType(unsigned ResNo) const
Return the type of a specified result.
APInt LLVM_ATTRIBUTE_UNUSED_RESULT lshr(unsigned shiftAmt) const
Logical right-shift function.
BUILD_PAIR - This is the opposite of EXTRACT_ELEMENT in some ways.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
static Constant * get(ArrayRef< Constant * > V)
FLT_ROUNDS_ - Returns current rounding mode: -1 Undefined 0 Round to 0 1 Round to nearest 2 Round to ...
MachinePointerInfo getWithOffset(int64_t O) const
CALLSEQ_START/CALLSEQ_END - These operators mark the beginning and end of a call sequence, and carry arbitrary information that target might want to know.
EVT getScalarType() const
getScalarType - If this is a vector type, return the element type, otherwise return this...
Val, OUTCHAIN = ATOMIC_SWAP(INCHAIN, ptr, amt) Val, OUTCHAIN = ATOMIC_LOAD_[OpName](INCHAIN, ptr, amt) For double-word atomic operations: ValLo, ValHi, OUTCHAIN = ATOMIC_SWAP(INCHAIN, ptr, amtLo, amtHi) ValLo, ValHi, OUTCHAIN = ATOMIC_LOAD_[OpName](INCHAIN, ptr, amtLo, amtHi) These correspond to the atomicrmw instruction.
Number of individual test Apply this number of consecutive mutations to each input exit after the first new interesting input is found the minimized corpus is saved into the first input directory Number of jobs to run If min(jobs, NumberOfCpuCores()/2)\" is used.") FUZZER_FLAG_INT(reload
allnodes_const_iterator allnodes_end() const
bool bitsGE(EVT VT) const
bitsGE - Return true if this has no less bits than VT.
FRAMEADDR, RETURNADDR - These nodes represent llvm.frameaddress and llvm.returnaddress on the DAG...
This class defines information used to lower LLVM code to legal SelectionDAG operators that the targe...
bool isInteger() const
isInteger - Return true if this is an integer, or a vector integer type.
This represents a list of ValueType's that has been intern'd by a SelectionDAG.
STACKSAVE - STACKSAVE has one operand, an input chain.
FRAME_TO_ARGS_OFFSET - This node represents offset from frame pointer to first (possible) on-stack ar...
uint64_t getZExtValue() const
Return the constant as a 64-bit unsigned integer value after it has been zero extended as appropriate...
EVT getVectorElementType() const
getVectorElementType - Given a vector type, return the type of each element.
unsigned AssignTopologicalOrder()
Topological-sort the AllNodes list and a assign a unique node id for each node in the DAG based on th...
[SU]INT_TO_FP - These operators convert integers (whose interpreted sign depends on the first letter)...
unsigned getNumValues() const
Return the number of values defined/returned by this operator.
bool LLVM_ATTRIBUTE_UNUSED_RESULT empty() const
Simple integer binary arithmetic operators.
SDValue getVectorShuffle(EVT VT, SDLoc dl, SDValue N1, SDValue N2, const int *MaskElts)
Return an ISD::VECTOR_SHUFFLE node.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory)...
bool isLittleEndian() const
Layout endianness...
const SDValue & getBasePtr() const
EVT getHalfSizedIntegerVT(LLVMContext &Context) const
getHalfSizedIntegerVT - Finds the smallest simple value type that is greater than or equal to half th...
SDValue getUNDEF(EVT VT)
Return an UNDEF node. UNDEF does not have a useful SDLoc.
CondCode
ISD::CondCode enum - These are ordered carefully to make the bitfields below work out...
TargetConstant* - Like Constant*, but the DAG does not do any folding, simplification, or lowering of the constant.
EVT getMemoryVT() const
Return the type of the in-memory value.
static void ExpandUnalignedStore(StoreSDNode *ST, SelectionDAG &DAG, const TargetLowering &TLI, SelectionDAGLegalize *DAGLegalize)
Expands an unaligned store to 2 half-size stores.
static bool useSinCos(SDNode *Node)
Only issue sincos libcall if both sin and cos are needed.
bool isSignedIntSetCC(CondCode Code)
isSignedIntSetCC - Return true if this is a setcc instruction that performs a signed comparison when ...
RESULT = INTRINSIC_WO_CHAIN(INTRINSICID, arg1, arg2, ...) This node represents a target intrinsic fun...
const DataLayout & getDataLayout() const
UNDEF - An undefined node.
This class is used to represent ISD::STORE nodes.
FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
BUILD_VECTOR(ELT0, ELT1, ELT2, ELT3,...) - Return a vector with the specified, possibly variable...
static bool useDivRem(SDNode *Node, bool isSigned, bool isDIV)
Only issue divrem libcall if both quotient and remainder are needed.
SDNode * getNode() const
get the SDNode which holds the desired result
A self-contained host- and target-independent arbitrary-precision floating-point software implementat...
bool isTypeLegal(EVT VT) const
Return true if the target has native support for the specified value type.
OUTCHAIN = INTRINSIC_VOID(INCHAIN, INTRINSICID, arg1, arg2, ...) This node represents a target intrin...
unsigned UnsafeFPMath
UnsafeFPMath - This flag is enabled when the -enable-unsafe-fp-math flag is specified on the command ...
unsigned getStoreSizeInBits() const
getStoreSizeInBits - Return the number of bits overwritten by a store of the specified value type...
bool isInteger() const
isInteger - Return true if this is an integer, or a vector integer type.
virtual bool isShuffleMaskLegal(const SmallVectorImpl< int > &, EVT) const
Targets can use this to indicate that they only support some VECTOR_SHUFFLE operations, those with specific masks.
READ_REGISTER, WRITE_REGISTER - This node represents llvm.register on the DAG, which implements the n...
APInt LLVM_ATTRIBUTE_UNUSED_RESULT trunc(unsigned width) const
Truncate to new width.
void Legalize()
This transforms the SelectionDAG into a SelectionDAG that is compatible with the target instruction s...
MVT - Machine Value Type.
const SDValue & getOperand(unsigned i) const
The instances of the Type class are immutable: once they are created, they are never changed...
void swap(SmallVectorImpl &RHS)
Simple binary floating point operators.
bool isNonTemporal() const
This is an important base class in LLVM.
VAEND, VASTART - VAEND and VASTART have three operands: an input chain, pointer, and a SRCVALUE...
bool isVector() const
isVector - Return true if this is a vector value type.
LoadExtType
LoadExtType enum - This enum defines the three variants of LOADEXT (load with extension).
LegalizeAction
This enum indicates whether operations are valid for a target, and if not, what action should be used...
INSERT_VECTOR_ELT(VECTOR, VAL, IDX) - Returns VECTOR with the element at IDX replaced with VAL...
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
This file contains the declarations for the subclasses of Constant, which represent the different fla...
APInt Or(const APInt &LHS, const APInt &RHS)
Bitwise OR function for APInt.
ConstantFP - Floating Point Values [float, double].
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
void RemoveDeadNodes()
This method deletes all unreachable nodes in the SelectionDAG.
static Type * getVoidTy(LLVMContext &C)
This class provides iterator support for SDUse operands that use a specific SDNode.
INIT_TRAMPOLINE - This corresponds to the init_trampoline intrinsic.
unsigned getOpcode() const
TRAP - Trapping instruction.
MVT getRegisterType(MVT VT) const
Return the type of registers that this ValueType will eventually require.
DEBUGTRAP - Trap intended to get the attention of a debugger.
CondCode getSetCCSwappedOperands(CondCode Operation)
getSetCCSwappedOperands - Return the operation corresponding to (Y op X) when given the operation for...
std::pair< NoneType, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
VAARG - VAARG has four operands: an input chain, a pointer, a SRCVALUE, and the alignment.
use_iterator use_begin() const
Provide iteration support to walk over all uses of an SDNode.
const SDValue & getValue() const
static bool isValueValidForType(EVT VT, const APFloat &Val)
SDValue getExtLoad(ISD::LoadExtType ExtType, SDLoc dl, EVT VT, SDValue Chain, SDValue Ptr, MachinePointerInfo PtrInfo, EVT MemVT, bool isVolatile, bool isNonTemporal, bool isInvariant, unsigned Alignment, const AAMDNodes &AAInfo=AAMDNodes())
Bit counting operators with an undefined result for zero inputs.
Val, OUTCHAIN = ATOMIC_CMP_SWAP(INCHAIN, ptr, cmp, swap) For double-word atomic operations: ValLo...
X = FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
EVT - Extended Value Type.
static UndefValue * get(Type *T)
get() - Static factory methods - Return an 'undef' object of the specified type.
std::vector< ArgListEntry > ArgListTy
const APFloat & getValueAPF() const
bool bitsEq(EVT VT) const
bitsEq - Return true if this has the same number of bits as VT.
const ConstantFP * getConstantFPValue() const
This structure contains all information that is necessary for lowering calls.
ISD::MemIndexedMode getAddressingMode() const
Return the addressing mode for this load or store: unindexed, pre-inc, pre-dec, post-inc, or post-dec.
PointerType * getPointerTo(unsigned AddrSpace=0)
getPointerTo - Return a pointer to the current type.
static EVT getVectorVT(LLVMContext &Context, EVT VT, unsigned NumElements)
getVectorVT - Returns the EVT that represents a vector NumElements in length, where each element is o...
MachinePointerInfo - This class contains a discriminated union of information about pointers in memor...
uint64_t getConstantOperandVal(unsigned Num) const
Helper method returns the integer value of a ConstantSDNode operand.
const SDValue & getRoot() const
Return the root tag of the SelectionDAG.
SDValue CreateStackTemporary(EVT VT, unsigned minAlign=1)
Create a stack temporary, suitable for holding the specified value type.
Triple - Helper class for working with autoconf configuration names.
EH_LABEL - Represents a label in mid basic block used to track locations needed for debug and excepti...
const MachinePointerInfo & getPointerInfo() const
bool bitsGT(EVT VT) const
bitsGT - Return true if this has more bits than VT.
TokenFactor - This node takes multiple tokens as input and produces a single token result...
A SetVector that performs no allocations if smaller than a certain size.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements...
This is the shared class of boolean and integer constants.
allnodes_const_iterator allnodes_begin() const
bool erase(PtrType Ptr)
erase - If the set contains the specified pointer, remove it and return true, otherwise return false...
const char * getLibcallName(RTLIB::Libcall Call) const
Get the libcall routine name for the specified libcall.
EXTRACT_VECTOR_ELT(VECTOR, IDX) - Returns a single element from VECTOR identified by the (potentially...
This is used to represent a portion of an LLVM function in a low-level Data Dependence DAG representa...
X = FP_ROUND_INREG(Y, VT) - This operator takes an FP register, and rounds it to a floating point val...
BRCOND - Conditional branch.
const SDValue & getChain() const
A collection of metadata nodes that might be associated with a memory access used by the alias-analys...
Byte Swap and Counting operators.
FP16_TO_FP, FP_TO_FP16 - These operators are used to perform promotions and truncation for half-preci...
MachineMemOperand * getMemOperand() const
Return a MachineMemOperand object describing the memory reference performed by operation.
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
static Constant * get(Type *Ty, uint64_t V, bool isSigned=false)
If Ty is a vector type, return a Constant with a splat of the given value.
Represents one node in the SelectionDAG.
CondCode getSetCCInverse(CondCode Operation, bool isInteger)
getSetCCInverse - Return the operation corresponding to !(X op Y), where 'op' is a valid SetCC operat...
static cl::opt< AlignMode > Align(cl::desc("Load/store alignment support"), cl::Hidden, cl::init(NoStrictAlign), cl::values(clEnumValN(StrictAlign,"aarch64-strict-align","Disallow all unaligned memory accesses"), clEnumValN(NoStrictAlign,"aarch64-no-strict-align","Allow unaligned memory accesses"), clEnumValEnd))
AAMDNodes getAAInfo() const
Returns the AA info that describes the dereference.
double BitsToDouble(uint64_t Bits)
BitsToDouble - This function takes a 64-bit integer and returns the bit equivalent double...
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
unsigned Log2_32(uint32_t Value)
Log2_32 - This function returns the floor log base 2 of the specified value, -1 if the value is zero...
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
static APInt getSplat(unsigned NewLen, const APInt &V)
Return a value containing V broadcasted over NewLen bits.
ISD::LoadExtType getExtensionType() const
Return whether this is a plain node, or one of the varieties of value-extending loads.
Class for arbitrary precision integers.
Select(COND, TRUEVAL, FALSEVAL).
op_iterator op_begin() const
static use_iterator use_end()
ZERO_EXTEND - Used for integer types, zeroing the new bits.
APInt bitcastToAPInt() const
SDValue getNode(unsigned Opcode, SDLoc DL, EVT VT, ArrayRef< SDUse > Ops)
Gets or creates the specified node.
ANY_EXTEND - Used for integer types. The high bits are undefined.
FCOPYSIGN(X, Y) - Return the value of X with the sign of Y.
iterator_range< value_op_iterator > op_values() const
APInt And(const APInt &LHS, const APInt &RHS)
Bitwise AND function for APInt.
unsigned getAddressSpace() const
Return the address space for the associated pointer.
BR_JT - Jumptable branch.
VACOPY - VACOPY has 5 operands: an input chain, a destination pointer, a source pointer, a SRCVALUE for the destination, and a SRCVALUE for the source.
uint64_t MinAlign(uint64_t A, uint64_t B)
MinAlign - A and B are either alignments or offsets.
Bitwise operators - logical and, logical or, logical xor.
pointer data()
Return a pointer to the vector's buffer, even if empty().
SMUL_LOHI/UMUL_LOHI - Multiply two integers of type iN, producing a signed/unsigned value of type i[2...
SIGN_EXTEND_INREG - This operator atomically performs a SHL/SRA pair to sign extend a small value in ...
LOAD and STORE have token chains as their first operand, then the same operands as an LLVM load/store...
unsigned getSizeInBits() const
getSizeInBits - Return the size of the specified value type in bits.
void ReplaceAllUsesWith(SDValue From, SDValue Op)
Modify anything using 'From' to use 'To' instead.
Fast - This calling convention attempts to make calls as fast as possible (e.g.
bool isIndexed() const
Return true if this is a pre/post inc/dec load/store.
op_iterator op_end() const
bool reachesChainWithoutSideEffects(SDValue Dest, unsigned Depth=2) const
Return true if this operand (which must be a chain) reaches the specified operand without crossing an...
FSINCOS - Compute both fsin and fcos as a single operation.
RESULT, OUTCHAIN = EH_SJLJ_SETJMP(INCHAIN, buffer) This corresponds to the eh.sjlj.setjmp intrinsic.
EVT getValueType() const
Return the ValueType of the referenced return value.
OUTCHAIN = EH_RETURN(INCHAIN, OFFSET, HANDLER) - This node represents 'eh_return' gcc dwarf builtin...
SDValue getConstant(uint64_t Val, SDLoc DL, EVT VT, bool isTarget=false, bool isOpaque=false)
const APFloat & getValueAPF() const
Libcall getATOMIC(unsigned Opc, MVT VT)
Return the SYNC_FETCH_AND_* value for the given opcode and type, or UNKNOWN_LIBCALL if there is none...
bool isByteSized() const
isByteSized - Return true if the bit size is a multiple of 8.
CONCAT_VECTORS(VECTOR0, VECTOR1, ...) - Given a number of values of vector type with the same length ...
bool isFloatingPoint() const
isFloatingPoint - Return true if this is a FP, or a vector FP type.
This class is used to form a handle around another node that is persistent and is updated across invo...
static bool isSinCosLibcallAvailable(SDNode *Node, const TargetLowering &TLI)
Return true if sincos libcall is available.
MVT getPointerTy(const DataLayout &DL, uint32_t AS=0) const
Return the pointer type for the given address space, defaults to the pointer type from the data layou...
LLVM Value Representation.
FMA - Perform a * b + c with no intermediate rounding step.
static bool ExpandBVWithShuffles(SDNode *Node, SelectionDAG &DAG, const TargetLowering &TLI, SDValue &Res)
bool isTruncatingStore() const
Return true if the op does a truncation before store.
PREFETCH - This corresponds to a prefetch intrinsic.
const TargetLowering & getTargetLoweringInfo() const
Primary interface to the complete machine description for the target machine.
C - The default llvm calling convention, compatible with C.
FMAD - Perform a * b + c, while getting the same result as the separately rounded operations...
SetCC operator - This evaluates to a true value iff the condition is true.
MERGE_VALUES - This node takes multiple discrete operands and returns them all as its individual resu...
static bool isVolatile(Instruction *Inst)
static APInt getNullValue(unsigned numBits)
Get the '0' value.
OUTCHAIN = ATOMIC_STORE(INCHAIN, ptr, val) This corresponds to "store atomic" instruction.
TRUNCATE - Completely drop the high bits.
EVT getShiftAmountTy(EVT LHSTy, const DataLayout &DL) const
unsigned getAlignment() const
void TransferDbgValues(SDValue From, SDValue To)
Transfer SDDbgValues.
static bool canCombineSinCosLibcall(SDNode *Node, const TargetLowering &TLI, const TargetMachine &TM)
Return true if sincos libcall is available and can be used to combine sin and cos.
Unlike LLVM values, Selection DAG nodes may return multiple values as the result of a computation...
MVT getSimpleValueType(unsigned ResNo) const
Return the type of a specified result as a simple type.
FNEG, FABS, FSQRT, FSIN, FCOS, FPOWI, FPOW, FLOG, FLOG2, FLOG10, FEXP, FEXP2, FCEIL, FTRUNC, FRINT, FNEARBYINT, FROUND, FFLOOR - Perform various unary floating point operations.
static EVT getIntegerVT(LLVMContext &Context, unsigned BitWidth)
getIntegerVT - Returns the EVT that represents an integer with the given number of bits...
Val, OUTCHAIN = ATOMIC_LOAD(INCHAIN, ptr) This corresponds to "load atomic" instruction.
SCALAR_TO_VECTOR(VAL) - This represents the operation of loading a scalar value into element 0 of the...
MVT getSimpleVT() const
getSimpleVT - Return the SimpleValueType held in the specified simple EVT.
This file describes how to lower LLVM code to machine code.
MULHU/MULHS - Multiply high - Multiply two integers of type iN, producing an unsigned/signed value of...
unsigned getVectorNumElements() const
getVectorNumElements - Given a vector type, return the number of elements it contains.
This class is used to represent ISD::LOAD nodes.
DYNAMIC_STACKALLOC - Allocate some number of bytes on the stack aligned to a specified boundary...