10b57cec5SDimitry Andric//===- TargetSelectionDAG.td - Common code for DAG isels ---*- tablegen -*-===//
20b57cec5SDimitry Andric//
30b57cec5SDimitry Andric// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric// See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric//
70b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric//
90b57cec5SDimitry Andric// This file defines the target-independent interfaces used by SelectionDAG
100b57cec5SDimitry Andric// instruction selection generators.
110b57cec5SDimitry Andric//
120b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
130b57cec5SDimitry Andric
140b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
150b57cec5SDimitry Andric// Selection DAG Type Constraint definitions.
160b57cec5SDimitry Andric//
170b57cec5SDimitry Andric// Note that the semantics of these constraints are hard coded into tblgen.  To
180b57cec5SDimitry Andric// modify or add constraints, you have to hack tblgen.
190b57cec5SDimitry Andric//
200b57cec5SDimitry Andric
210b57cec5SDimitry Andricclass SDTypeConstraint<int opnum> {
220b57cec5SDimitry Andric  int OperandNum = opnum;
230b57cec5SDimitry Andric}
240b57cec5SDimitry Andric
250b57cec5SDimitry Andric// SDTCisVT - The specified operand has exactly this VT.
260b57cec5SDimitry Andricclass SDTCisVT<int OpNum, ValueType vt> : SDTypeConstraint<OpNum> {
270b57cec5SDimitry Andric  ValueType VT = vt;
280b57cec5SDimitry Andric}
290b57cec5SDimitry Andric
300b57cec5SDimitry Andricclass SDTCisPtrTy<int OpNum> : SDTypeConstraint<OpNum>;
310b57cec5SDimitry Andric
320b57cec5SDimitry Andric// SDTCisInt - The specified operand has integer type.
330b57cec5SDimitry Andricclass SDTCisInt<int OpNum> : SDTypeConstraint<OpNum>;
340b57cec5SDimitry Andric
350b57cec5SDimitry Andric// SDTCisFP - The specified operand has floating-point type.
360b57cec5SDimitry Andricclass SDTCisFP<int OpNum> : SDTypeConstraint<OpNum>;
370b57cec5SDimitry Andric
380b57cec5SDimitry Andric// SDTCisVec - The specified operand has a vector type.
390b57cec5SDimitry Andricclass SDTCisVec<int OpNum> : SDTypeConstraint<OpNum>;
400b57cec5SDimitry Andric
410b57cec5SDimitry Andric// SDTCisSameAs - The two specified operands have identical types.
420b57cec5SDimitry Andricclass SDTCisSameAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
430b57cec5SDimitry Andric  int OtherOperandNum = OtherOp;
440b57cec5SDimitry Andric}
450b57cec5SDimitry Andric
460b57cec5SDimitry Andric// SDTCisVTSmallerThanOp - The specified operand is a VT SDNode, and its type is
470b57cec5SDimitry Andric// smaller than the 'Other' operand.
480b57cec5SDimitry Andricclass SDTCisVTSmallerThanOp<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
490b57cec5SDimitry Andric  int OtherOperandNum = OtherOp;
500b57cec5SDimitry Andric}
510b57cec5SDimitry Andric
520b57cec5SDimitry Andricclass SDTCisOpSmallerThanOp<int SmallOp, int BigOp> : SDTypeConstraint<SmallOp>{
530b57cec5SDimitry Andric  int BigOperandNum = BigOp;
540b57cec5SDimitry Andric}
550b57cec5SDimitry Andric
560b57cec5SDimitry Andric/// SDTCisEltOfVec - This indicates that ThisOp is a scalar type of the same
570b57cec5SDimitry Andric/// type as the element type of OtherOp, which is a vector type.
580b57cec5SDimitry Andricclass SDTCisEltOfVec<int ThisOp, int OtherOp>
590b57cec5SDimitry Andric  : SDTypeConstraint<ThisOp> {
600b57cec5SDimitry Andric  int OtherOpNum = OtherOp;
610b57cec5SDimitry Andric}
620b57cec5SDimitry Andric
630b57cec5SDimitry Andric/// SDTCisSubVecOfVec - This indicates that ThisOp is a vector type
640b57cec5SDimitry Andric/// with length less that of OtherOp, which is a vector type.
650b57cec5SDimitry Andricclass SDTCisSubVecOfVec<int ThisOp, int OtherOp>
660b57cec5SDimitry Andric  : SDTypeConstraint<ThisOp> {
670b57cec5SDimitry Andric  int OtherOpNum = OtherOp;
680b57cec5SDimitry Andric}
690b57cec5SDimitry Andric
700b57cec5SDimitry Andric// SDTCVecEltisVT - The specified operand is vector type with element type
710b57cec5SDimitry Andric// of VT.
720b57cec5SDimitry Andricclass SDTCVecEltisVT<int OpNum, ValueType vt> : SDTypeConstraint<OpNum> {
730b57cec5SDimitry Andric  ValueType VT = vt;
740b57cec5SDimitry Andric}
750b57cec5SDimitry Andric
760b57cec5SDimitry Andric// SDTCisSameNumEltsAs - The two specified operands have identical number
770b57cec5SDimitry Andric// of elements.
780b57cec5SDimitry Andricclass SDTCisSameNumEltsAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
790b57cec5SDimitry Andric  int OtherOperandNum = OtherOp;
800b57cec5SDimitry Andric}
810b57cec5SDimitry Andric
820b57cec5SDimitry Andric// SDTCisSameSizeAs - The two specified operands have identical size.
830b57cec5SDimitry Andricclass SDTCisSameSizeAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
840b57cec5SDimitry Andric  int OtherOperandNum = OtherOp;
850b57cec5SDimitry Andric}
860b57cec5SDimitry Andric
870b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
880b57cec5SDimitry Andric// Selection DAG Type Profile definitions.
890b57cec5SDimitry Andric//
900b57cec5SDimitry Andric// These use the constraints defined above to describe the type requirements of
910b57cec5SDimitry Andric// the various nodes.  These are not hard coded into tblgen, allowing targets to
920b57cec5SDimitry Andric// add their own if needed.
930b57cec5SDimitry Andric//
940b57cec5SDimitry Andric
950b57cec5SDimitry Andric// SDTypeProfile - This profile describes the type requirements of a Selection
960b57cec5SDimitry Andric// DAG node.
970b57cec5SDimitry Andricclass SDTypeProfile<int numresults, int numoperands,
980b57cec5SDimitry Andric                    list<SDTypeConstraint> constraints> {
990b57cec5SDimitry Andric  int NumResults = numresults;
1000b57cec5SDimitry Andric  int NumOperands = numoperands;
1010b57cec5SDimitry Andric  list<SDTypeConstraint> Constraints = constraints;
1020b57cec5SDimitry Andric}
1030b57cec5SDimitry Andric
1040b57cec5SDimitry Andric// Builtin profiles.
1050b57cec5SDimitry Andricdef SDTIntLeaf: SDTypeProfile<1, 0, [SDTCisInt<0>]>;         // for 'imm'.
1060b57cec5SDimitry Andricdef SDTFPLeaf : SDTypeProfile<1, 0, [SDTCisFP<0>]>;          // for 'fpimm'.
1070b57cec5SDimitry Andricdef SDTPtrLeaf: SDTypeProfile<1, 0, [SDTCisPtrTy<0>]>;       // for '&g'.
1080b57cec5SDimitry Andricdef SDTOther  : SDTypeProfile<1, 0, [SDTCisVT<0, OtherVT>]>; // for 'vt'.
1090b57cec5SDimitry Andricdef SDTUNDEF  : SDTypeProfile<1, 0, []>;                     // for 'undef'.
1100b57cec5SDimitry Andricdef SDTUnaryOp  : SDTypeProfile<1, 1, []>;                   // for bitconvert.
1110b57cec5SDimitry Andric
112bdd1243dSDimitry Andricdef SDTPtrAddOp : SDTypeProfile<1, 2, [     // ptradd
113bdd1243dSDimitry Andric  SDTCisSameAs<0, 1>, SDTCisInt<2>, SDTCisPtrTy<1>
114bdd1243dSDimitry Andric]>;
1150b57cec5SDimitry Andricdef SDTIntBinOp : SDTypeProfile<1, 2, [     // add, and, or, xor, udiv, etc.
1160b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0>
1170b57cec5SDimitry Andric]>;
1180b57cec5SDimitry Andricdef SDTIntShiftOp : SDTypeProfile<1, 2, [   // shl, sra, srl
1190b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisInt<0>, SDTCisInt<2>
1200b57cec5SDimitry Andric]>;
1210b57cec5SDimitry Andricdef SDTIntShiftDOp: SDTypeProfile<1, 3, [   // fshl, fshr
1220b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0>, SDTCisInt<3>
1230b57cec5SDimitry Andric]>;
1240b57cec5SDimitry Andricdef SDTIntSatNoShOp : SDTypeProfile<1, 2, [   // ssat with no shift
1250b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisInt<2>
1260b57cec5SDimitry Andric]>;
1270b57cec5SDimitry Andricdef SDTIntBinHiLoOp : SDTypeProfile<2, 2, [ // mulhi, mullo, sdivrem, udivrem
1280b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisSameAs<0, 3>,SDTCisInt<0>
1290b57cec5SDimitry Andric]>;
130480093f4SDimitry Andricdef SDTIntScaledBinOp : SDTypeProfile<1, 3, [  // smulfix, sdivfix, etc
1310b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0>, SDTCisInt<3>
1320b57cec5SDimitry Andric]>;
1330b57cec5SDimitry Andric
1340b57cec5SDimitry Andricdef SDTFPBinOp : SDTypeProfile<1, 2, [      // fadd, fmul, etc.
1350b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisFP<0>
1360b57cec5SDimitry Andric]>;
1370b57cec5SDimitry Andricdef SDTFPSignOp : SDTypeProfile<1, 2, [     // fcopysign.
1380b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisFP<0>, SDTCisFP<2>
1390b57cec5SDimitry Andric]>;
1400b57cec5SDimitry Andricdef SDTFPTernaryOp : SDTypeProfile<1, 3, [  // fmadd, fnmsub, etc.
1410b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisSameAs<0, 3>, SDTCisFP<0>
1420b57cec5SDimitry Andric]>;
1438bcb0991SDimitry Andricdef SDTIntUnaryOp : SDTypeProfile<1, 1, [ // bitreverse
1440b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisInt<0>
1450b57cec5SDimitry Andric]>;
1468bcb0991SDimitry Andricdef SDTIntBitCountUnaryOp : SDTypeProfile<1, 1, [   // ctlz, cttz
1478bcb0991SDimitry Andric  SDTCisInt<0>, SDTCisInt<1>
1488bcb0991SDimitry Andric]>;
1490b57cec5SDimitry Andricdef SDTIntExtendOp : SDTypeProfile<1, 1, [  // sext, zext, anyext
1500b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisInt<1>, SDTCisOpSmallerThanOp<1, 0>, SDTCisSameNumEltsAs<0, 1>
1510b57cec5SDimitry Andric]>;
1520b57cec5SDimitry Andricdef SDTIntTruncOp  : SDTypeProfile<1, 1, [  // trunc
1530b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisInt<1>, SDTCisOpSmallerThanOp<0, 1>, SDTCisSameNumEltsAs<0, 1>
1540b57cec5SDimitry Andric]>;
1550b57cec5SDimitry Andricdef SDTFPUnaryOp  : SDTypeProfile<1, 1, [   // fneg, fsqrt, etc
1560b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisFP<0>
1570b57cec5SDimitry Andric]>;
158fe6060f1SDimitry Andricdef SDTFPRoundOp  : SDTypeProfile<1, 1, [   // fpround
1590b57cec5SDimitry Andric  SDTCisFP<0>, SDTCisFP<1>, SDTCisOpSmallerThanOp<0, 1>, SDTCisSameNumEltsAs<0, 1>
1600b57cec5SDimitry Andric]>;
161fe6060f1SDimitry Andricdef SDTFPExtendOp  : SDTypeProfile<1, 1, [  // fpextend
1620b57cec5SDimitry Andric  SDTCisFP<0>, SDTCisFP<1>, SDTCisOpSmallerThanOp<1, 0>, SDTCisSameNumEltsAs<0, 1>
1630b57cec5SDimitry Andric]>;
164bdd1243dSDimitry Andricdef SDIsFPClassOp : SDTypeProfile<1, 2, [   // is_fpclass
165bdd1243dSDimitry Andric  SDTCisInt<0>, SDTCisFP<1>, SDTCisInt<2>, SDTCisSameNumEltsAs<0, 1>
166bdd1243dSDimitry Andric]>;
1670b57cec5SDimitry Andricdef SDTIntToFPOp : SDTypeProfile<1, 1, [    // [su]int_to_fp
1680b57cec5SDimitry Andric  SDTCisFP<0>, SDTCisInt<1>, SDTCisSameNumEltsAs<0, 1>
1690b57cec5SDimitry Andric]>;
1700b57cec5SDimitry Andricdef SDTFPToIntOp : SDTypeProfile<1, 1, [    // fp_to_[su]int
1710b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisFP<1>, SDTCisSameNumEltsAs<0, 1>
1720b57cec5SDimitry Andric]>;
173e8d8bef9SDimitry Andricdef SDTFPToIntSatOp : SDTypeProfile<1, 2, [    // fp_to_[su]int_sat
174fe6060f1SDimitry Andric  SDTCisInt<0>, SDTCisFP<1>, SDTCisSameNumEltsAs<0, 1>, SDTCisVT<2, OtherVT>
175e8d8bef9SDimitry Andric]>;
17606c3fb27SDimitry Andricdef SDTFPExpOp : SDTypeProfile<1, 2, [      // ldexp
17706c3fb27SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisFP<0>, SDTCisInt<2>
17806c3fb27SDimitry Andric]>;
1795f757f3fSDimitry Andricdef SDTGetFPStateOp : SDTypeProfile<1, 0, [ // get_fpenv, get_fpmode
1805f757f3fSDimitry Andric  SDTCisInt<0>
1815f757f3fSDimitry Andric]>;
1825f757f3fSDimitry Andricdef SDTSetFPStateOp : SDTypeProfile<0, 1, [ // set_fpenv, set_fpmode
1835f757f3fSDimitry Andric  SDTCisInt<0>
1845f757f3fSDimitry Andric]>;
1850b57cec5SDimitry Andricdef SDTExtInreg : SDTypeProfile<1, 2, [     // sext_inreg
1860b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisInt<0>, SDTCisVT<2, OtherVT>,
1870b57cec5SDimitry Andric  SDTCisVTSmallerThanOp<2, 1>
1880b57cec5SDimitry Andric]>;
1890b57cec5SDimitry Andricdef SDTExtInvec : SDTypeProfile<1, 1, [     // sext_invec
1900b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisVec<0>, SDTCisInt<1>, SDTCisVec<1>,
1910b57cec5SDimitry Andric  SDTCisOpSmallerThanOp<1, 0>
1920b57cec5SDimitry Andric]>;
193bdd1243dSDimitry Andricdef SDTFreeze : SDTypeProfile<1, 1, [
194bdd1243dSDimitry Andric  SDTCisSameAs<0, 1>
195bdd1243dSDimitry Andric]>;
1960b57cec5SDimitry Andric
1970b57cec5SDimitry Andricdef SDTSetCC : SDTypeProfile<1, 3, [        // setcc
1980b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisSameAs<1, 2>, SDTCisVT<3, OtherVT>
1990b57cec5SDimitry Andric]>;
2000b57cec5SDimitry Andric
2010b57cec5SDimitry Andricdef SDTSelect : SDTypeProfile<1, 3, [       // select
2020b57cec5SDimitry Andric  SDTCisInt<1>, SDTCisSameAs<0, 2>, SDTCisSameAs<2, 3>
2030b57cec5SDimitry Andric]>;
2040b57cec5SDimitry Andric
2050b57cec5SDimitry Andricdef SDTVSelect : SDTypeProfile<1, 3, [       // vselect
2060b57cec5SDimitry Andric  SDTCisVec<0>, SDTCisInt<1>, SDTCisSameAs<0, 2>, SDTCisSameAs<2, 3>, SDTCisSameNumEltsAs<0, 1>
2070b57cec5SDimitry Andric]>;
2080b57cec5SDimitry Andric
2090b57cec5SDimitry Andricdef SDTSelectCC : SDTypeProfile<1, 5, [     // select_cc
2100b57cec5SDimitry Andric  SDTCisSameAs<1, 2>, SDTCisSameAs<3, 4>, SDTCisSameAs<0, 3>,
2110b57cec5SDimitry Andric  SDTCisVT<5, OtherVT>
2120b57cec5SDimitry Andric]>;
2130b57cec5SDimitry Andric
2140b57cec5SDimitry Andricdef SDTBr : SDTypeProfile<0, 1, [           // br
2150b57cec5SDimitry Andric  SDTCisVT<0, OtherVT>
2160b57cec5SDimitry Andric]>;
2170b57cec5SDimitry Andric
2180b57cec5SDimitry Andricdef SDTBrCC : SDTypeProfile<0, 4, [       // brcc
2190b57cec5SDimitry Andric  SDTCisVT<0, OtherVT>, SDTCisSameAs<1, 2>, SDTCisVT<3, OtherVT>
2200b57cec5SDimitry Andric]>;
2210b57cec5SDimitry Andric
2220b57cec5SDimitry Andricdef SDTBrcond : SDTypeProfile<0, 2, [       // brcond
2230b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisVT<1, OtherVT>
2240b57cec5SDimitry Andric]>;
2250b57cec5SDimitry Andric
2260b57cec5SDimitry Andricdef SDTBrind : SDTypeProfile<0, 1, [        // brind
2270b57cec5SDimitry Andric  SDTCisPtrTy<0>
2280b57cec5SDimitry Andric]>;
2290b57cec5SDimitry Andric
2300b57cec5SDimitry Andricdef SDTCatchret : SDTypeProfile<0, 2, [     // catchret
2310b57cec5SDimitry Andric  SDTCisVT<0, OtherVT>, SDTCisVT<1, OtherVT>
2320b57cec5SDimitry Andric]>;
2330b57cec5SDimitry Andric
2340b57cec5SDimitry Andricdef SDTNone : SDTypeProfile<0, 0, []>;      // ret, trap
2350b57cec5SDimitry Andric
236e8d8bef9SDimitry Andricdef SDTUBSANTrap : SDTypeProfile<0, 1, []>;      // ubsantrap
237e8d8bef9SDimitry Andric
2380b57cec5SDimitry Andricdef SDTLoad : SDTypeProfile<1, 1, [         // load
2390b57cec5SDimitry Andric  SDTCisPtrTy<1>
2400b57cec5SDimitry Andric]>;
2410b57cec5SDimitry Andric
2420b57cec5SDimitry Andricdef SDTStore : SDTypeProfile<0, 2, [        // store
2430b57cec5SDimitry Andric  SDTCisPtrTy<1>
2440b57cec5SDimitry Andric]>;
2450b57cec5SDimitry Andric
2460b57cec5SDimitry Andricdef SDTIStore : SDTypeProfile<1, 3, [       // indexed store
2470b57cec5SDimitry Andric  SDTCisSameAs<0, 2>, SDTCisPtrTy<0>, SDTCisPtrTy<3>
2480b57cec5SDimitry Andric]>;
2490b57cec5SDimitry Andric
250480093f4SDimitry Andricdef SDTMaskedStore: SDTypeProfile<0, 4, [       // masked store
251480093f4SDimitry Andric  SDTCisVec<0>, SDTCisPtrTy<1>, SDTCisPtrTy<2>, SDTCisVec<3>, SDTCisSameNumEltsAs<0, 3>
2520b57cec5SDimitry Andric]>;
2530b57cec5SDimitry Andric
254480093f4SDimitry Andricdef SDTMaskedLoad: SDTypeProfile<1, 4, [       // masked load
255480093f4SDimitry Andric  SDTCisVec<0>, SDTCisPtrTy<1>, SDTCisPtrTy<2>, SDTCisVec<3>, SDTCisSameAs<0, 4>,
256480093f4SDimitry Andric  SDTCisSameNumEltsAs<0, 3>
2570b57cec5SDimitry Andric]>;
2580b57cec5SDimitry Andric
25981ad6265SDimitry Andricdef SDTMaskedGather : SDTypeProfile<1, 4, [
26081ad6265SDimitry Andric  SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisVec<2>, SDTCisPtrTy<3>, SDTCisVec<4>,
26181ad6265SDimitry Andric  SDTCisSameNumEltsAs<0, 2>, SDTCisSameNumEltsAs<0, 4>
26281ad6265SDimitry Andric]>;
26381ad6265SDimitry Andric
26481ad6265SDimitry Andricdef SDTMaskedScatter : SDTypeProfile<0, 4, [
26581ad6265SDimitry Andric  SDTCisVec<0>, SDTCisVec<1>, SDTCisPtrTy<2>, SDTCisVec<3>,
26681ad6265SDimitry Andric  SDTCisSameNumEltsAs<0, 1>, SDTCisSameNumEltsAs<0, 3>
26781ad6265SDimitry Andric]>;
26881ad6265SDimitry Andric
2690b57cec5SDimitry Andricdef SDTVecShuffle : SDTypeProfile<1, 2, [
2700b57cec5SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>
2710b57cec5SDimitry Andric]>;
272fe6060f1SDimitry Andricdef SDTVecSlice : SDTypeProfile<1, 3, [     // vector splice
273fe6060f1SDimitry Andric  SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>, SDTCisInt<3>
274fe6060f1SDimitry Andric]>;
2750b57cec5SDimitry Andricdef SDTVecExtract : SDTypeProfile<1, 2, [   // vector extract
2760b57cec5SDimitry Andric  SDTCisEltOfVec<0, 1>, SDTCisPtrTy<2>
2770b57cec5SDimitry Andric]>;
2780b57cec5SDimitry Andricdef SDTVecInsert : SDTypeProfile<1, 3, [    // vector insert
2790b57cec5SDimitry Andric  SDTCisEltOfVec<2, 1>, SDTCisSameAs<0, 1>, SDTCisPtrTy<3>
2800b57cec5SDimitry Andric]>;
2818bcb0991SDimitry Andricdef SDTVecReduce : SDTypeProfile<1, 1, [    // vector reduction
2828bcb0991SDimitry Andric  SDTCisInt<0>, SDTCisVec<1>
2838bcb0991SDimitry Andric]>;
284e8d8bef9SDimitry Andricdef SDTFPVecReduce : SDTypeProfile<1, 1, [  // FP vector reduction
285e8d8bef9SDimitry Andric  SDTCisFP<0>, SDTCisVec<1>
286e8d8bef9SDimitry Andric]>;
287e8d8bef9SDimitry Andric
288fe6060f1SDimitry Andricdef SDTVecReverse : SDTypeProfile<1, 1, [  // vector reverse
289fe6060f1SDimitry Andric  SDTCisVec<0>, SDTCisSameAs<0,1>
290fe6060f1SDimitry Andric]>;
2910b57cec5SDimitry Andric
2920b57cec5SDimitry Andricdef SDTSubVecExtract : SDTypeProfile<1, 2, [// subvector extract
2930b57cec5SDimitry Andric  SDTCisSubVecOfVec<0,1>, SDTCisInt<2>
2940b57cec5SDimitry Andric]>;
2950b57cec5SDimitry Andricdef SDTSubVecInsert : SDTypeProfile<1, 3, [ // subvector insert
2960b57cec5SDimitry Andric  SDTCisSubVecOfVec<2, 1>, SDTCisSameAs<0,1>, SDTCisInt<3>
2970b57cec5SDimitry Andric]>;
2980b57cec5SDimitry Andric
2990b57cec5SDimitry Andricdef SDTPrefetch : SDTypeProfile<0, 4, [     // prefetch
3000b57cec5SDimitry Andric  SDTCisPtrTy<0>, SDTCisSameAs<1, 2>, SDTCisSameAs<1, 3>, SDTCisInt<1>
3010b57cec5SDimitry Andric]>;
3020b57cec5SDimitry Andric
3030b57cec5SDimitry Andricdef SDTAtomicFence : SDTypeProfile<0, 2, [
3040b57cec5SDimitry Andric  SDTCisSameAs<0,1>, SDTCisPtrTy<0>
3050b57cec5SDimitry Andric]>;
3060b57cec5SDimitry Andricdef SDTAtomic3 : SDTypeProfile<1, 3, [
3070b57cec5SDimitry Andric  SDTCisSameAs<0,2>,  SDTCisSameAs<0,3>, SDTCisInt<0>, SDTCisPtrTy<1>
3080b57cec5SDimitry Andric]>;
3090b57cec5SDimitry Andricdef SDTAtomic2 : SDTypeProfile<1, 2, [
3100b57cec5SDimitry Andric  SDTCisSameAs<0,2>, SDTCisInt<0>, SDTCisPtrTy<1>
3110b57cec5SDimitry Andric]>;
3120b57cec5SDimitry Andric
3130b57cec5SDimitry Andricdef SDTFPAtomic2 : SDTypeProfile<1, 2, [
3140b57cec5SDimitry Andric  SDTCisSameAs<0,2>, SDTCisFP<0>, SDTCisPtrTy<1>
3150b57cec5SDimitry Andric]>;
3160b57cec5SDimitry Andric
3170b57cec5SDimitry Andricdef SDTAtomicStore : SDTypeProfile<0, 2, [
3185f757f3fSDimitry Andric  SDTCisInt<0>, SDTCisPtrTy<1>
3190b57cec5SDimitry Andric]>;
3200b57cec5SDimitry Andricdef SDTAtomicLoad : SDTypeProfile<1, 1, [
3210b57cec5SDimitry Andric  SDTCisInt<0>, SDTCisPtrTy<1>
3220b57cec5SDimitry Andric]>;
3230b57cec5SDimitry Andric
3240b57cec5SDimitry Andricclass SDCallSeqStart<list<SDTypeConstraint> constraints> :
3250b57cec5SDimitry Andric        SDTypeProfile<0, 2, constraints>;
3260b57cec5SDimitry Andricclass SDCallSeqEnd<list<SDTypeConstraint> constraints> :
3270b57cec5SDimitry Andric        SDTypeProfile<0, 2, constraints>;
3280b57cec5SDimitry Andric
3290b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
3300b57cec5SDimitry Andric// Selection DAG Node definitions.
3310b57cec5SDimitry Andric//
3320b57cec5SDimitry Andricclass SDNode<string opcode, SDTypeProfile typeprof,
3330b57cec5SDimitry Andric             list<SDNodeProperty> props = [], string sdclass = "SDNode">
3340b57cec5SDimitry Andric             : SDPatternOperator {
3350b57cec5SDimitry Andric  string Opcode  = opcode;
3360b57cec5SDimitry Andric  string SDClass = sdclass;
3370b57cec5SDimitry Andric  let Properties = props;
3380b57cec5SDimitry Andric  SDTypeProfile TypeProfile = typeprof;
3390b57cec5SDimitry Andric}
3400b57cec5SDimitry Andric
3410b57cec5SDimitry Andric// Special TableGen-recognized dag nodes
3420b57cec5SDimitry Andricdef set;
3430b57cec5SDimitry Andricdef implicit;
3440b57cec5SDimitry Andricdef node;
3450b57cec5SDimitry Andricdef srcvalue;
3460b57cec5SDimitry Andric
3470b57cec5SDimitry Andricdef imm        : SDNode<"ISD::Constant"  , SDTIntLeaf , [], "ConstantSDNode">;
3480b57cec5SDimitry Andricdef timm       : SDNode<"ISD::TargetConstant",SDTIntLeaf, [], "ConstantSDNode">;
3490b57cec5SDimitry Andricdef fpimm      : SDNode<"ISD::ConstantFP", SDTFPLeaf  , [], "ConstantFPSDNode">;
3500b57cec5SDimitry Andricdef vt         : SDNode<"ISD::VALUETYPE" , SDTOther   , [], "VTSDNode">;
3510b57cec5SDimitry Andricdef bb         : SDNode<"ISD::BasicBlock", SDTOther   , [], "BasicBlockSDNode">;
3520b57cec5SDimitry Andricdef cond       : SDNode<"ISD::CONDCODE"  , SDTOther   , [], "CondCodeSDNode">;
3530b57cec5SDimitry Andricdef undef      : SDNode<"ISD::UNDEF"     , SDTUNDEF   , []>;
3545ffd83dbSDimitry Andricdef vscale     : SDNode<"ISD::VSCALE"    , SDTIntUnaryOp, []>;
3550b57cec5SDimitry Andricdef globaladdr : SDNode<"ISD::GlobalAddress",         SDTPtrLeaf, [],
3560b57cec5SDimitry Andric                        "GlobalAddressSDNode">;
3570b57cec5SDimitry Andricdef tglobaladdr : SDNode<"ISD::TargetGlobalAddress",  SDTPtrLeaf, [],
3580b57cec5SDimitry Andric                         "GlobalAddressSDNode">;
3590b57cec5SDimitry Andricdef globaltlsaddr : SDNode<"ISD::GlobalTLSAddress",         SDTPtrLeaf, [],
3600b57cec5SDimitry Andric                          "GlobalAddressSDNode">;
3610b57cec5SDimitry Andricdef tglobaltlsaddr : SDNode<"ISD::TargetGlobalTLSAddress",  SDTPtrLeaf, [],
3620b57cec5SDimitry Andric                           "GlobalAddressSDNode">;
3630b57cec5SDimitry Andricdef constpool   : SDNode<"ISD::ConstantPool",         SDTPtrLeaf, [],
3640b57cec5SDimitry Andric                         "ConstantPoolSDNode">;
3650b57cec5SDimitry Andricdef tconstpool  : SDNode<"ISD::TargetConstantPool",   SDTPtrLeaf, [],
3660b57cec5SDimitry Andric                         "ConstantPoolSDNode">;
3670b57cec5SDimitry Andricdef jumptable   : SDNode<"ISD::JumpTable",            SDTPtrLeaf, [],
3680b57cec5SDimitry Andric                         "JumpTableSDNode">;
3690b57cec5SDimitry Andricdef tjumptable  : SDNode<"ISD::TargetJumpTable",      SDTPtrLeaf, [],
3700b57cec5SDimitry Andric                         "JumpTableSDNode">;
3710b57cec5SDimitry Andricdef frameindex  : SDNode<"ISD::FrameIndex",           SDTPtrLeaf, [],
3720b57cec5SDimitry Andric                         "FrameIndexSDNode">;
3730b57cec5SDimitry Andricdef tframeindex : SDNode<"ISD::TargetFrameIndex",     SDTPtrLeaf, [],
3740b57cec5SDimitry Andric                         "FrameIndexSDNode">;
3750b57cec5SDimitry Andricdef externalsym : SDNode<"ISD::ExternalSymbol",       SDTPtrLeaf, [],
3760b57cec5SDimitry Andric                         "ExternalSymbolSDNode">;
3770b57cec5SDimitry Andricdef texternalsym: SDNode<"ISD::TargetExternalSymbol", SDTPtrLeaf, [],
3780b57cec5SDimitry Andric                         "ExternalSymbolSDNode">;
3790b57cec5SDimitry Andricdef mcsym: SDNode<"ISD::MCSymbol", SDTPtrLeaf, [], "MCSymbolSDNode">;
3800b57cec5SDimitry Andricdef blockaddress : SDNode<"ISD::BlockAddress",        SDTPtrLeaf, [],
3810b57cec5SDimitry Andric                         "BlockAddressSDNode">;
3820b57cec5SDimitry Andricdef tblockaddress: SDNode<"ISD::TargetBlockAddress",  SDTPtrLeaf, [],
3830b57cec5SDimitry Andric                         "BlockAddressSDNode">;
3840b57cec5SDimitry Andric
3850b57cec5SDimitry Andricdef add        : SDNode<"ISD::ADD"       , SDTIntBinOp   ,
3860b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
387bdd1243dSDimitry Andricdef ptradd     : SDNode<"ISD::ADD"       , SDTPtrAddOp, []>;
3880b57cec5SDimitry Andricdef sub        : SDNode<"ISD::SUB"       , SDTIntBinOp>;
3890b57cec5SDimitry Andricdef mul        : SDNode<"ISD::MUL"       , SDTIntBinOp,
3900b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
3910b57cec5SDimitry Andricdef mulhs      : SDNode<"ISD::MULHS"     , SDTIntBinOp, [SDNPCommutative]>;
3920b57cec5SDimitry Andricdef mulhu      : SDNode<"ISD::MULHU"     , SDTIntBinOp, [SDNPCommutative]>;
39381ad6265SDimitry Andricdef avgfloors  : SDNode<"ISD::AVGFLOORS" , SDTIntBinOp, [SDNPCommutative]>;
39481ad6265SDimitry Andricdef avgflooru  : SDNode<"ISD::AVGFLOORU" , SDTIntBinOp, [SDNPCommutative]>;
39581ad6265SDimitry Andricdef avgceils   : SDNode<"ISD::AVGCEILS"  , SDTIntBinOp, [SDNPCommutative]>;
39681ad6265SDimitry Andricdef avgceilu   : SDNode<"ISD::AVGCEILU"  , SDTIntBinOp, [SDNPCommutative]>;
397fe6060f1SDimitry Andricdef abds       : SDNode<"ISD::ABDS"      , SDTIntBinOp, [SDNPCommutative]>;
398fe6060f1SDimitry Andricdef abdu       : SDNode<"ISD::ABDU"      , SDTIntBinOp, [SDNPCommutative]>;
3990b57cec5SDimitry Andricdef smullohi   : SDNode<"ISD::SMUL_LOHI" , SDTIntBinHiLoOp, [SDNPCommutative]>;
4000b57cec5SDimitry Andricdef umullohi   : SDNode<"ISD::UMUL_LOHI" , SDTIntBinHiLoOp, [SDNPCommutative]>;
4010b57cec5SDimitry Andricdef sdiv       : SDNode<"ISD::SDIV"      , SDTIntBinOp>;
4020b57cec5SDimitry Andricdef udiv       : SDNode<"ISD::UDIV"      , SDTIntBinOp>;
4030b57cec5SDimitry Andricdef srem       : SDNode<"ISD::SREM"      , SDTIntBinOp>;
4040b57cec5SDimitry Andricdef urem       : SDNode<"ISD::UREM"      , SDTIntBinOp>;
4050b57cec5SDimitry Andricdef sdivrem    : SDNode<"ISD::SDIVREM"   , SDTIntBinHiLoOp>;
4060b57cec5SDimitry Andricdef udivrem    : SDNode<"ISD::UDIVREM"   , SDTIntBinHiLoOp>;
4070b57cec5SDimitry Andricdef srl        : SDNode<"ISD::SRL"       , SDTIntShiftOp>;
4080b57cec5SDimitry Andricdef sra        : SDNode<"ISD::SRA"       , SDTIntShiftOp>;
4090b57cec5SDimitry Andricdef shl        : SDNode<"ISD::SHL"       , SDTIntShiftOp>;
4100b57cec5SDimitry Andricdef rotl       : SDNode<"ISD::ROTL"      , SDTIntShiftOp>;
4110b57cec5SDimitry Andricdef rotr       : SDNode<"ISD::ROTR"      , SDTIntShiftOp>;
4120b57cec5SDimitry Andricdef fshl       : SDNode<"ISD::FSHL"      , SDTIntShiftDOp>;
4130b57cec5SDimitry Andricdef fshr       : SDNode<"ISD::FSHR"      , SDTIntShiftDOp>;
4140b57cec5SDimitry Andricdef and        : SDNode<"ISD::AND"       , SDTIntBinOp,
4150b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
4160b57cec5SDimitry Andricdef or         : SDNode<"ISD::OR"        , SDTIntBinOp,
4170b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
4180b57cec5SDimitry Andricdef xor        : SDNode<"ISD::XOR"       , SDTIntBinOp,
4190b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
4200b57cec5SDimitry Andricdef addc       : SDNode<"ISD::ADDC"      , SDTIntBinOp,
4210b57cec5SDimitry Andric                        [SDNPCommutative, SDNPOutGlue]>;
4220b57cec5SDimitry Andricdef adde       : SDNode<"ISD::ADDE"      , SDTIntBinOp,
4230b57cec5SDimitry Andric                        [SDNPCommutative, SDNPOutGlue, SDNPInGlue]>;
4240b57cec5SDimitry Andricdef subc       : SDNode<"ISD::SUBC"      , SDTIntBinOp,
4250b57cec5SDimitry Andric                        [SDNPOutGlue]>;
4260b57cec5SDimitry Andricdef sube       : SDNode<"ISD::SUBE"      , SDTIntBinOp,
4270b57cec5SDimitry Andric                        [SDNPOutGlue, SDNPInGlue]>;
4280b57cec5SDimitry Andricdef smin       : SDNode<"ISD::SMIN"      , SDTIntBinOp,
4290b57cec5SDimitry Andric                                  [SDNPCommutative, SDNPAssociative]>;
4300b57cec5SDimitry Andricdef smax       : SDNode<"ISD::SMAX"      , SDTIntBinOp,
4310b57cec5SDimitry Andric                                  [SDNPCommutative, SDNPAssociative]>;
4320b57cec5SDimitry Andricdef umin       : SDNode<"ISD::UMIN"      , SDTIntBinOp,
4330b57cec5SDimitry Andric                                  [SDNPCommutative, SDNPAssociative]>;
4340b57cec5SDimitry Andricdef umax       : SDNode<"ISD::UMAX"      , SDTIntBinOp,
4350b57cec5SDimitry Andric                                  [SDNPCommutative, SDNPAssociative]>;
4360b57cec5SDimitry Andric
4370b57cec5SDimitry Andricdef saddsat    : SDNode<"ISD::SADDSAT"   , SDTIntBinOp, [SDNPCommutative]>;
4380b57cec5SDimitry Andricdef uaddsat    : SDNode<"ISD::UADDSAT"   , SDTIntBinOp, [SDNPCommutative]>;
4390b57cec5SDimitry Andricdef ssubsat    : SDNode<"ISD::SSUBSAT"   , SDTIntBinOp>;
4400b57cec5SDimitry Andricdef usubsat    : SDNode<"ISD::USUBSAT"   , SDTIntBinOp>;
441e8d8bef9SDimitry Andricdef sshlsat    : SDNode<"ISD::SSHLSAT"   , SDTIntBinOp>;
442e8d8bef9SDimitry Andricdef ushlsat    : SDNode<"ISD::USHLSAT"   , SDTIntBinOp>;
4430b57cec5SDimitry Andric
4440b57cec5SDimitry Andricdef smulfix    : SDNode<"ISD::SMULFIX"   , SDTIntScaledBinOp, [SDNPCommutative]>;
4450b57cec5SDimitry Andricdef smulfixsat : SDNode<"ISD::SMULFIXSAT", SDTIntScaledBinOp, [SDNPCommutative]>;
4460b57cec5SDimitry Andricdef umulfix    : SDNode<"ISD::UMULFIX"   , SDTIntScaledBinOp, [SDNPCommutative]>;
4478bcb0991SDimitry Andricdef umulfixsat : SDNode<"ISD::UMULFIXSAT", SDTIntScaledBinOp, [SDNPCommutative]>;
448480093f4SDimitry Andricdef sdivfix    : SDNode<"ISD::SDIVFIX"   , SDTIntScaledBinOp>;
4495ffd83dbSDimitry Andricdef sdivfixsat : SDNode<"ISD::SDIVFIXSAT", SDTIntScaledBinOp>;
450480093f4SDimitry Andricdef udivfix    : SDNode<"ISD::UDIVFIX"   , SDTIntScaledBinOp>;
4515ffd83dbSDimitry Andricdef udivfixsat : SDNode<"ISD::UDIVFIXSAT", SDTIntScaledBinOp>;
4520b57cec5SDimitry Andric
4530b57cec5SDimitry Andricdef sext_inreg : SDNode<"ISD::SIGN_EXTEND_INREG", SDTExtInreg>;
4540b57cec5SDimitry Andricdef sext_invec : SDNode<"ISD::SIGN_EXTEND_VECTOR_INREG", SDTExtInvec>;
4550b57cec5SDimitry Andricdef zext_invec : SDNode<"ISD::ZERO_EXTEND_VECTOR_INREG", SDTExtInvec>;
4560b57cec5SDimitry Andric
4570b57cec5SDimitry Andricdef abs        : SDNode<"ISD::ABS"        , SDTIntUnaryOp>;
4580b57cec5SDimitry Andricdef bitreverse : SDNode<"ISD::BITREVERSE" , SDTIntUnaryOp>;
4590b57cec5SDimitry Andricdef bswap      : SDNode<"ISD::BSWAP"      , SDTIntUnaryOp>;
4608bcb0991SDimitry Andricdef ctlz       : SDNode<"ISD::CTLZ"       , SDTIntBitCountUnaryOp>;
4618bcb0991SDimitry Andricdef cttz       : SDNode<"ISD::CTTZ"       , SDTIntBitCountUnaryOp>;
4628bcb0991SDimitry Andricdef ctpop      : SDNode<"ISD::CTPOP"      , SDTIntBitCountUnaryOp>;
4638bcb0991SDimitry Andricdef ctlz_zero_undef : SDNode<"ISD::CTLZ_ZERO_UNDEF", SDTIntBitCountUnaryOp>;
4648bcb0991SDimitry Andricdef cttz_zero_undef : SDNode<"ISD::CTTZ_ZERO_UNDEF", SDTIntBitCountUnaryOp>;
4650b57cec5SDimitry Andricdef sext       : SDNode<"ISD::SIGN_EXTEND", SDTIntExtendOp>;
4660b57cec5SDimitry Andricdef zext       : SDNode<"ISD::ZERO_EXTEND", SDTIntExtendOp>;
4670b57cec5SDimitry Andricdef anyext     : SDNode<"ISD::ANY_EXTEND" , SDTIntExtendOp>;
4680b57cec5SDimitry Andricdef trunc      : SDNode<"ISD::TRUNCATE"   , SDTIntTruncOp>;
4690b57cec5SDimitry Andricdef bitconvert : SDNode<"ISD::BITCAST"    , SDTUnaryOp>;
4700b57cec5SDimitry Andricdef addrspacecast : SDNode<"ISD::ADDRSPACECAST", SDTUnaryOp>;
471bdd1243dSDimitry Andricdef freeze     : SDNode<"ISD::FREEZE"     , SDTFreeze>;
4720b57cec5SDimitry Andricdef extractelt : SDNode<"ISD::EXTRACT_VECTOR_ELT", SDTVecExtract>;
4730b57cec5SDimitry Andricdef insertelt  : SDNode<"ISD::INSERT_VECTOR_ELT", SDTVecInsert>;
4740b57cec5SDimitry Andric
4758bcb0991SDimitry Andricdef vecreduce_add  : SDNode<"ISD::VECREDUCE_ADD", SDTVecReduce>;
4768bcb0991SDimitry Andricdef vecreduce_smax  : SDNode<"ISD::VECREDUCE_SMAX", SDTVecReduce>;
4778bcb0991SDimitry Andricdef vecreduce_umax  : SDNode<"ISD::VECREDUCE_UMAX", SDTVecReduce>;
4788bcb0991SDimitry Andricdef vecreduce_smin  : SDNode<"ISD::VECREDUCE_SMIN", SDTVecReduce>;
4798bcb0991SDimitry Andricdef vecreduce_umin  : SDNode<"ISD::VECREDUCE_UMIN", SDTVecReduce>;
480e8d8bef9SDimitry Andricdef vecreduce_fadd  : SDNode<"ISD::VECREDUCE_FADD", SDTFPVecReduce>;
48106c3fb27SDimitry Andricdef vecreduce_fmin  : SDNode<"ISD::VECREDUCE_FMIN", SDTFPVecReduce>;
48206c3fb27SDimitry Andricdef vecreduce_fmax  : SDNode<"ISD::VECREDUCE_FMAX", SDTFPVecReduce>;
48306c3fb27SDimitry Andricdef vecreduce_fminimum : SDNode<"ISD::VECREDUCE_FMINIMUM", SDTFPVecReduce>;
48406c3fb27SDimitry Andricdef vecreduce_fmaximum : SDNode<"ISD::VECREDUCE_FMAXIMUM", SDTFPVecReduce>;
4858bcb0991SDimitry Andric
4860b57cec5SDimitry Andricdef fadd       : SDNode<"ISD::FADD"       , SDTFPBinOp, [SDNPCommutative]>;
4870b57cec5SDimitry Andricdef fsub       : SDNode<"ISD::FSUB"       , SDTFPBinOp>;
4880b57cec5SDimitry Andricdef fmul       : SDNode<"ISD::FMUL"       , SDTFPBinOp, [SDNPCommutative]>;
4890b57cec5SDimitry Andricdef fdiv       : SDNode<"ISD::FDIV"       , SDTFPBinOp>;
4900b57cec5SDimitry Andricdef frem       : SDNode<"ISD::FREM"       , SDTFPBinOp>;
491e8d8bef9SDimitry Andricdef fma        : SDNode<"ISD::FMA"        , SDTFPTernaryOp, [SDNPCommutative]>;
492e8d8bef9SDimitry Andricdef fmad       : SDNode<"ISD::FMAD"       , SDTFPTernaryOp, [SDNPCommutative]>;
4930b57cec5SDimitry Andricdef fabs       : SDNode<"ISD::FABS"       , SDTFPUnaryOp>;
4940b57cec5SDimitry Andricdef fminnum    : SDNode<"ISD::FMINNUM"    , SDTFPBinOp,
4950b57cec5SDimitry Andric                                  [SDNPCommutative, SDNPAssociative]>;
4960b57cec5SDimitry Andricdef fmaxnum    : SDNode<"ISD::FMAXNUM"    , SDTFPBinOp,
4970b57cec5SDimitry Andric                                  [SDNPCommutative, SDNPAssociative]>;
4980b57cec5SDimitry Andricdef fminnum_ieee : SDNode<"ISD::FMINNUM_IEEE", SDTFPBinOp,
4990b57cec5SDimitry Andric                          [SDNPCommutative]>;
5000b57cec5SDimitry Andricdef fmaxnum_ieee  : SDNode<"ISD::FMAXNUM_IEEE", SDTFPBinOp,
5010b57cec5SDimitry Andric                           [SDNPCommutative]>;
5020b57cec5SDimitry Andricdef fminimum   : SDNode<"ISD::FMINIMUM"   , SDTFPBinOp,
5030b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
5040b57cec5SDimitry Andricdef fmaximum   : SDNode<"ISD::FMAXIMUM"   , SDTFPBinOp,
5050b57cec5SDimitry Andric                        [SDNPCommutative, SDNPAssociative]>;
5060b57cec5SDimitry Andricdef fgetsign   : SDNode<"ISD::FGETSIGN"   , SDTFPToIntOp>;
5070b57cec5SDimitry Andricdef fcanonicalize : SDNode<"ISD::FCANONICALIZE", SDTFPUnaryOp>;
5080b57cec5SDimitry Andricdef fneg       : SDNode<"ISD::FNEG"       , SDTFPUnaryOp>;
5090b57cec5SDimitry Andricdef fsqrt      : SDNode<"ISD::FSQRT"      , SDTFPUnaryOp>;
5100b57cec5SDimitry Andricdef fsin       : SDNode<"ISD::FSIN"       , SDTFPUnaryOp>;
5110b57cec5SDimitry Andricdef fcos       : SDNode<"ISD::FCOS"       , SDTFPUnaryOp>;
5120b57cec5SDimitry Andricdef fexp2      : SDNode<"ISD::FEXP2"      , SDTFPUnaryOp>;
5135f757f3fSDimitry Andricdef fexp10     : SDNode<"ISD::FEXP10"     , SDTFPUnaryOp>;
5140b57cec5SDimitry Andricdef fpow       : SDNode<"ISD::FPOW"       , SDTFPBinOp>;
5150b57cec5SDimitry Andricdef flog2      : SDNode<"ISD::FLOG2"      , SDTFPUnaryOp>;
51606c3fb27SDimitry Andricdef fldexp     : SDNode<"ISD::FLDEXP"     , SDTFPExpOp>;
5170b57cec5SDimitry Andricdef frint      : SDNode<"ISD::FRINT"      , SDTFPUnaryOp>;
5180b57cec5SDimitry Andricdef ftrunc     : SDNode<"ISD::FTRUNC"     , SDTFPUnaryOp>;
5190b57cec5SDimitry Andricdef fceil      : SDNode<"ISD::FCEIL"      , SDTFPUnaryOp>;
5200b57cec5SDimitry Andricdef ffloor     : SDNode<"ISD::FFLOOR"     , SDTFPUnaryOp>;
5210b57cec5SDimitry Andricdef fnearbyint : SDNode<"ISD::FNEARBYINT" , SDTFPUnaryOp>;
5220b57cec5SDimitry Andricdef fround     : SDNode<"ISD::FROUND"     , SDTFPUnaryOp>;
523fe6060f1SDimitry Andricdef froundeven : SDNode<"ISD::FROUNDEVEN" , SDTFPUnaryOp>;
5240b57cec5SDimitry Andric
5250b57cec5SDimitry Andricdef lround     : SDNode<"ISD::LROUND"     , SDTFPToIntOp>;
5260b57cec5SDimitry Andricdef llround    : SDNode<"ISD::LLROUND"    , SDTFPToIntOp>;
5270b57cec5SDimitry Andricdef lrint      : SDNode<"ISD::LRINT"      , SDTFPToIntOp>;
5280b57cec5SDimitry Andricdef llrint     : SDNode<"ISD::LLRINT"     , SDTFPToIntOp>;
5290b57cec5SDimitry Andric
5300b57cec5SDimitry Andricdef fpround    : SDNode<"ISD::FP_ROUND"   , SDTFPRoundOp>;
5310b57cec5SDimitry Andricdef fpextend   : SDNode<"ISD::FP_EXTEND"  , SDTFPExtendOp>;
5320b57cec5SDimitry Andricdef fcopysign  : SDNode<"ISD::FCOPYSIGN"  , SDTFPSignOp>;
5330b57cec5SDimitry Andric
534bdd1243dSDimitry Andricdef is_fpclass : SDNode<"ISD::IS_FPCLASS" , SDIsFPClassOp>;
535bdd1243dSDimitry Andric
5360b57cec5SDimitry Andricdef sint_to_fp : SDNode<"ISD::SINT_TO_FP" , SDTIntToFPOp>;
5370b57cec5SDimitry Andricdef uint_to_fp : SDNode<"ISD::UINT_TO_FP" , SDTIntToFPOp>;
5380b57cec5SDimitry Andricdef fp_to_sint : SDNode<"ISD::FP_TO_SINT" , SDTFPToIntOp>;
5390b57cec5SDimitry Andricdef fp_to_uint : SDNode<"ISD::FP_TO_UINT" , SDTFPToIntOp>;
540e8d8bef9SDimitry Andricdef fp_to_sint_sat : SDNode<"ISD::FP_TO_SINT_SAT" , SDTFPToIntSatOp>;
541e8d8bef9SDimitry Andricdef fp_to_uint_sat : SDNode<"ISD::FP_TO_UINT_SAT" , SDTFPToIntSatOp>;
5420b57cec5SDimitry Andricdef f16_to_fp  : SDNode<"ISD::FP16_TO_FP" , SDTIntToFPOp>;
5430b57cec5SDimitry Andricdef fp_to_f16  : SDNode<"ISD::FP_TO_FP16" , SDTFPToIntOp>;
5440b57cec5SDimitry Andric
5450b57cec5SDimitry Andricdef strict_fadd       : SDNode<"ISD::STRICT_FADD",
5460b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain, SDNPCommutative]>;
5470b57cec5SDimitry Andricdef strict_fsub       : SDNode<"ISD::STRICT_FSUB",
5480b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain]>;
5490b57cec5SDimitry Andricdef strict_fmul       : SDNode<"ISD::STRICT_FMUL",
5500b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain, SDNPCommutative]>;
5510b57cec5SDimitry Andricdef strict_fdiv       : SDNode<"ISD::STRICT_FDIV",
5520b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain]>;
5530b57cec5SDimitry Andricdef strict_frem       : SDNode<"ISD::STRICT_FREM",
5540b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain]>;
5550b57cec5SDimitry Andricdef strict_fma        : SDNode<"ISD::STRICT_FMA",
556e8d8bef9SDimitry Andric                               SDTFPTernaryOp, [SDNPHasChain, SDNPCommutative]>;
5570b57cec5SDimitry Andricdef strict_fsqrt      : SDNode<"ISD::STRICT_FSQRT",
5580b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5590b57cec5SDimitry Andricdef strict_fsin       : SDNode<"ISD::STRICT_FSIN",
5600b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5610b57cec5SDimitry Andricdef strict_fcos       : SDNode<"ISD::STRICT_FCOS",
5620b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5630b57cec5SDimitry Andricdef strict_fexp2      : SDNode<"ISD::STRICT_FEXP2",
5640b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5650b57cec5SDimitry Andricdef strict_fpow       : SDNode<"ISD::STRICT_FPOW",
5660b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain]>;
56706c3fb27SDimitry Andricdef strict_fldexp       : SDNode<"ISD::STRICT_FLDEXP",
56806c3fb27SDimitry Andric                               SDTFPExpOp, [SDNPHasChain]>;
5690b57cec5SDimitry Andricdef strict_flog2      : SDNode<"ISD::STRICT_FLOG2",
5700b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5710b57cec5SDimitry Andricdef strict_frint      : SDNode<"ISD::STRICT_FRINT",
5720b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5738bcb0991SDimitry Andricdef strict_lrint      : SDNode<"ISD::STRICT_LRINT",
5748bcb0991SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
5758bcb0991SDimitry Andricdef strict_llrint     : SDNode<"ISD::STRICT_LLRINT",
5768bcb0991SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
5770b57cec5SDimitry Andricdef strict_fnearbyint : SDNode<"ISD::STRICT_FNEARBYINT",
5780b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5790b57cec5SDimitry Andricdef strict_fceil      : SDNode<"ISD::STRICT_FCEIL",
5800b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5810b57cec5SDimitry Andricdef strict_ffloor     : SDNode<"ISD::STRICT_FFLOOR",
5820b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5838bcb0991SDimitry Andricdef strict_lround     : SDNode<"ISD::STRICT_LROUND",
5848bcb0991SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
5858bcb0991SDimitry Andricdef strict_llround    : SDNode<"ISD::STRICT_LLROUND",
5868bcb0991SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
5870b57cec5SDimitry Andricdef strict_fround     : SDNode<"ISD::STRICT_FROUND",
5880b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
589fe6060f1SDimitry Andricdef strict_froundeven : SDNode<"ISD::STRICT_FROUNDEVEN",
590fe6060f1SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5910b57cec5SDimitry Andricdef strict_ftrunc     : SDNode<"ISD::STRICT_FTRUNC",
5920b57cec5SDimitry Andric                               SDTFPUnaryOp, [SDNPHasChain]>;
5930b57cec5SDimitry Andricdef strict_fminnum    : SDNode<"ISD::STRICT_FMINNUM",
5940b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain,
5950b57cec5SDimitry Andric                                            SDNPCommutative, SDNPAssociative]>;
5960b57cec5SDimitry Andricdef strict_fmaxnum    : SDNode<"ISD::STRICT_FMAXNUM",
5970b57cec5SDimitry Andric                               SDTFPBinOp, [SDNPHasChain,
5980b57cec5SDimitry Andric                                            SDNPCommutative, SDNPAssociative]>;
599480093f4SDimitry Andricdef strict_fminimum   : SDNode<"ISD::STRICT_FMINIMUM",
600480093f4SDimitry Andric                               SDTFPBinOp, [SDNPHasChain,
601480093f4SDimitry Andric                                            SDNPCommutative, SDNPAssociative]>;
602480093f4SDimitry Andricdef strict_fmaximum   : SDNode<"ISD::STRICT_FMAXIMUM",
603480093f4SDimitry Andric                               SDTFPBinOp, [SDNPHasChain,
604480093f4SDimitry Andric                                            SDNPCommutative, SDNPAssociative]>;
6050b57cec5SDimitry Andricdef strict_fpround    : SDNode<"ISD::STRICT_FP_ROUND",
6060b57cec5SDimitry Andric                               SDTFPRoundOp, [SDNPHasChain]>;
6070b57cec5SDimitry Andricdef strict_fpextend   : SDNode<"ISD::STRICT_FP_EXTEND",
6080b57cec5SDimitry Andric                               SDTFPExtendOp, [SDNPHasChain]>;
6098bcb0991SDimitry Andricdef strict_fp_to_sint : SDNode<"ISD::STRICT_FP_TO_SINT",
6108bcb0991SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
6118bcb0991SDimitry Andricdef strict_fp_to_uint : SDNode<"ISD::STRICT_FP_TO_UINT",
6128bcb0991SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
613480093f4SDimitry Andricdef strict_sint_to_fp : SDNode<"ISD::STRICT_SINT_TO_FP",
614480093f4SDimitry Andric                               SDTIntToFPOp, [SDNPHasChain]>;
615480093f4SDimitry Andricdef strict_uint_to_fp : SDNode<"ISD::STRICT_UINT_TO_FP",
616480093f4SDimitry Andric                               SDTIntToFPOp, [SDNPHasChain]>;
6171db9f3b2SDimitry Andric
6181db9f3b2SDimitry Andricdef strict_f16_to_fp  : SDNode<"ISD::STRICT_FP16_TO_FP",
6191db9f3b2SDimitry Andric                               SDTIntToFPOp, [SDNPHasChain]>;
6201db9f3b2SDimitry Andricdef strict_fp_to_f16  : SDNode<"ISD::STRICT_FP_TO_FP16",
6211db9f3b2SDimitry Andric                               SDTFPToIntOp, [SDNPHasChain]>;
6221db9f3b2SDimitry Andric
623e8d8bef9SDimitry Andricdef strict_fsetcc  : SDNode<"ISD::STRICT_FSETCC",  SDTSetCC, [SDNPHasChain]>;
624e8d8bef9SDimitry Andricdef strict_fsetccs : SDNode<"ISD::STRICT_FSETCCS", SDTSetCC, [SDNPHasChain]>;
6250b57cec5SDimitry Andric
6265f757f3fSDimitry Andricdef get_fpenv      : SDNode<"ISD::GET_FPENV", SDTGetFPStateOp, [SDNPHasChain]>;
6275f757f3fSDimitry Andricdef set_fpenv      : SDNode<"ISD::SET_FPENV", SDTSetFPStateOp, [SDNPHasChain]>;
6285f757f3fSDimitry Andricdef reset_fpenv    : SDNode<"ISD::RESET_FPENV", SDTNone, [SDNPHasChain]>;
6295f757f3fSDimitry Andricdef get_fpmode     : SDNode<"ISD::GET_FPMODE", SDTGetFPStateOp, [SDNPHasChain]>;
6305f757f3fSDimitry Andricdef set_fpmode     : SDNode<"ISD::SET_FPMODE", SDTSetFPStateOp, [SDNPHasChain]>;
6315f757f3fSDimitry Andricdef reset_fpmode   : SDNode<"ISD::RESET_FPMODE", SDTNone, [SDNPHasChain]>;
6325f757f3fSDimitry Andric
6330b57cec5SDimitry Andricdef setcc      : SDNode<"ISD::SETCC"      , SDTSetCC>;
6340b57cec5SDimitry Andricdef select     : SDNode<"ISD::SELECT"     , SDTSelect>;
6350b57cec5SDimitry Andricdef vselect    : SDNode<"ISD::VSELECT"    , SDTVSelect>;
6360b57cec5SDimitry Andricdef selectcc   : SDNode<"ISD::SELECT_CC"  , SDTSelectCC>;
6370b57cec5SDimitry Andric
6380b57cec5SDimitry Andricdef brcc       : SDNode<"ISD::BR_CC"      , SDTBrCC,   [SDNPHasChain]>;
6390b57cec5SDimitry Andricdef brcond     : SDNode<"ISD::BRCOND"     , SDTBrcond, [SDNPHasChain]>;
6400b57cec5SDimitry Andricdef brind      : SDNode<"ISD::BRIND"      , SDTBrind,  [SDNPHasChain]>;
6410b57cec5SDimitry Andricdef br         : SDNode<"ISD::BR"         , SDTBr,     [SDNPHasChain]>;
6420b57cec5SDimitry Andricdef catchret   : SDNode<"ISD::CATCHRET"   , SDTCatchret,
6430b57cec5SDimitry Andric                        [SDNPHasChain, SDNPSideEffect]>;
6440b57cec5SDimitry Andricdef cleanupret : SDNode<"ISD::CLEANUPRET" , SDTNone,   [SDNPHasChain]>;
6450b57cec5SDimitry Andric
6460b57cec5SDimitry Andricdef trap       : SDNode<"ISD::TRAP"       , SDTNone,
6470b57cec5SDimitry Andric                        [SDNPHasChain, SDNPSideEffect]>;
6480b57cec5SDimitry Andricdef debugtrap  : SDNode<"ISD::DEBUGTRAP"  , SDTNone,
6490b57cec5SDimitry Andric                        [SDNPHasChain, SDNPSideEffect]>;
650e8d8bef9SDimitry Andricdef ubsantrap  : SDNode<"ISD::UBSANTRAP"  , SDTUBSANTrap,
651e8d8bef9SDimitry Andric                        [SDNPHasChain, SDNPSideEffect]>;
6520b57cec5SDimitry Andric
6530b57cec5SDimitry Andricdef prefetch   : SDNode<"ISD::PREFETCH"   , SDTPrefetch,
6540b57cec5SDimitry Andric                        [SDNPHasChain, SDNPMayLoad, SDNPMayStore,
6550b57cec5SDimitry Andric                         SDNPMemOperand]>;
6560b57cec5SDimitry Andric
6570b57cec5SDimitry Andricdef readcyclecounter : SDNode<"ISD::READCYCLECOUNTER", SDTIntLeaf,
6580b57cec5SDimitry Andric                     [SDNPHasChain, SDNPSideEffect]>;
6590b57cec5SDimitry Andric
660bdd1243dSDimitry Andricdef membarrier : SDNode<"ISD::MEMBARRIER", SDTNone,
661bdd1243dSDimitry Andric                        [SDNPHasChain, SDNPSideEffect]>;
662bdd1243dSDimitry Andric
6635f757f3fSDimitry Andricdef jump_table_debug_info : SDNode<"ISD::JUMP_TABLE_DEBUG_INFO", SDTNone,
6645f757f3fSDimitry Andric                        [SDNPHasChain]>;
6655f757f3fSDimitry Andric
6660b57cec5SDimitry Andricdef atomic_fence : SDNode<"ISD::ATOMIC_FENCE" , SDTAtomicFence,
6670b57cec5SDimitry Andric                          [SDNPHasChain, SDNPSideEffect]>;
6680b57cec5SDimitry Andric
6690b57cec5SDimitry Andricdef atomic_cmp_swap : SDNode<"ISD::ATOMIC_CMP_SWAP" , SDTAtomic3,
6700b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6710b57cec5SDimitry Andricdef atomic_load_add : SDNode<"ISD::ATOMIC_LOAD_ADD" , SDTAtomic2,
6720b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6730b57cec5SDimitry Andricdef atomic_swap     : SDNode<"ISD::ATOMIC_SWAP", SDTAtomic2,
6740b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6750b57cec5SDimitry Andricdef atomic_load_sub : SDNode<"ISD::ATOMIC_LOAD_SUB" , SDTAtomic2,
6760b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6770b57cec5SDimitry Andricdef atomic_load_and : SDNode<"ISD::ATOMIC_LOAD_AND" , SDTAtomic2,
6780b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6790b57cec5SDimitry Andricdef atomic_load_clr : SDNode<"ISD::ATOMIC_LOAD_CLR" , SDTAtomic2,
6800b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6810b57cec5SDimitry Andricdef atomic_load_or  : SDNode<"ISD::ATOMIC_LOAD_OR" , SDTAtomic2,
6820b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6830b57cec5SDimitry Andricdef atomic_load_xor : SDNode<"ISD::ATOMIC_LOAD_XOR" , SDTAtomic2,
6840b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6850b57cec5SDimitry Andricdef atomic_load_nand: SDNode<"ISD::ATOMIC_LOAD_NAND", SDTAtomic2,
6860b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6870b57cec5SDimitry Andricdef atomic_load_min : SDNode<"ISD::ATOMIC_LOAD_MIN", SDTAtomic2,
6880b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6890b57cec5SDimitry Andricdef atomic_load_max : SDNode<"ISD::ATOMIC_LOAD_MAX", SDTAtomic2,
6900b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6910b57cec5SDimitry Andricdef atomic_load_umin : SDNode<"ISD::ATOMIC_LOAD_UMIN", SDTAtomic2,
6920b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6930b57cec5SDimitry Andricdef atomic_load_umax : SDNode<"ISD::ATOMIC_LOAD_UMAX", SDTAtomic2,
6940b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6950b57cec5SDimitry Andricdef atomic_load_fadd : SDNode<"ISD::ATOMIC_LOAD_FADD" , SDTFPAtomic2,
6960b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
6970b57cec5SDimitry Andricdef atomic_load_fsub : SDNode<"ISD::ATOMIC_LOAD_FSUB" , SDTFPAtomic2,
6980b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
699753f127fSDimitry Andricdef atomic_load_fmax : SDNode<"ISD::ATOMIC_LOAD_FMAX", SDTFPAtomic2,
700753f127fSDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
701753f127fSDimitry Andricdef atomic_load_fmin : SDNode<"ISD::ATOMIC_LOAD_FMIN", SDTFPAtomic2,
702753f127fSDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
703bdd1243dSDimitry Andricdef atomic_load_uinc_wrap : SDNode<"ISD::ATOMIC_LOAD_UINC_WRAP", SDTAtomic2,
704bdd1243dSDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
705bdd1243dSDimitry Andricdef atomic_load_udec_wrap : SDNode<"ISD::ATOMIC_LOAD_UDEC_WRAP", SDTAtomic2,
706bdd1243dSDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
7070b57cec5SDimitry Andric
7080b57cec5SDimitry Andricdef atomic_load      : SDNode<"ISD::ATOMIC_LOAD", SDTAtomicLoad,
7090b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
7100b57cec5SDimitry Andricdef atomic_store     : SDNode<"ISD::ATOMIC_STORE", SDTAtomicStore,
7110b57cec5SDimitry Andric                    [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
7120b57cec5SDimitry Andric
7130b57cec5SDimitry Andricdef masked_st    : SDNode<"ISD::MSTORE",  SDTMaskedStore,
7140b57cec5SDimitry Andric                       [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
7150b57cec5SDimitry Andricdef masked_ld    : SDNode<"ISD::MLOAD",  SDTMaskedLoad,
7160b57cec5SDimitry Andric                       [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
7170b57cec5SDimitry Andric
71881ad6265SDimitry Andricdef masked_gather : SDNode<"ISD::MGATHER", SDTMaskedGather,
71981ad6265SDimitry Andric                           [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
72081ad6265SDimitry Andric
72181ad6265SDimitry Andricdef masked_scatter : SDNode<"ISD::MSCATTER", SDTMaskedScatter,
72281ad6265SDimitry Andric                            [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
72381ad6265SDimitry Andric
7240b57cec5SDimitry Andric// Do not use ld, st directly. Use load, extload, sextload, zextload, store,
7250b57cec5SDimitry Andric// and truncst (see below).
7260b57cec5SDimitry Andricdef ld         : SDNode<"ISD::LOAD"       , SDTLoad,
7270b57cec5SDimitry Andric                        [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
7280b57cec5SDimitry Andricdef st         : SDNode<"ISD::STORE"      , SDTStore,
7290b57cec5SDimitry Andric                        [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
7300b57cec5SDimitry Andricdef ist        : SDNode<"ISD::STORE"      , SDTIStore,
7310b57cec5SDimitry Andric                        [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
7320b57cec5SDimitry Andric
7330b57cec5SDimitry Andricdef vector_shuffle : SDNode<"ISD::VECTOR_SHUFFLE", SDTVecShuffle, []>;
734fe6060f1SDimitry Andricdef vector_reverse : SDNode<"ISD::VECTOR_REVERSE", SDTVecReverse>;
735fe6060f1SDimitry Andricdef vector_splice : SDNode<"ISD::VECTOR_SPLICE", SDTVecSlice, []>;
7360b57cec5SDimitry Andricdef build_vector : SDNode<"ISD::BUILD_VECTOR", SDTypeProfile<1, -1, []>, []>;
737e8d8bef9SDimitry Andricdef splat_vector : SDNode<"ISD::SPLAT_VECTOR", SDTypeProfile<1, 1, []>, []>;
738fe6060f1SDimitry Andricdef step_vector : SDNode<"ISD::STEP_VECTOR", SDTypeProfile<1, 1,
739fe6060f1SDimitry Andric                       [SDTCisVec<0>, SDTCisInt<1>]>, []>;
7400b57cec5SDimitry Andricdef scalar_to_vector : SDNode<"ISD::SCALAR_TO_VECTOR", SDTypeProfile<1, 1, []>,
7410b57cec5SDimitry Andric                              []>;
7420b57cec5SDimitry Andric
7430b57cec5SDimitry Andric// vector_extract/vector_insert are deprecated. extractelt/insertelt
7440b57cec5SDimitry Andric// are preferred.
7450b57cec5SDimitry Andricdef vector_extract : SDNode<"ISD::EXTRACT_VECTOR_ELT",
7460b57cec5SDimitry Andric    SDTypeProfile<1, 2, [SDTCisPtrTy<2>]>, []>;
7470b57cec5SDimitry Andricdef vector_insert : SDNode<"ISD::INSERT_VECTOR_ELT",
7480b57cec5SDimitry Andric    SDTypeProfile<1, 3, [SDTCisSameAs<0, 1>, SDTCisPtrTy<3>]>, []>;
7490b57cec5SDimitry Andricdef concat_vectors : SDNode<"ISD::CONCAT_VECTORS",
7500b57cec5SDimitry Andric    SDTypeProfile<1, 2, [SDTCisSubVecOfVec<1, 0>, SDTCisSameAs<1, 2>]>,[]>;
7510b57cec5SDimitry Andric
7520b57cec5SDimitry Andric// This operator does not do subvector type checking.  The ARM
7530b57cec5SDimitry Andric// backend, at least, needs it.
7540b57cec5SDimitry Andricdef vector_extract_subvec : SDNode<"ISD::EXTRACT_SUBVECTOR",
7550b57cec5SDimitry Andric    SDTypeProfile<1, 2, [SDTCisInt<2>, SDTCisVec<1>, SDTCisVec<0>]>,
7560b57cec5SDimitry Andric    []>;
757fcaf7f86SDimitry Andricdef vector_insert_subvec : SDNode<"ISD::INSERT_SUBVECTOR",
758fcaf7f86SDimitry Andric    SDTypeProfile<1, 3, [SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisVec<2>, SDTCisInt<3>]>,
759fcaf7f86SDimitry Andric    []>;
7600b57cec5SDimitry Andric
7610b57cec5SDimitry Andric// This operator does subvector type checking.
7620b57cec5SDimitry Andricdef extract_subvector : SDNode<"ISD::EXTRACT_SUBVECTOR", SDTSubVecExtract, []>;
7630b57cec5SDimitry Andricdef insert_subvector : SDNode<"ISD::INSERT_SUBVECTOR", SDTSubVecInsert, []>;
7640b57cec5SDimitry Andric
7650b57cec5SDimitry Andric// Nodes for intrinsics, you should use the intrinsic itself and let tblgen use
7660b57cec5SDimitry Andric// these internally.  Don't reference these directly.
7670b57cec5SDimitry Andricdef intrinsic_void : SDNode<"ISD::INTRINSIC_VOID",
7680b57cec5SDimitry Andric                            SDTypeProfile<0, -1, [SDTCisPtrTy<0>]>,
7690b57cec5SDimitry Andric                            [SDNPHasChain]>;
7700b57cec5SDimitry Andricdef intrinsic_w_chain : SDNode<"ISD::INTRINSIC_W_CHAIN",
7710b57cec5SDimitry Andric                               SDTypeProfile<1, -1, [SDTCisPtrTy<1>]>,
7720b57cec5SDimitry Andric                               [SDNPHasChain]>;
7730b57cec5SDimitry Andricdef intrinsic_wo_chain : SDNode<"ISD::INTRINSIC_WO_CHAIN",
7740b57cec5SDimitry Andric                                SDTypeProfile<1, -1, [SDTCisPtrTy<1>]>, []>;
7750b57cec5SDimitry Andric
7765ffd83dbSDimitry Andricdef SDT_assert : SDTypeProfile<1, 1,
7770b57cec5SDimitry Andric  [SDTCisInt<0>, SDTCisInt<1>, SDTCisSameAs<1, 0>]>;
7785ffd83dbSDimitry Andricdef assertsext : SDNode<"ISD::AssertSext", SDT_assert>;
7795ffd83dbSDimitry Andricdef assertzext : SDNode<"ISD::AssertZext", SDT_assert>;
7805ffd83dbSDimitry Andricdef assertalign : SDNode<"ISD::AssertAlign", SDT_assert>;
7810b57cec5SDimitry Andric
7820b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
7830b57cec5SDimitry Andric// Selection DAG Condition Codes
7840b57cec5SDimitry Andric
7858bcb0991SDimitry Andricclass CondCode<string fcmpName = "", string icmpName = ""> {
7868bcb0991SDimitry Andric  string ICmpPredicate = icmpName;
7878bcb0991SDimitry Andric  string FCmpPredicate = fcmpName;
7888bcb0991SDimitry Andric}
7890b57cec5SDimitry Andric
7908bcb0991SDimitry Andric// ISD::CondCode enums, and mapping to CmpInst::Predicate names
7918bcb0991SDimitry Andricdef SETOEQ : CondCode<"FCMP_OEQ">;
7928bcb0991SDimitry Andricdef SETOGT : CondCode<"FCMP_OGT">;
7938bcb0991SDimitry Andricdef SETOGE : CondCode<"FCMP_OGE">;
7948bcb0991SDimitry Andricdef SETOLT : CondCode<"FCMP_OLT">;
7958bcb0991SDimitry Andricdef SETOLE : CondCode<"FCMP_OLE">;
7968bcb0991SDimitry Andricdef SETONE : CondCode<"FCMP_ONE">;
7978bcb0991SDimitry Andricdef SETO   : CondCode<"FCMP_ORD">;
7988bcb0991SDimitry Andricdef SETUO  : CondCode<"FCMP_UNO">;
7998bcb0991SDimitry Andricdef SETUEQ : CondCode<"FCMP_UEQ">;
8008bcb0991SDimitry Andricdef SETUGT : CondCode<"FCMP_UGT", "ICMP_UGT">;
8018bcb0991SDimitry Andricdef SETUGE : CondCode<"FCMP_UGE", "ICMP_UGE">;
8028bcb0991SDimitry Andricdef SETULT : CondCode<"FCMP_ULT", "ICMP_ULT">;
8038bcb0991SDimitry Andricdef SETULE : CondCode<"FCMP_ULE", "ICMP_ULE">;
8048bcb0991SDimitry Andricdef SETUNE : CondCode<"FCMP_UNE">;
8058bcb0991SDimitry Andricdef SETEQ : CondCode<"", "ICMP_EQ">;
8068bcb0991SDimitry Andricdef SETGT : CondCode<"", "ICMP_SGT">;
8078bcb0991SDimitry Andricdef SETGE : CondCode<"", "ICMP_SGE">;
8088bcb0991SDimitry Andricdef SETLT : CondCode<"", "ICMP_SLT">;
8098bcb0991SDimitry Andricdef SETLE : CondCode<"", "ICMP_SLE">;
8108bcb0991SDimitry Andricdef SETNE : CondCode<"", "ICMP_NE">;
8110b57cec5SDimitry Andric
8120b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
8130b57cec5SDimitry Andric// Selection DAG Node Transformation Functions.
8140b57cec5SDimitry Andric//
8150b57cec5SDimitry Andric// This mechanism allows targets to manipulate nodes in the output DAG once a
8160b57cec5SDimitry Andric// match has been formed.  This is typically used to manipulate immediate
8170b57cec5SDimitry Andric// values.
8180b57cec5SDimitry Andric//
8190b57cec5SDimitry Andricclass SDNodeXForm<SDNode opc, code xformFunction> {
8200b57cec5SDimitry Andric  SDNode Opcode = opc;
8210b57cec5SDimitry Andric  code XFormFunction = xformFunction;
8220b57cec5SDimitry Andric}
8230b57cec5SDimitry Andric
8240b57cec5SDimitry Andricdef NOOP_SDNodeXForm : SDNodeXForm<imm, [{}]>;
8250b57cec5SDimitry Andric
8260b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
8270b57cec5SDimitry Andric// Selection DAG Pattern Fragments.
8280b57cec5SDimitry Andric//
8290b57cec5SDimitry Andric// Pattern fragments are reusable chunks of dags that match specific things.
8300b57cec5SDimitry Andric// They can take arguments and have C++ predicates that control whether they
8310b57cec5SDimitry Andric// match.  They are intended to make the patterns for common instructions more
8320b57cec5SDimitry Andric// compact and readable.
8330b57cec5SDimitry Andric//
8340b57cec5SDimitry Andric
8350b57cec5SDimitry Andric/// PatFrags - Represents a set of pattern fragments.  Each single fragment
8360b57cec5SDimitry Andric/// can match something on the DAG, from a single node to multiple nested other
8370b57cec5SDimitry Andric/// fragments.   The whole set of fragments matches if any of the single
8385ffd83dbSDimitry Andric/// fragments match.  This allows e.g. matching and "add with overflow" and
8390b57cec5SDimitry Andric/// a regular "add" with the same fragment set.
8400b57cec5SDimitry Andric///
8410b57cec5SDimitry Andricclass PatFrags<dag ops, list<dag> frags, code pred = [{}],
8420b57cec5SDimitry Andric               SDNodeXForm xform = NOOP_SDNodeXForm> : SDPatternOperator {
8430b57cec5SDimitry Andric  dag Operands = ops;
8440b57cec5SDimitry Andric  list<dag> Fragments = frags;
8450b57cec5SDimitry Andric  code PredicateCode = pred;
8460b57cec5SDimitry Andric  code GISelPredicateCode = [{}];
8470b57cec5SDimitry Andric  code ImmediateCode = [{}];
8480b57cec5SDimitry Andric  SDNodeXForm OperandTransform = xform;
8490b57cec5SDimitry Andric
8500b57cec5SDimitry Andric  // When this is set, the PredicateCode may refer to a constant Operands
8510b57cec5SDimitry Andric  // vector which contains the captured nodes of the DAG, in the order listed
8520b57cec5SDimitry Andric  // by the Operands field above.
8530b57cec5SDimitry Andric  //
8540b57cec5SDimitry Andric  // This is useful when Fragments involves associative / commutative
8550b57cec5SDimitry Andric  // operators: a single piece of code can easily refer to all operands even
8560b57cec5SDimitry Andric  // when re-associated / commuted variants of the fragment are matched.
857e8d8bef9SDimitry Andric  bit PredicateCodeUsesOperands = false;
8580b57cec5SDimitry Andric
8590b57cec5SDimitry Andric  // Define a few pre-packaged predicates. This helps GlobalISel import
8600b57cec5SDimitry Andric  // existing rules from SelectionDAG for many common cases.
8610b57cec5SDimitry Andric  // They will be tested prior to the code in pred and must not be used in
8620b57cec5SDimitry Andric  // ImmLeaf and its subclasses.
8630b57cec5SDimitry Andric
864753f127fSDimitry Andric  // If set to true, a predicate is added that checks for the absence of use of
865753f127fSDimitry Andric  // the first result.
866753f127fSDimitry Andric  bit HasNoUse = ?;
867753f127fSDimitry Andric
8680b57cec5SDimitry Andric  // Is the desired pre-packaged predicate for a load?
8690b57cec5SDimitry Andric  bit IsLoad = ?;
8700b57cec5SDimitry Andric  // Is the desired pre-packaged predicate for a store?
8710b57cec5SDimitry Andric  bit IsStore = ?;
8720b57cec5SDimitry Andric  // Is the desired pre-packaged predicate for an atomic?
8730b57cec5SDimitry Andric  bit IsAtomic = ?;
8740b57cec5SDimitry Andric
8750b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getAddressingMode() == ISD::UNINDEXED;
8760b57cec5SDimitry Andric  // cast<StoreSDNode>(N)->getAddressingMode() == ISD::UNINDEXED;
8770b57cec5SDimitry Andric  bit IsUnindexed = ?;
8780b57cec5SDimitry Andric
8790b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getExtensionType() != ISD::NON_EXTLOAD
8800b57cec5SDimitry Andric  bit IsNonExtLoad = ?;
8810b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getExtensionType() == ISD::EXTLOAD;
8820b57cec5SDimitry Andric  bit IsAnyExtLoad = ?;
8830b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getExtensionType() == ISD::SEXTLOAD;
8840b57cec5SDimitry Andric  bit IsSignExtLoad = ?;
8850b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getExtensionType() == ISD::ZEXTLOAD;
8860b57cec5SDimitry Andric  bit IsZeroExtLoad = ?;
8870b57cec5SDimitry Andric  // !cast<StoreSDNode>(N)->isTruncatingStore();
8880b57cec5SDimitry Andric  // cast<StoreSDNode>(N)->isTruncatingStore();
8890b57cec5SDimitry Andric  bit IsTruncStore = ?;
8900b57cec5SDimitry Andric
8910b57cec5SDimitry Andric  // cast<MemSDNode>(N)->getAddressSpace() ==
8920b57cec5SDimitry Andric  // If this empty, accept any address space.
8930b57cec5SDimitry Andric  list<int> AddressSpaces = ?;
8940b57cec5SDimitry Andric
895bdd1243dSDimitry Andric  // cast<MemSDNode>(N)->getAlign() >=
8968bcb0991SDimitry Andric  // If this is empty, accept any alignment.
8978bcb0991SDimitry Andric  int MinAlignment = ?;
8988bcb0991SDimitry Andric
8990b57cec5SDimitry Andric  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::Monotonic
9000b57cec5SDimitry Andric  bit IsAtomicOrderingMonotonic = ?;
9010b57cec5SDimitry Andric  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::Acquire
9020b57cec5SDimitry Andric  bit IsAtomicOrderingAcquire = ?;
9030b57cec5SDimitry Andric  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::Release
9040b57cec5SDimitry Andric  bit IsAtomicOrderingRelease = ?;
9050b57cec5SDimitry Andric  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::AcquireRelease
9060b57cec5SDimitry Andric  bit IsAtomicOrderingAcquireRelease = ?;
9070b57cec5SDimitry Andric  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::SequentiallyConsistent
9080b57cec5SDimitry Andric  bit IsAtomicOrderingSequentiallyConsistent = ?;
9090b57cec5SDimitry Andric
9100b57cec5SDimitry Andric  // isAcquireOrStronger(cast<AtomicSDNode>(N)->getOrdering())
9110b57cec5SDimitry Andric  // !isAcquireOrStronger(cast<AtomicSDNode>(N)->getOrdering())
9120b57cec5SDimitry Andric  bit IsAtomicOrderingAcquireOrStronger = ?;
9130b57cec5SDimitry Andric
9140b57cec5SDimitry Andric  // isReleaseOrStronger(cast<AtomicSDNode>(N)->getOrdering())
9150b57cec5SDimitry Andric  // !isReleaseOrStronger(cast<AtomicSDNode>(N)->getOrdering())
9160b57cec5SDimitry Andric  bit IsAtomicOrderingReleaseOrStronger = ?;
9170b57cec5SDimitry Andric
9180b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getMemoryVT() == MVT::<VT>;
9190b57cec5SDimitry Andric  // cast<StoreSDNode>(N)->getMemoryVT() == MVT::<VT>;
9200b57cec5SDimitry Andric  ValueType MemoryVT = ?;
9210b57cec5SDimitry Andric  // cast<LoadSDNode>(N)->getMemoryVT().getScalarType() == MVT::<VT>;
9220b57cec5SDimitry Andric  // cast<StoreSDNode>(N)->getMemoryVT().getScalarType() == MVT::<VT>;
9230b57cec5SDimitry Andric  ValueType ScalarMemoryVT = ?;
9240b57cec5SDimitry Andric}
9250b57cec5SDimitry Andric
92606c3fb27SDimitry Andric// Patterns and PatFrags can also subclass GISelFlags to set flags that affect
92706c3fb27SDimitry Andric// how GlobalISel behaves when matching them.
92806c3fb27SDimitry Andricclass GISelFlags {
92906c3fb27SDimitry Andric  bit GIIgnoreCopies = ?;
93006c3fb27SDimitry Andric}
93106c3fb27SDimitry Andric
9320b57cec5SDimitry Andric// PatFrag - A version of PatFrags matching only a single fragment.
9330b57cec5SDimitry Andricclass PatFrag<dag ops, dag frag, code pred = [{}],
9340b57cec5SDimitry Andric              SDNodeXForm xform = NOOP_SDNodeXForm>
9350b57cec5SDimitry Andric  : PatFrags<ops, [frag], pred, xform>;
9360b57cec5SDimitry Andric
9370b57cec5SDimitry Andric// OutPatFrag is a pattern fragment that is used as part of an output pattern
9380b57cec5SDimitry Andric// (not an input pattern). These do not have predicates or transforms, but are
9390b57cec5SDimitry Andric// used to avoid repeated subexpressions in output patterns.
9400b57cec5SDimitry Andricclass OutPatFrag<dag ops, dag frag>
9410b57cec5SDimitry Andric : PatFrag<ops, frag, [{}], NOOP_SDNodeXForm>;
9420b57cec5SDimitry Andric
9430b57cec5SDimitry Andric// PatLeaf's are pattern fragments that have no operands.  This is just a helper
9440b57cec5SDimitry Andric// to define immediates and other common things concisely.
9450b57cec5SDimitry Andricclass PatLeaf<dag frag, code pred = [{}], SDNodeXForm xform = NOOP_SDNodeXForm>
9460b57cec5SDimitry Andric : PatFrag<(ops), frag, pred, xform>;
9470b57cec5SDimitry Andric
9480b57cec5SDimitry Andric
9490b57cec5SDimitry Andric// ImmLeaf is a pattern fragment with a constraint on the immediate.  The
9500b57cec5SDimitry Andric// constraint is a function that is run on the immediate (always with the value
9510b57cec5SDimitry Andric// sign extended out to an int64_t) as Imm.  For example:
9520b57cec5SDimitry Andric//
9530b57cec5SDimitry Andric//  def immSExt8 : ImmLeaf<i16, [{ return (char)Imm == Imm; }]>;
9540b57cec5SDimitry Andric//
9550b57cec5SDimitry Andric// this is a more convenient form to match 'imm' nodes in than PatLeaf and also
9560b57cec5SDimitry Andric// is preferred over using PatLeaf because it allows the code generator to
9570b57cec5SDimitry Andric// reason more about the constraint.
9580b57cec5SDimitry Andric//
9590b57cec5SDimitry Andric// If FastIsel should ignore all instructions that have an operand of this type,
9600b57cec5SDimitry Andric// the FastIselShouldIgnore flag can be set.  This is an optimization to reduce
9610b57cec5SDimitry Andric// the code size of the generated fast instruction selector.
9620b57cec5SDimitry Andricclass ImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm,
9630b57cec5SDimitry Andric              SDNode ImmNode = imm>
9640b57cec5SDimitry Andric  : PatFrag<(ops), (vt ImmNode), [{}], xform> {
9650b57cec5SDimitry Andric  let ImmediateCode = pred;
966e8d8bef9SDimitry Andric  bit FastIselShouldIgnore = false;
9670b57cec5SDimitry Andric
9680b57cec5SDimitry Andric  // Is the data type of the immediate an APInt?
969e8d8bef9SDimitry Andric  bit IsAPInt = false;
9700b57cec5SDimitry Andric
9710b57cec5SDimitry Andric  // Is the data type of the immediate an APFloat?
972e8d8bef9SDimitry Andric  bit IsAPFloat = false;
9730b57cec5SDimitry Andric}
9740b57cec5SDimitry Andric
9758bcb0991SDimitry Andric// Convenience wrapper for ImmLeaf to use timm/TargetConstant instead
9768bcb0991SDimitry Andric// of imm/Constant.
9778bcb0991SDimitry Andricclass TImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm,
9788bcb0991SDimitry Andric  SDNode ImmNode = timm> : ImmLeaf<vt, pred, xform, ImmNode>;
9798bcb0991SDimitry Andric
9800b57cec5SDimitry Andric// An ImmLeaf except that Imm is an APInt. This is useful when you need to
9810b57cec5SDimitry Andric// zero-extend the immediate instead of sign-extend it.
9820b57cec5SDimitry Andric//
9830b57cec5SDimitry Andric// Note that FastISel does not currently understand IntImmLeaf and will not
9840b57cec5SDimitry Andric// generate code for rules that make use of it. As such, it does not make sense
9850b57cec5SDimitry Andric// to replace ImmLeaf with IntImmLeaf. However, replacing PatLeaf with an
9860b57cec5SDimitry Andric// IntImmLeaf will allow GlobalISel to import the rule.
9870b57cec5SDimitry Andricclass IntImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm>
9880b57cec5SDimitry Andric    : ImmLeaf<vt, pred, xform> {
989e8d8bef9SDimitry Andric  let IsAPInt = true;
990e8d8bef9SDimitry Andric  let FastIselShouldIgnore = true;
9910b57cec5SDimitry Andric}
9920b57cec5SDimitry Andric
9930b57cec5SDimitry Andric// An ImmLeaf except that Imm is an APFloat.
9940b57cec5SDimitry Andric//
9950b57cec5SDimitry Andric// Note that FastISel does not currently understand FPImmLeaf and will not
9960b57cec5SDimitry Andric// generate code for rules that make use of it.
9970b57cec5SDimitry Andricclass FPImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm>
9980b57cec5SDimitry Andric  : ImmLeaf<vt, pred, xform, fpimm> {
999e8d8bef9SDimitry Andric  let IsAPFloat = true;
1000e8d8bef9SDimitry Andric  let FastIselShouldIgnore = true;
10010b57cec5SDimitry Andric}
10020b57cec5SDimitry Andric
10030b57cec5SDimitry Andric// Leaf fragments.
10040b57cec5SDimitry Andric
10050b57cec5SDimitry Andricdef vtInt      : PatLeaf<(vt),  [{ return N->getVT().isInteger(); }]>;
10060b57cec5SDimitry Andricdef vtFP       : PatLeaf<(vt),  [{ return N->getVT().isFloatingPoint(); }]>;
10070b57cec5SDimitry Andric
1008e8d8bef9SDimitry Andric// Use ISD::isConstantSplatVectorAllOnes or ISD::isConstantSplatVectorAllZeros
1009e8d8bef9SDimitry Andric// to look for the corresponding build_vector or splat_vector. Will look through
1010e8d8bef9SDimitry Andric// bitcasts and check for either opcode, except when used as a pattern root.
1011e8d8bef9SDimitry Andric// When used as a pattern root, only fixed-length build_vector and scalable
1012e8d8bef9SDimitry Andric// splat_vector are supported.
1013fe6060f1SDimitry Andricdef immAllOnesV  : SDPatternOperator; // ISD::isConstantSplatVectorAllOnes
1014fe6060f1SDimitry Andricdef immAllZerosV : SDPatternOperator; // ISD::isConstantSplatVectorAllZeros
10150b57cec5SDimitry Andric
10160b57cec5SDimitry Andric// Other helper fragments.
10170b57cec5SDimitry Andricdef not  : PatFrag<(ops node:$in), (xor node:$in, -1)>;
10180b57cec5SDimitry Andricdef vnot : PatFrag<(ops node:$in), (xor node:$in, immAllOnesV)>;
10190b57cec5SDimitry Andricdef ineg : PatFrag<(ops node:$in), (sub 0, node:$in)>;
10200b57cec5SDimitry Andric
1021e8d8bef9SDimitry Andricdef zanyext : PatFrags<(ops node:$op),
1022e8d8bef9SDimitry Andric                       [(zext node:$op),
1023e8d8bef9SDimitry Andric                        (anyext node:$op)]>;
1024e8d8bef9SDimitry Andric
10250b57cec5SDimitry Andric// null_frag - The null pattern operator is used in multiclass instantiations
10260b57cec5SDimitry Andric// which accept an SDPatternOperator for use in matching patterns for internal
10270b57cec5SDimitry Andric// definitions. When expanding a pattern, if the null fragment is referenced
10280b57cec5SDimitry Andric// in the expansion, the pattern is discarded and it is as-if '[]' had been
10290b57cec5SDimitry Andric// specified. This allows multiclasses to have the isel patterns be optional.
10300b57cec5SDimitry Andricdef null_frag : SDPatternOperator;
10310b57cec5SDimitry Andric
10320b57cec5SDimitry Andric// load fragments.
10330b57cec5SDimitry Andricdef unindexedload : PatFrag<(ops node:$ptr), (ld node:$ptr)> {
1034e8d8bef9SDimitry Andric  let IsLoad = true;
1035e8d8bef9SDimitry Andric  let IsUnindexed = true;
10360b57cec5SDimitry Andric}
10370b57cec5SDimitry Andricdef load : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1038e8d8bef9SDimitry Andric  let IsLoad = true;
1039e8d8bef9SDimitry Andric  let IsNonExtLoad = true;
10400b57cec5SDimitry Andric}
10410b57cec5SDimitry Andric
10420b57cec5SDimitry Andric// extending load fragments.
10430b57cec5SDimitry Andricdef extload   : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1044e8d8bef9SDimitry Andric  let IsLoad = true;
1045e8d8bef9SDimitry Andric  let IsAnyExtLoad = true;
10460b57cec5SDimitry Andric}
10470b57cec5SDimitry Andricdef sextload  : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1048e8d8bef9SDimitry Andric  let IsLoad = true;
1049e8d8bef9SDimitry Andric  let IsSignExtLoad = true;
10500b57cec5SDimitry Andric}
10510b57cec5SDimitry Andricdef zextload  : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1052e8d8bef9SDimitry Andric  let IsLoad = true;
1053e8d8bef9SDimitry Andric  let IsZeroExtLoad = true;
10540b57cec5SDimitry Andric}
10550b57cec5SDimitry Andric
10560b57cec5SDimitry Andricdef extloadi1  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1057e8d8bef9SDimitry Andric  let IsLoad = true;
10580b57cec5SDimitry Andric  let MemoryVT = i1;
10590b57cec5SDimitry Andric}
10600b57cec5SDimitry Andricdef extloadi8  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1061e8d8bef9SDimitry Andric  let IsLoad = true;
10620b57cec5SDimitry Andric  let MemoryVT = i8;
10630b57cec5SDimitry Andric}
10640b57cec5SDimitry Andricdef extloadi16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1065e8d8bef9SDimitry Andric  let IsLoad = true;
10660b57cec5SDimitry Andric  let MemoryVT = i16;
10670b57cec5SDimitry Andric}
10680b57cec5SDimitry Andricdef extloadi32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1069e8d8bef9SDimitry Andric  let IsLoad = true;
10700b57cec5SDimitry Andric  let MemoryVT = i32;
10710b57cec5SDimitry Andric}
10725f757f3fSDimitry Andricdef extloadi64 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
10735f757f3fSDimitry Andric  let IsLoad = true;
10745f757f3fSDimitry Andric  let MemoryVT = i64;
10755f757f3fSDimitry Andric}
10760946e70aSDimitry Andricdef extloadf16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1077e8d8bef9SDimitry Andric  let IsLoad = true;
10780946e70aSDimitry Andric  let MemoryVT = f16;
10790946e70aSDimitry Andric}
10800b57cec5SDimitry Andricdef extloadf32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1081e8d8bef9SDimitry Andric  let IsLoad = true;
10820b57cec5SDimitry Andric  let MemoryVT = f32;
10830b57cec5SDimitry Andric}
10840b57cec5SDimitry Andricdef extloadf64 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1085e8d8bef9SDimitry Andric  let IsLoad = true;
10860b57cec5SDimitry Andric  let MemoryVT = f64;
10870b57cec5SDimitry Andric}
10880b57cec5SDimitry Andric
10890b57cec5SDimitry Andricdef sextloadi1  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1090e8d8bef9SDimitry Andric  let IsLoad = true;
10910b57cec5SDimitry Andric  let MemoryVT = i1;
10920b57cec5SDimitry Andric}
10930b57cec5SDimitry Andricdef sextloadi8  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1094e8d8bef9SDimitry Andric  let IsLoad = true;
10950b57cec5SDimitry Andric  let MemoryVT = i8;
10960b57cec5SDimitry Andric}
10970b57cec5SDimitry Andricdef sextloadi16 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1098e8d8bef9SDimitry Andric  let IsLoad = true;
10990b57cec5SDimitry Andric  let MemoryVT = i16;
11000b57cec5SDimitry Andric}
11010b57cec5SDimitry Andricdef sextloadi32 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1102e8d8bef9SDimitry Andric  let IsLoad = true;
11030b57cec5SDimitry Andric  let MemoryVT = i32;
11040b57cec5SDimitry Andric}
11055f757f3fSDimitry Andricdef sextloadi64 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
11065f757f3fSDimitry Andric  let IsLoad = true;
11075f757f3fSDimitry Andric  let MemoryVT = i64;
11085f757f3fSDimitry Andric}
11090b57cec5SDimitry Andric
11100b57cec5SDimitry Andricdef zextloadi1  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1111e8d8bef9SDimitry Andric  let IsLoad = true;
11120b57cec5SDimitry Andric  let MemoryVT = i1;
11130b57cec5SDimitry Andric}
11140b57cec5SDimitry Andricdef zextloadi8  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1115e8d8bef9SDimitry Andric  let IsLoad = true;
11160b57cec5SDimitry Andric  let MemoryVT = i8;
11170b57cec5SDimitry Andric}
11180b57cec5SDimitry Andricdef zextloadi16 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1119e8d8bef9SDimitry Andric  let IsLoad = true;
11200b57cec5SDimitry Andric  let MemoryVT = i16;
11210b57cec5SDimitry Andric}
11220b57cec5SDimitry Andricdef zextloadi32 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1123e8d8bef9SDimitry Andric  let IsLoad = true;
11240b57cec5SDimitry Andric  let MemoryVT = i32;
11250b57cec5SDimitry Andric}
11265f757f3fSDimitry Andricdef zextloadi64 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
11275f757f3fSDimitry Andric  let IsLoad = true;
11285f757f3fSDimitry Andric  let MemoryVT = i64;
11295f757f3fSDimitry Andric}
11300b57cec5SDimitry Andric
11310b57cec5SDimitry Andricdef extloadvi1  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1132e8d8bef9SDimitry Andric  let IsLoad = true;
11330b57cec5SDimitry Andric  let ScalarMemoryVT = i1;
11340b57cec5SDimitry Andric}
11350b57cec5SDimitry Andricdef extloadvi8  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1136e8d8bef9SDimitry Andric  let IsLoad = true;
11370b57cec5SDimitry Andric  let ScalarMemoryVT = i8;
11380b57cec5SDimitry Andric}
11390b57cec5SDimitry Andricdef extloadvi16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1140e8d8bef9SDimitry Andric  let IsLoad = true;
11410b57cec5SDimitry Andric  let ScalarMemoryVT = i16;
11420b57cec5SDimitry Andric}
11430b57cec5SDimitry Andricdef extloadvi32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1144e8d8bef9SDimitry Andric  let IsLoad = true;
11450b57cec5SDimitry Andric  let ScalarMemoryVT = i32;
11460b57cec5SDimitry Andric}
1147349cc55cSDimitry Andricdef extloadvf16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1148349cc55cSDimitry Andric  let IsLoad = true;
1149349cc55cSDimitry Andric  let ScalarMemoryVT = f16;
1150349cc55cSDimitry Andric}
11510b57cec5SDimitry Andricdef extloadvf32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1152e8d8bef9SDimitry Andric  let IsLoad = true;
11530b57cec5SDimitry Andric  let ScalarMemoryVT = f32;
11540b57cec5SDimitry Andric}
11550b57cec5SDimitry Andricdef extloadvf64 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1156e8d8bef9SDimitry Andric  let IsLoad = true;
11570b57cec5SDimitry Andric  let ScalarMemoryVT = f64;
11580b57cec5SDimitry Andric}
11590b57cec5SDimitry Andric
11600b57cec5SDimitry Andricdef sextloadvi1  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1161e8d8bef9SDimitry Andric  let IsLoad = true;
11620b57cec5SDimitry Andric  let ScalarMemoryVT = i1;
11630b57cec5SDimitry Andric}
11640b57cec5SDimitry Andricdef sextloadvi8  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1165e8d8bef9SDimitry Andric  let IsLoad = true;
11660b57cec5SDimitry Andric  let ScalarMemoryVT = i8;
11670b57cec5SDimitry Andric}
11680b57cec5SDimitry Andricdef sextloadvi16 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1169e8d8bef9SDimitry Andric  let IsLoad = true;
11700b57cec5SDimitry Andric  let ScalarMemoryVT = i16;
11710b57cec5SDimitry Andric}
11720b57cec5SDimitry Andricdef sextloadvi32 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1173e8d8bef9SDimitry Andric  let IsLoad = true;
11740b57cec5SDimitry Andric  let ScalarMemoryVT = i32;
11750b57cec5SDimitry Andric}
11760b57cec5SDimitry Andric
11770b57cec5SDimitry Andricdef zextloadvi1  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1178e8d8bef9SDimitry Andric  let IsLoad = true;
11790b57cec5SDimitry Andric  let ScalarMemoryVT = i1;
11800b57cec5SDimitry Andric}
11810b57cec5SDimitry Andricdef zextloadvi8  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1182e8d8bef9SDimitry Andric  let IsLoad = true;
11830b57cec5SDimitry Andric  let ScalarMemoryVT = i8;
11840b57cec5SDimitry Andric}
11850b57cec5SDimitry Andricdef zextloadvi16 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1186e8d8bef9SDimitry Andric  let IsLoad = true;
11870b57cec5SDimitry Andric  let ScalarMemoryVT = i16;
11880b57cec5SDimitry Andric}
11890b57cec5SDimitry Andricdef zextloadvi32 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1190e8d8bef9SDimitry Andric  let IsLoad = true;
11910b57cec5SDimitry Andric  let ScalarMemoryVT = i32;
11920b57cec5SDimitry Andric}
11930b57cec5SDimitry Andric
11940b57cec5SDimitry Andric// store fragments.
11950b57cec5SDimitry Andricdef unindexedstore : PatFrag<(ops node:$val, node:$ptr),
11960b57cec5SDimitry Andric                             (st node:$val, node:$ptr)> {
1197e8d8bef9SDimitry Andric  let IsStore = true;
1198e8d8bef9SDimitry Andric  let IsUnindexed = true;
11990b57cec5SDimitry Andric}
12000b57cec5SDimitry Andricdef store : PatFrag<(ops node:$val, node:$ptr),
12010b57cec5SDimitry Andric                    (unindexedstore node:$val, node:$ptr)> {
1202e8d8bef9SDimitry Andric  let IsStore = true;
1203e8d8bef9SDimitry Andric  let IsTruncStore = false;
12040b57cec5SDimitry Andric}
12050b57cec5SDimitry Andric
12060b57cec5SDimitry Andric// truncstore fragments.
12070b57cec5SDimitry Andricdef truncstore : PatFrag<(ops node:$val, node:$ptr),
12080b57cec5SDimitry Andric                         (unindexedstore node:$val, node:$ptr)> {
1209e8d8bef9SDimitry Andric  let IsStore = true;
1210e8d8bef9SDimitry Andric  let IsTruncStore = true;
12110b57cec5SDimitry Andric}
12120b57cec5SDimitry Andricdef truncstorei8 : PatFrag<(ops node:$val, node:$ptr),
12130b57cec5SDimitry Andric                           (truncstore node:$val, node:$ptr)> {
1214e8d8bef9SDimitry Andric  let IsStore = true;
12150b57cec5SDimitry Andric  let MemoryVT = i8;
1216fe6060f1SDimitry Andric  let IsTruncStore = true;
12170b57cec5SDimitry Andric}
12180b57cec5SDimitry Andricdef truncstorei16 : PatFrag<(ops node:$val, node:$ptr),
12190b57cec5SDimitry Andric                            (truncstore node:$val, node:$ptr)> {
1220e8d8bef9SDimitry Andric  let IsStore = true;
12210b57cec5SDimitry Andric  let MemoryVT = i16;
1222fe6060f1SDimitry Andric  let IsTruncStore = true;
12230b57cec5SDimitry Andric}
12240b57cec5SDimitry Andricdef truncstorei32 : PatFrag<(ops node:$val, node:$ptr),
12250b57cec5SDimitry Andric                            (truncstore node:$val, node:$ptr)> {
1226e8d8bef9SDimitry Andric  let IsStore = true;
12270b57cec5SDimitry Andric  let MemoryVT = i32;
1228fe6060f1SDimitry Andric  let IsTruncStore = true;
12290b57cec5SDimitry Andric}
12305f757f3fSDimitry Andricdef truncstorei64 : PatFrag<(ops node:$val, node:$ptr),
12315f757f3fSDimitry Andric                            (truncstore node:$val, node:$ptr)> {
12325f757f3fSDimitry Andric  let IsStore = true;
12335f757f3fSDimitry Andric  let MemoryVT = i64;
12345f757f3fSDimitry Andric  let IsTruncStore = true;
12355f757f3fSDimitry Andric}
12360946e70aSDimitry Andricdef truncstoref16 : PatFrag<(ops node:$val, node:$ptr),
12370946e70aSDimitry Andric                            (truncstore node:$val, node:$ptr)> {
1238e8d8bef9SDimitry Andric  let IsStore = true;
12390946e70aSDimitry Andric  let MemoryVT = f16;
12400946e70aSDimitry Andric}
12410b57cec5SDimitry Andricdef truncstoref32 : PatFrag<(ops node:$val, node:$ptr),
12420b57cec5SDimitry Andric                            (truncstore node:$val, node:$ptr)> {
1243e8d8bef9SDimitry Andric  let IsStore = true;
12440b57cec5SDimitry Andric  let MemoryVT = f32;
12450b57cec5SDimitry Andric}
12460b57cec5SDimitry Andricdef truncstoref64 : PatFrag<(ops node:$val, node:$ptr),
12470b57cec5SDimitry Andric                            (truncstore node:$val, node:$ptr)> {
1248e8d8bef9SDimitry Andric  let IsStore = true;
12490b57cec5SDimitry Andric  let MemoryVT = f64;
12500b57cec5SDimitry Andric}
12510b57cec5SDimitry Andric
12520b57cec5SDimitry Andricdef truncstorevi8 : PatFrag<(ops node:$val, node:$ptr),
12530b57cec5SDimitry Andric                            (truncstore node:$val, node:$ptr)> {
1254e8d8bef9SDimitry Andric  let IsStore = true;
12550b57cec5SDimitry Andric  let ScalarMemoryVT = i8;
12560b57cec5SDimitry Andric}
12570b57cec5SDimitry Andric
12580b57cec5SDimitry Andricdef truncstorevi16 : PatFrag<(ops node:$val, node:$ptr),
12590b57cec5SDimitry Andric                             (truncstore node:$val, node:$ptr)> {
1260e8d8bef9SDimitry Andric  let IsStore = true;
12610b57cec5SDimitry Andric  let ScalarMemoryVT = i16;
12620b57cec5SDimitry Andric}
12630b57cec5SDimitry Andric
12640b57cec5SDimitry Andricdef truncstorevi32 : PatFrag<(ops node:$val, node:$ptr),
12650b57cec5SDimitry Andric                             (truncstore node:$val, node:$ptr)> {
1266e8d8bef9SDimitry Andric  let IsStore = true;
12670b57cec5SDimitry Andric  let ScalarMemoryVT = i32;
12680b57cec5SDimitry Andric}
12690b57cec5SDimitry Andric
12700b57cec5SDimitry Andric// indexed store fragments.
12710b57cec5SDimitry Andricdef istore : PatFrag<(ops node:$val, node:$base, node:$offset),
12720b57cec5SDimitry Andric                     (ist node:$val, node:$base, node:$offset)> {
1273e8d8bef9SDimitry Andric  let IsStore = true;
1274e8d8bef9SDimitry Andric  let IsTruncStore = false;
12750b57cec5SDimitry Andric}
12760b57cec5SDimitry Andric
12770b57cec5SDimitry Andricdef pre_store : PatFrag<(ops node:$val, node:$base, node:$offset),
12780b57cec5SDimitry Andric                        (istore node:$val, node:$base, node:$offset), [{
12790b57cec5SDimitry Andric  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
12800b57cec5SDimitry Andric  return AM == ISD::PRE_INC || AM == ISD::PRE_DEC;
12810b57cec5SDimitry Andric}]>;
12820b57cec5SDimitry Andric
12830b57cec5SDimitry Andricdef itruncstore : PatFrag<(ops node:$val, node:$base, node:$offset),
12840b57cec5SDimitry Andric                          (ist node:$val, node:$base, node:$offset)> {
1285e8d8bef9SDimitry Andric  let IsStore = true;
1286e8d8bef9SDimitry Andric  let IsTruncStore = true;
12870b57cec5SDimitry Andric}
12880b57cec5SDimitry Andricdef pre_truncst : PatFrag<(ops node:$val, node:$base, node:$offset),
12890b57cec5SDimitry Andric                          (itruncstore node:$val, node:$base, node:$offset), [{
12900b57cec5SDimitry Andric  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
12910b57cec5SDimitry Andric  return AM == ISD::PRE_INC || AM == ISD::PRE_DEC;
12920b57cec5SDimitry Andric}]>;
12930b57cec5SDimitry Andricdef pre_truncsti1 : PatFrag<(ops node:$val, node:$base, node:$offset),
12940b57cec5SDimitry Andric                            (pre_truncst node:$val, node:$base, node:$offset)> {
1295e8d8bef9SDimitry Andric  let IsStore = true;
12960b57cec5SDimitry Andric  let MemoryVT = i1;
12970b57cec5SDimitry Andric}
12980b57cec5SDimitry Andricdef pre_truncsti8 : PatFrag<(ops node:$val, node:$base, node:$offset),
12990b57cec5SDimitry Andric                            (pre_truncst node:$val, node:$base, node:$offset)> {
1300e8d8bef9SDimitry Andric  let IsStore = true;
13010b57cec5SDimitry Andric  let MemoryVT = i8;
13020b57cec5SDimitry Andric}
13030b57cec5SDimitry Andricdef pre_truncsti16 : PatFrag<(ops node:$val, node:$base, node:$offset),
13040b57cec5SDimitry Andric                             (pre_truncst node:$val, node:$base, node:$offset)> {
1305e8d8bef9SDimitry Andric  let IsStore = true;
13060b57cec5SDimitry Andric  let MemoryVT = i16;
13070b57cec5SDimitry Andric}
13080b57cec5SDimitry Andricdef pre_truncsti32 : PatFrag<(ops node:$val, node:$base, node:$offset),
13090b57cec5SDimitry Andric                             (pre_truncst node:$val, node:$base, node:$offset)> {
1310e8d8bef9SDimitry Andric  let IsStore = true;
13110b57cec5SDimitry Andric  let MemoryVT = i32;
13120b57cec5SDimitry Andric}
13130b57cec5SDimitry Andricdef pre_truncstf32 : PatFrag<(ops node:$val, node:$base, node:$offset),
13140b57cec5SDimitry Andric                             (pre_truncst node:$val, node:$base, node:$offset)> {
1315e8d8bef9SDimitry Andric  let IsStore = true;
13160b57cec5SDimitry Andric  let MemoryVT = f32;
13170b57cec5SDimitry Andric}
13188bcb0991SDimitry Andricdef pre_truncstvi8 : PatFrag<(ops node:$val, node:$base, node:$offset),
13198bcb0991SDimitry Andric                             (pre_truncst node:$val, node:$base, node:$offset)> {
1320e8d8bef9SDimitry Andric  let IsStore = true;
13218bcb0991SDimitry Andric  let ScalarMemoryVT = i8;
13228bcb0991SDimitry Andric}
13238bcb0991SDimitry Andricdef pre_truncstvi16 : PatFrag<(ops node:$val, node:$base, node:$offset),
13248bcb0991SDimitry Andric                              (pre_truncst node:$val, node:$base, node:$offset)> {
1325e8d8bef9SDimitry Andric  let IsStore = true;
13268bcb0991SDimitry Andric  let ScalarMemoryVT = i16;
13278bcb0991SDimitry Andric}
13280b57cec5SDimitry Andric
13290b57cec5SDimitry Andricdef post_store : PatFrag<(ops node:$val, node:$ptr, node:$offset),
13300b57cec5SDimitry Andric                         (istore node:$val, node:$ptr, node:$offset), [{
13310b57cec5SDimitry Andric  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
13320b57cec5SDimitry Andric  return AM == ISD::POST_INC || AM == ISD::POST_DEC;
13330b57cec5SDimitry Andric}]>;
13340b57cec5SDimitry Andric
13350b57cec5SDimitry Andricdef post_truncst : PatFrag<(ops node:$val, node:$base, node:$offset),
13360b57cec5SDimitry Andric                           (itruncstore node:$val, node:$base, node:$offset), [{
13370b57cec5SDimitry Andric  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
13380b57cec5SDimitry Andric  return AM == ISD::POST_INC || AM == ISD::POST_DEC;
13390b57cec5SDimitry Andric}]>;
13400b57cec5SDimitry Andricdef post_truncsti1 : PatFrag<(ops node:$val, node:$base, node:$offset),
13410b57cec5SDimitry Andric                             (post_truncst node:$val, node:$base, node:$offset)> {
1342e8d8bef9SDimitry Andric  let IsStore = true;
13430b57cec5SDimitry Andric  let MemoryVT = i1;
13440b57cec5SDimitry Andric}
13450b57cec5SDimitry Andricdef post_truncsti8 : PatFrag<(ops node:$val, node:$base, node:$offset),
13460b57cec5SDimitry Andric                             (post_truncst node:$val, node:$base, node:$offset)> {
1347e8d8bef9SDimitry Andric  let IsStore = true;
13480b57cec5SDimitry Andric  let MemoryVT = i8;
13490b57cec5SDimitry Andric}
13500b57cec5SDimitry Andricdef post_truncsti16 : PatFrag<(ops node:$val, node:$base, node:$offset),
13510b57cec5SDimitry Andric                              (post_truncst node:$val, node:$base, node:$offset)> {
1352e8d8bef9SDimitry Andric  let IsStore = true;
13530b57cec5SDimitry Andric  let MemoryVT = i16;
13540b57cec5SDimitry Andric}
13550b57cec5SDimitry Andricdef post_truncsti32 : PatFrag<(ops node:$val, node:$base, node:$offset),
13560b57cec5SDimitry Andric                              (post_truncst node:$val, node:$base, node:$offset)> {
1357e8d8bef9SDimitry Andric  let IsStore = true;
13580b57cec5SDimitry Andric  let MemoryVT = i32;
13590b57cec5SDimitry Andric}
13600b57cec5SDimitry Andricdef post_truncstf32 : PatFrag<(ops node:$val, node:$base, node:$offset),
13610b57cec5SDimitry Andric                              (post_truncst node:$val, node:$base, node:$offset)> {
1362e8d8bef9SDimitry Andric  let IsStore = true;
13630b57cec5SDimitry Andric  let MemoryVT = f32;
13640b57cec5SDimitry Andric}
13658bcb0991SDimitry Andricdef post_truncstvi8 : PatFrag<(ops node:$val, node:$base, node:$offset),
13668bcb0991SDimitry Andric                              (post_truncst node:$val, node:$base, node:$offset)> {
1367e8d8bef9SDimitry Andric  let IsStore = true;
13688bcb0991SDimitry Andric  let ScalarMemoryVT = i8;
13698bcb0991SDimitry Andric}
13708bcb0991SDimitry Andricdef post_truncstvi16 : PatFrag<(ops node:$val, node:$base, node:$offset),
13718bcb0991SDimitry Andric                               (post_truncst node:$val, node:$base, node:$offset)> {
1372e8d8bef9SDimitry Andric  let IsStore = true;
13738bcb0991SDimitry Andric  let ScalarMemoryVT = i16;
13748bcb0991SDimitry Andric}
13750b57cec5SDimitry Andric
1376bdd1243dSDimitry Andric// A helper for matching undef or freeze undef
1377bdd1243dSDimitry Andricdef undef_or_freeze_undef : PatFrags<(ops), [(undef), (freeze undef)]>;
1378bdd1243dSDimitry Andric
13798bcb0991SDimitry Andric// TODO: Split these into volatile and unordered flavors to enable
13808bcb0991SDimitry Andric// selectively legal optimizations for each.  (See D66309)
13818bcb0991SDimitry Andricdef simple_load : PatFrag<(ops node:$ptr),
13820b57cec5SDimitry Andric                          (load node:$ptr), [{
13838bcb0991SDimitry Andric  return cast<LoadSDNode>(N)->isSimple();
13840b57cec5SDimitry Andric}]>;
13858bcb0991SDimitry Andricdef simple_store : PatFrag<(ops node:$val, node:$ptr),
13860b57cec5SDimitry Andric                           (store node:$val, node:$ptr), [{
13878bcb0991SDimitry Andric  return cast<StoreSDNode>(N)->isSimple();
13880b57cec5SDimitry Andric}]>;
13890b57cec5SDimitry Andric
13900b57cec5SDimitry Andric// nontemporal store fragments.
13910b57cec5SDimitry Andricdef nontemporalstore : PatFrag<(ops node:$val, node:$ptr),
13920b57cec5SDimitry Andric                               (store node:$val, node:$ptr), [{
13930b57cec5SDimitry Andric  return cast<StoreSDNode>(N)->isNonTemporal();
13940b57cec5SDimitry Andric}]>;
13950b57cec5SDimitry Andric
13960b57cec5SDimitry Andricdef alignednontemporalstore : PatFrag<(ops node:$val, node:$ptr),
13970b57cec5SDimitry Andric                                      (nontemporalstore node:$val, node:$ptr), [{
13980b57cec5SDimitry Andric  StoreSDNode *St = cast<StoreSDNode>(N);
1399bdd1243dSDimitry Andric  return St->getAlign() >= St->getMemoryVT().getStoreSize();
14000b57cec5SDimitry Andric}]>;
14010b57cec5SDimitry Andric
14020b57cec5SDimitry Andricdef unalignednontemporalstore : PatFrag<(ops node:$val, node:$ptr),
14030b57cec5SDimitry Andric                                        (nontemporalstore node:$val, node:$ptr), [{
14040b57cec5SDimitry Andric  StoreSDNode *St = cast<StoreSDNode>(N);
14050b57cec5SDimitry Andric  return St->getAlignment() < St->getMemoryVT().getStoreSize();
14060b57cec5SDimitry Andric}]>;
14070b57cec5SDimitry Andric
14080b57cec5SDimitry Andric// nontemporal load fragments.
14090b57cec5SDimitry Andricdef nontemporalload : PatFrag<(ops node:$ptr),
14100b57cec5SDimitry Andric                               (load node:$ptr), [{
14110b57cec5SDimitry Andric  return cast<LoadSDNode>(N)->isNonTemporal();
14120b57cec5SDimitry Andric}]>;
14130b57cec5SDimitry Andric
14140b57cec5SDimitry Andricdef alignednontemporalload : PatFrag<(ops node:$ptr),
14150b57cec5SDimitry Andric                                      (nontemporalload node:$ptr), [{
14160b57cec5SDimitry Andric  LoadSDNode *Ld = cast<LoadSDNode>(N);
1417bdd1243dSDimitry Andric  return Ld->getAlign() >= Ld->getMemoryVT().getStoreSize();
14180b57cec5SDimitry Andric}]>;
14190b57cec5SDimitry Andric
14200b57cec5SDimitry Andric// setcc convenience fragments.
14210b57cec5SDimitry Andricdef setoeq : PatFrag<(ops node:$lhs, node:$rhs),
14220b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETOEQ)>;
14230b57cec5SDimitry Andricdef setogt : PatFrag<(ops node:$lhs, node:$rhs),
14240b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETOGT)>;
14250b57cec5SDimitry Andricdef setoge : PatFrag<(ops node:$lhs, node:$rhs),
14260b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETOGE)>;
14270b57cec5SDimitry Andricdef setolt : PatFrag<(ops node:$lhs, node:$rhs),
14280b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETOLT)>;
14290b57cec5SDimitry Andricdef setole : PatFrag<(ops node:$lhs, node:$rhs),
14300b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETOLE)>;
14310b57cec5SDimitry Andricdef setone : PatFrag<(ops node:$lhs, node:$rhs),
14320b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETONE)>;
14330b57cec5SDimitry Andricdef seto   : PatFrag<(ops node:$lhs, node:$rhs),
14340b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETO)>;
14350b57cec5SDimitry Andricdef setuo  : PatFrag<(ops node:$lhs, node:$rhs),
14360b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETUO)>;
14370b57cec5SDimitry Andricdef setueq : PatFrag<(ops node:$lhs, node:$rhs),
14380b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETUEQ)>;
14390b57cec5SDimitry Andricdef setugt : PatFrag<(ops node:$lhs, node:$rhs),
14400b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETUGT)>;
14410b57cec5SDimitry Andricdef setuge : PatFrag<(ops node:$lhs, node:$rhs),
14420b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETUGE)>;
14430b57cec5SDimitry Andricdef setult : PatFrag<(ops node:$lhs, node:$rhs),
14440b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETULT)>;
14450b57cec5SDimitry Andricdef setule : PatFrag<(ops node:$lhs, node:$rhs),
14460b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETULE)>;
14470b57cec5SDimitry Andricdef setune : PatFrag<(ops node:$lhs, node:$rhs),
14480b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETUNE)>;
14490b57cec5SDimitry Andricdef seteq  : PatFrag<(ops node:$lhs, node:$rhs),
14500b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETEQ)>;
14510b57cec5SDimitry Andricdef setgt  : PatFrag<(ops node:$lhs, node:$rhs),
14520b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETGT)>;
14530b57cec5SDimitry Andricdef setge  : PatFrag<(ops node:$lhs, node:$rhs),
14540b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETGE)>;
14550b57cec5SDimitry Andricdef setlt  : PatFrag<(ops node:$lhs, node:$rhs),
14560b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETLT)>;
14570b57cec5SDimitry Andricdef setle  : PatFrag<(ops node:$lhs, node:$rhs),
14580b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETLE)>;
14590b57cec5SDimitry Andricdef setne  : PatFrag<(ops node:$lhs, node:$rhs),
14600b57cec5SDimitry Andric                     (setcc node:$lhs, node:$rhs, SETNE)>;
14610b57cec5SDimitry Andric
14620b57cec5SDimitry Andric// We don't have strict FP extended loads as single DAG nodes, but we can
14630b57cec5SDimitry Andric// still provide convenience fragments to match those operations.
14640b57cec5SDimitry Andricdef strict_extloadf32 : PatFrag<(ops node:$ptr),
14650b57cec5SDimitry Andric                                (strict_fpextend (f32 (load node:$ptr)))>;
14660b57cec5SDimitry Andricdef strict_extloadf64 : PatFrag<(ops node:$ptr),
14670b57cec5SDimitry Andric                                (strict_fpextend (f64 (load node:$ptr)))>;
14680b57cec5SDimitry Andric
14690b57cec5SDimitry Andric// Convenience fragments to match both strict and non-strict fp operations
14700b57cec5SDimitry Andricdef any_fadd       : PatFrags<(ops node:$lhs, node:$rhs),
14710b57cec5SDimitry Andric                              [(strict_fadd node:$lhs, node:$rhs),
14720b57cec5SDimitry Andric                               (fadd node:$lhs, node:$rhs)]>;
14730b57cec5SDimitry Andricdef any_fsub       : PatFrags<(ops node:$lhs, node:$rhs),
14740b57cec5SDimitry Andric                              [(strict_fsub node:$lhs, node:$rhs),
14750b57cec5SDimitry Andric                               (fsub node:$lhs, node:$rhs)]>;
14760b57cec5SDimitry Andricdef any_fmul       : PatFrags<(ops node:$lhs, node:$rhs),
14770b57cec5SDimitry Andric                              [(strict_fmul node:$lhs, node:$rhs),
14780b57cec5SDimitry Andric                               (fmul node:$lhs, node:$rhs)]>;
14790b57cec5SDimitry Andricdef any_fdiv       : PatFrags<(ops node:$lhs, node:$rhs),
14800b57cec5SDimitry Andric                              [(strict_fdiv node:$lhs, node:$rhs),
14810b57cec5SDimitry Andric                               (fdiv node:$lhs, node:$rhs)]>;
14820b57cec5SDimitry Andricdef any_frem       : PatFrags<(ops node:$lhs, node:$rhs),
14830b57cec5SDimitry Andric                              [(strict_frem node:$lhs, node:$rhs),
14840b57cec5SDimitry Andric                               (frem node:$lhs, node:$rhs)]>;
14850b57cec5SDimitry Andricdef any_fma        : PatFrags<(ops node:$src1, node:$src2, node:$src3),
14860b57cec5SDimitry Andric                              [(strict_fma node:$src1, node:$src2, node:$src3),
14870b57cec5SDimitry Andric                               (fma node:$src1, node:$src2, node:$src3)]>;
14880b57cec5SDimitry Andricdef any_fsqrt      : PatFrags<(ops node:$src),
14890b57cec5SDimitry Andric                              [(strict_fsqrt node:$src),
14900b57cec5SDimitry Andric                               (fsqrt node:$src)]>;
14910b57cec5SDimitry Andricdef any_fsin       : PatFrags<(ops node:$src),
14920b57cec5SDimitry Andric                              [(strict_fsin node:$src),
14930b57cec5SDimitry Andric                               (fsin node:$src)]>;
14940b57cec5SDimitry Andricdef any_fcos       : PatFrags<(ops node:$src),
14950b57cec5SDimitry Andric                              [(strict_fcos node:$src),
14960b57cec5SDimitry Andric                               (fcos node:$src)]>;
14970b57cec5SDimitry Andricdef any_fexp2      : PatFrags<(ops node:$src),
14980b57cec5SDimitry Andric                              [(strict_fexp2 node:$src),
14990b57cec5SDimitry Andric                               (fexp2 node:$src)]>;
15000b57cec5SDimitry Andricdef any_fpow       : PatFrags<(ops node:$lhs, node:$rhs),
15010b57cec5SDimitry Andric                              [(strict_fpow node:$lhs, node:$rhs),
15020b57cec5SDimitry Andric                               (fpow node:$lhs, node:$rhs)]>;
150306c3fb27SDimitry Andricdef any_fldexp      : PatFrags<(ops node:$lhs, node:$rhs),
150406c3fb27SDimitry Andric                              [(strict_fldexp node:$lhs, node:$rhs),
150506c3fb27SDimitry Andric                               (fldexp node:$lhs, node:$rhs)]>;
15060b57cec5SDimitry Andricdef any_flog2      : PatFrags<(ops node:$src),
15070b57cec5SDimitry Andric                              [(strict_flog2 node:$src),
15080b57cec5SDimitry Andric                               (flog2 node:$src)]>;
15090b57cec5SDimitry Andricdef any_frint      : PatFrags<(ops node:$src),
15100b57cec5SDimitry Andric                              [(strict_frint node:$src),
15110b57cec5SDimitry Andric                               (frint node:$src)]>;
15128bcb0991SDimitry Andricdef any_lrint      : PatFrags<(ops node:$src),
15138bcb0991SDimitry Andric                              [(strict_lrint node:$src),
15148bcb0991SDimitry Andric                               (lrint node:$src)]>;
15158bcb0991SDimitry Andricdef any_llrint     : PatFrags<(ops node:$src),
15168bcb0991SDimitry Andric                              [(strict_llrint node:$src),
15178bcb0991SDimitry Andric                               (llrint node:$src)]>;
15180b57cec5SDimitry Andricdef any_fnearbyint : PatFrags<(ops node:$src),
15190b57cec5SDimitry Andric                              [(strict_fnearbyint node:$src),
15200b57cec5SDimitry Andric                               (fnearbyint node:$src)]>;
15210b57cec5SDimitry Andricdef any_fceil      : PatFrags<(ops node:$src),
15220b57cec5SDimitry Andric                              [(strict_fceil node:$src),
15230b57cec5SDimitry Andric                               (fceil node:$src)]>;
15240b57cec5SDimitry Andricdef any_ffloor     : PatFrags<(ops node:$src),
15250b57cec5SDimitry Andric                              [(strict_ffloor node:$src),
15260b57cec5SDimitry Andric                               (ffloor node:$src)]>;
15278bcb0991SDimitry Andricdef any_lround     : PatFrags<(ops node:$src),
15288bcb0991SDimitry Andric                              [(strict_lround node:$src),
15298bcb0991SDimitry Andric                               (lround node:$src)]>;
15308bcb0991SDimitry Andricdef any_llround    : PatFrags<(ops node:$src),
15318bcb0991SDimitry Andric                              [(strict_llround node:$src),
15328bcb0991SDimitry Andric                               (llround node:$src)]>;
15330b57cec5SDimitry Andricdef any_fround     : PatFrags<(ops node:$src),
15340b57cec5SDimitry Andric                              [(strict_fround node:$src),
15350b57cec5SDimitry Andric                               (fround node:$src)]>;
1536fe6060f1SDimitry Andricdef any_froundeven : PatFrags<(ops node:$src),
1537fe6060f1SDimitry Andric                              [(strict_froundeven node:$src),
1538fe6060f1SDimitry Andric                               (froundeven node:$src)]>;
15390b57cec5SDimitry Andricdef any_ftrunc     : PatFrags<(ops node:$src),
15400b57cec5SDimitry Andric                              [(strict_ftrunc node:$src),
15410b57cec5SDimitry Andric                               (ftrunc node:$src)]>;
15420b57cec5SDimitry Andricdef any_fmaxnum    : PatFrags<(ops node:$lhs, node:$rhs),
15430b57cec5SDimitry Andric                              [(strict_fmaxnum node:$lhs, node:$rhs),
15440b57cec5SDimitry Andric                               (fmaxnum node:$lhs, node:$rhs)]>;
15450b57cec5SDimitry Andricdef any_fminnum    : PatFrags<(ops node:$lhs, node:$rhs),
15460b57cec5SDimitry Andric                              [(strict_fminnum node:$lhs, node:$rhs),
15470b57cec5SDimitry Andric                               (fminnum node:$lhs, node:$rhs)]>;
1548480093f4SDimitry Andricdef any_fmaximum   : PatFrags<(ops node:$lhs, node:$rhs),
1549480093f4SDimitry Andric                              [(strict_fmaximum node:$lhs, node:$rhs),
1550480093f4SDimitry Andric                               (fmaximum node:$lhs, node:$rhs)]>;
1551480093f4SDimitry Andricdef any_fminimum   : PatFrags<(ops node:$lhs, node:$rhs),
1552480093f4SDimitry Andric                              [(strict_fminimum node:$lhs, node:$rhs),
1553480093f4SDimitry Andric                               (fminimum node:$lhs, node:$rhs)]>;
15540b57cec5SDimitry Andricdef any_fpround    : PatFrags<(ops node:$src),
15550b57cec5SDimitry Andric                              [(strict_fpround node:$src),
15560b57cec5SDimitry Andric                               (fpround node:$src)]>;
15570b57cec5SDimitry Andricdef any_fpextend   : PatFrags<(ops node:$src),
15580b57cec5SDimitry Andric                              [(strict_fpextend node:$src),
15590b57cec5SDimitry Andric                               (fpextend node:$src)]>;
15600b57cec5SDimitry Andricdef any_extloadf32 : PatFrags<(ops node:$ptr),
15610b57cec5SDimitry Andric                              [(strict_extloadf32 node:$ptr),
15620b57cec5SDimitry Andric                               (extloadf32 node:$ptr)]>;
15630b57cec5SDimitry Andricdef any_extloadf64 : PatFrags<(ops node:$ptr),
15640b57cec5SDimitry Andric                              [(strict_extloadf64 node:$ptr),
15650b57cec5SDimitry Andric                               (extloadf64 node:$ptr)]>;
15668bcb0991SDimitry Andricdef any_fp_to_sint : PatFrags<(ops node:$src),
15678bcb0991SDimitry Andric                              [(strict_fp_to_sint node:$src),
15688bcb0991SDimitry Andric                               (fp_to_sint node:$src)]>;
15698bcb0991SDimitry Andricdef any_fp_to_uint : PatFrags<(ops node:$src),
15708bcb0991SDimitry Andric                              [(strict_fp_to_uint node:$src),
15718bcb0991SDimitry Andric                               (fp_to_uint node:$src)]>;
1572480093f4SDimitry Andricdef any_sint_to_fp : PatFrags<(ops node:$src),
1573480093f4SDimitry Andric                              [(strict_sint_to_fp node:$src),
1574480093f4SDimitry Andric                               (sint_to_fp node:$src)]>;
1575480093f4SDimitry Andricdef any_uint_to_fp : PatFrags<(ops node:$src),
1576480093f4SDimitry Andric                              [(strict_uint_to_fp node:$src),
1577480093f4SDimitry Andric                               (uint_to_fp node:$src)]>;
1578e8d8bef9SDimitry Andricdef any_fsetcc : PatFrags<(ops node:$lhs, node:$rhs, node:$pred),
1579e8d8bef9SDimitry Andric                          [(strict_fsetcc node:$lhs, node:$rhs, node:$pred),
1580e8d8bef9SDimitry Andric                           (setcc node:$lhs, node:$rhs, node:$pred)]>;
1581e8d8bef9SDimitry Andricdef any_fsetccs : PatFrags<(ops node:$lhs, node:$rhs, node:$pred),
1582e8d8bef9SDimitry Andric                          [(strict_fsetccs node:$lhs, node:$rhs, node:$pred),
1583e8d8bef9SDimitry Andric                           (setcc node:$lhs, node:$rhs, node:$pred)]>;
15840b57cec5SDimitry Andric
15851db9f3b2SDimitry Andricdef any_f16_to_fp : PatFrags<(ops node:$src),
15861db9f3b2SDimitry Andric                              [(f16_to_fp node:$src),
15871db9f3b2SDimitry Andric                               (strict_f16_to_fp node:$src)]>;
15881db9f3b2SDimitry Andricdef any_fp_to_f16 : PatFrags<(ops node:$src),
15891db9f3b2SDimitry Andric                              [(fp_to_f16 node:$src),
15901db9f3b2SDimitry Andric                               (strict_fp_to_f16 node:$src)]>;
15911db9f3b2SDimitry Andric
1592349cc55cSDimitry Andricmulticlass binary_atomic_op_ord {
15935ffd83dbSDimitry Andric  def NAME#_monotonic : PatFrag<(ops node:$ptr, node:$val),
15945ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1595e8d8bef9SDimitry Andric    let IsAtomic = true;
1596e8d8bef9SDimitry Andric    let IsAtomicOrderingMonotonic = true;
15970b57cec5SDimitry Andric  }
15985ffd83dbSDimitry Andric  def NAME#_acquire : PatFrag<(ops node:$ptr, node:$val),
15995ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1600e8d8bef9SDimitry Andric    let IsAtomic = true;
1601e8d8bef9SDimitry Andric    let IsAtomicOrderingAcquire = true;
16020b57cec5SDimitry Andric  }
16035ffd83dbSDimitry Andric  def NAME#_release : PatFrag<(ops node:$ptr, node:$val),
16045ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1605e8d8bef9SDimitry Andric    let IsAtomic = true;
1606e8d8bef9SDimitry Andric    let IsAtomicOrderingRelease = true;
16070b57cec5SDimitry Andric  }
16085ffd83dbSDimitry Andric  def NAME#_acq_rel : PatFrag<(ops node:$ptr, node:$val),
16095ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1610e8d8bef9SDimitry Andric    let IsAtomic = true;
1611e8d8bef9SDimitry Andric    let IsAtomicOrderingAcquireRelease = true;
16120b57cec5SDimitry Andric  }
16135ffd83dbSDimitry Andric  def NAME#_seq_cst : PatFrag<(ops node:$ptr, node:$val),
16145ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1615e8d8bef9SDimitry Andric    let IsAtomic = true;
1616e8d8bef9SDimitry Andric    let IsAtomicOrderingSequentiallyConsistent = true;
16170b57cec5SDimitry Andric  }
16180b57cec5SDimitry Andric}
16190b57cec5SDimitry Andric
1620349cc55cSDimitry Andricmulticlass ternary_atomic_op_ord {
16215ffd83dbSDimitry Andric  def NAME#_monotonic : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16225ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1623e8d8bef9SDimitry Andric    let IsAtomic = true;
1624e8d8bef9SDimitry Andric    let IsAtomicOrderingMonotonic = true;
16250b57cec5SDimitry Andric  }
16265ffd83dbSDimitry Andric  def NAME#_acquire : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16275ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1628e8d8bef9SDimitry Andric    let IsAtomic = true;
1629e8d8bef9SDimitry Andric    let IsAtomicOrderingAcquire = true;
16300b57cec5SDimitry Andric  }
16315ffd83dbSDimitry Andric  def NAME#_release : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16325ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1633e8d8bef9SDimitry Andric    let IsAtomic = true;
1634e8d8bef9SDimitry Andric    let IsAtomicOrderingRelease = true;
16350b57cec5SDimitry Andric  }
16365ffd83dbSDimitry Andric  def NAME#_acq_rel : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16375ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1638e8d8bef9SDimitry Andric    let IsAtomic = true;
1639e8d8bef9SDimitry Andric    let IsAtomicOrderingAcquireRelease = true;
16400b57cec5SDimitry Andric  }
16415ffd83dbSDimitry Andric  def NAME#_seq_cst : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16425ffd83dbSDimitry Andric      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1643e8d8bef9SDimitry Andric    let IsAtomic = true;
1644e8d8bef9SDimitry Andric    let IsAtomicOrderingSequentiallyConsistent = true;
16450b57cec5SDimitry Andric  }
16460b57cec5SDimitry Andric}
16470b57cec5SDimitry Andric
16488bcb0991SDimitry Andricmulticlass binary_atomic_op<SDNode atomic_op, bit IsInt = 1> {
16490b57cec5SDimitry Andric  def _8 : PatFrag<(ops node:$ptr, node:$val),
16500b57cec5SDimitry Andric                   (atomic_op  node:$ptr, node:$val)> {
1651e8d8bef9SDimitry Andric    let IsAtomic = true;
16528bcb0991SDimitry Andric    let MemoryVT = !if(IsInt, i8, ?);
16530b57cec5SDimitry Andric  }
16540b57cec5SDimitry Andric  def _16 : PatFrag<(ops node:$ptr, node:$val),
16550b57cec5SDimitry Andric                    (atomic_op node:$ptr, node:$val)> {
1656e8d8bef9SDimitry Andric    let IsAtomic = true;
16578bcb0991SDimitry Andric    let MemoryVT = !if(IsInt, i16, f16);
16580b57cec5SDimitry Andric  }
16590b57cec5SDimitry Andric  def _32 : PatFrag<(ops node:$ptr, node:$val),
16600b57cec5SDimitry Andric                    (atomic_op node:$ptr, node:$val)> {
1661e8d8bef9SDimitry Andric    let IsAtomic = true;
16628bcb0991SDimitry Andric    let MemoryVT = !if(IsInt, i32, f32);
16630b57cec5SDimitry Andric  }
16640b57cec5SDimitry Andric  def _64 : PatFrag<(ops node:$ptr, node:$val),
16650b57cec5SDimitry Andric                    (atomic_op node:$ptr, node:$val)> {
1666e8d8bef9SDimitry Andric    let IsAtomic = true;
16678bcb0991SDimitry Andric    let MemoryVT = !if(IsInt, i64, f64);
16680b57cec5SDimitry Andric  }
16690b57cec5SDimitry Andric
1670349cc55cSDimitry Andric  defm NAME#_8  : binary_atomic_op_ord;
1671349cc55cSDimitry Andric  defm NAME#_16 : binary_atomic_op_ord;
1672349cc55cSDimitry Andric  defm NAME#_32 : binary_atomic_op_ord;
1673349cc55cSDimitry Andric  defm NAME#_64 : binary_atomic_op_ord;
16740b57cec5SDimitry Andric}
16750b57cec5SDimitry Andric
16760b57cec5SDimitry Andricmulticlass ternary_atomic_op<SDNode atomic_op> {
16770b57cec5SDimitry Andric  def _8 : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16780b57cec5SDimitry Andric                   (atomic_op  node:$ptr, node:$cmp, node:$val)> {
1679e8d8bef9SDimitry Andric    let IsAtomic = true;
16800b57cec5SDimitry Andric    let MemoryVT = i8;
16810b57cec5SDimitry Andric  }
16820b57cec5SDimitry Andric  def _16 : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16830b57cec5SDimitry Andric                    (atomic_op node:$ptr, node:$cmp, node:$val)> {
1684e8d8bef9SDimitry Andric    let IsAtomic = true;
16850b57cec5SDimitry Andric    let MemoryVT = i16;
16860b57cec5SDimitry Andric  }
16870b57cec5SDimitry Andric  def _32 : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16880b57cec5SDimitry Andric                    (atomic_op node:$ptr, node:$cmp, node:$val)> {
1689e8d8bef9SDimitry Andric    let IsAtomic = true;
16900b57cec5SDimitry Andric    let MemoryVT = i32;
16910b57cec5SDimitry Andric  }
16920b57cec5SDimitry Andric  def _64 : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
16930b57cec5SDimitry Andric                    (atomic_op node:$ptr, node:$cmp, node:$val)> {
1694e8d8bef9SDimitry Andric    let IsAtomic = true;
16950b57cec5SDimitry Andric    let MemoryVT = i64;
16960b57cec5SDimitry Andric  }
16970b57cec5SDimitry Andric
1698349cc55cSDimitry Andric  defm NAME#_8  : ternary_atomic_op_ord;
1699349cc55cSDimitry Andric  defm NAME#_16 : ternary_atomic_op_ord;
1700349cc55cSDimitry Andric  defm NAME#_32 : ternary_atomic_op_ord;
1701349cc55cSDimitry Andric  defm NAME#_64 : ternary_atomic_op_ord;
17020b57cec5SDimitry Andric}
17030b57cec5SDimitry Andric
17040b57cec5SDimitry Andricdefm atomic_load_add  : binary_atomic_op<atomic_load_add>;
17050b57cec5SDimitry Andricdefm atomic_swap      : binary_atomic_op<atomic_swap>;
17060b57cec5SDimitry Andricdefm atomic_load_sub  : binary_atomic_op<atomic_load_sub>;
17070b57cec5SDimitry Andricdefm atomic_load_and  : binary_atomic_op<atomic_load_and>;
17080b57cec5SDimitry Andricdefm atomic_load_clr  : binary_atomic_op<atomic_load_clr>;
17090b57cec5SDimitry Andricdefm atomic_load_or   : binary_atomic_op<atomic_load_or>;
17100b57cec5SDimitry Andricdefm atomic_load_xor  : binary_atomic_op<atomic_load_xor>;
17110b57cec5SDimitry Andricdefm atomic_load_nand : binary_atomic_op<atomic_load_nand>;
17120b57cec5SDimitry Andricdefm atomic_load_min  : binary_atomic_op<atomic_load_min>;
17130b57cec5SDimitry Andricdefm atomic_load_max  : binary_atomic_op<atomic_load_max>;
17140b57cec5SDimitry Andricdefm atomic_load_umin : binary_atomic_op<atomic_load_umin>;
17150b57cec5SDimitry Andricdefm atomic_load_umax : binary_atomic_op<atomic_load_umax>;
17160b57cec5SDimitry Andricdefm atomic_cmp_swap  : ternary_atomic_op<atomic_cmp_swap>;
17170b57cec5SDimitry Andric
1718753f127fSDimitry Andric/// Atomic load which zeroes the excess high bits.
1719753f127fSDimitry Andricdef atomic_load_zext :
1720753f127fSDimitry Andric  PatFrag<(ops node:$ptr), (atomic_load node:$ptr)> {
1721753f127fSDimitry Andric  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1722753f127fSDimitry Andric  let IsZeroExtLoad = true;
1723753f127fSDimitry Andric}
1724753f127fSDimitry Andric
1725753f127fSDimitry Andric/// Atomic load which sign extends the excess high bits.
1726753f127fSDimitry Andricdef atomic_load_sext :
1727753f127fSDimitry Andric  PatFrag<(ops node:$ptr), (atomic_load node:$ptr)> {
1728753f127fSDimitry Andric  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1729753f127fSDimitry Andric  let IsSignExtLoad = true;
1730753f127fSDimitry Andric}
1731753f127fSDimitry Andric
17320b57cec5SDimitry Andricdef atomic_load_8 :
17330b57cec5SDimitry Andric  PatFrag<(ops node:$ptr),
17340b57cec5SDimitry Andric          (atomic_load node:$ptr)> {
1735e8d8bef9SDimitry Andric  let IsAtomic = true;
17360b57cec5SDimitry Andric  let MemoryVT = i8;
17370b57cec5SDimitry Andric}
1738753f127fSDimitry Andric
17390b57cec5SDimitry Andricdef atomic_load_16 :
17400b57cec5SDimitry Andric  PatFrag<(ops node:$ptr),
17410b57cec5SDimitry Andric          (atomic_load node:$ptr)> {
1742e8d8bef9SDimitry Andric  let IsAtomic = true;
17430b57cec5SDimitry Andric  let MemoryVT = i16;
17440b57cec5SDimitry Andric}
1745753f127fSDimitry Andric
17460b57cec5SDimitry Andricdef atomic_load_32 :
17470b57cec5SDimitry Andric  PatFrag<(ops node:$ptr),
17480b57cec5SDimitry Andric          (atomic_load node:$ptr)> {
1749e8d8bef9SDimitry Andric  let IsAtomic = true;
17500b57cec5SDimitry Andric  let MemoryVT = i32;
17510b57cec5SDimitry Andric}
17520b57cec5SDimitry Andricdef atomic_load_64 :
17530b57cec5SDimitry Andric  PatFrag<(ops node:$ptr),
17540b57cec5SDimitry Andric          (atomic_load node:$ptr)> {
1755e8d8bef9SDimitry Andric  let IsAtomic = true;
17560b57cec5SDimitry Andric  let MemoryVT = i64;
17570b57cec5SDimitry Andric}
17580b57cec5SDimitry Andric
1759753f127fSDimitry Andricdef atomic_load_zext_8 :
1760753f127fSDimitry Andric  PatFrag<(ops node:$ptr), (atomic_load_zext node:$ptr)> {
1761753f127fSDimitry Andric  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1762753f127fSDimitry Andric  let MemoryVT = i8;
1763753f127fSDimitry Andric}
1764753f127fSDimitry Andric
1765753f127fSDimitry Andricdef atomic_load_zext_16 :
1766753f127fSDimitry Andric  PatFrag<(ops node:$ptr), (atomic_load_zext node:$ptr)> {
1767753f127fSDimitry Andric  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1768753f127fSDimitry Andric  let MemoryVT = i16;
1769753f127fSDimitry Andric}
1770753f127fSDimitry Andric
1771753f127fSDimitry Andricdef atomic_load_sext_8 :
1772753f127fSDimitry Andric  PatFrag<(ops node:$ptr), (atomic_load_sext node:$ptr)> {
1773753f127fSDimitry Andric  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1774753f127fSDimitry Andric  let MemoryVT = i8;
1775753f127fSDimitry Andric}
1776753f127fSDimitry Andric
1777753f127fSDimitry Andricdef atomic_load_sext_16 :
1778753f127fSDimitry Andric  PatFrag<(ops node:$ptr), (atomic_load_sext node:$ptr)> {
1779753f127fSDimitry Andric  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1780753f127fSDimitry Andric  let MemoryVT = i16;
1781753f127fSDimitry Andric}
1782753f127fSDimitry Andric
1783753f127fSDimitry Andric// Atomic load which zeroes or anyextends the high bits.
1784753f127fSDimitry Andricdef atomic_load_az_8 : PatFrags<(ops node:$op),
1785753f127fSDimitry Andric                                [(atomic_load_8 node:$op),
1786753f127fSDimitry Andric                                 (atomic_load_zext_8 node:$op)]>;
1787753f127fSDimitry Andric
1788753f127fSDimitry Andric// Atomic load which zeroes or anyextends the high bits.
1789753f127fSDimitry Andricdef atomic_load_az_16 : PatFrags<(ops node:$op),
1790753f127fSDimitry Andric                                 [(atomic_load_16 node:$op),
1791753f127fSDimitry Andric                                  (atomic_load_zext_16 node:$op)]>;
1792753f127fSDimitry Andric
179381ad6265SDimitry Andricdef nonext_masked_gather :
179481ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
179581ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
179681ad6265SDimitry Andric  return cast<MaskedGatherSDNode>(N)->getExtensionType() == ISD::NON_EXTLOAD;
179781ad6265SDimitry Andric}]>;
179881ad6265SDimitry Andric
179981ad6265SDimitry Andric// Any extending masked gather fragments.
180081ad6265SDimitry Andricdef ext_masked_gather_i8 :
180181ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
180281ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
180381ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
180481ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::EXTLOAD &&
180581ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i8;
180681ad6265SDimitry Andric}]>;
180781ad6265SDimitry Andricdef ext_masked_gather_i16 :
180881ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
180981ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
181081ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
181181ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::EXTLOAD &&
181281ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i16;
181381ad6265SDimitry Andric}]>;
181481ad6265SDimitry Andricdef ext_masked_gather_i32 :
181581ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
181681ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
181781ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
181881ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::EXTLOAD &&
181981ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i32;
182081ad6265SDimitry Andric}]>;
182181ad6265SDimitry Andric
182281ad6265SDimitry Andric// Sign extending masked gather fragments.
182381ad6265SDimitry Andricdef sext_masked_gather_i8 :
182481ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
182581ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
182681ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
182781ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::SEXTLOAD &&
182881ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i8;
182981ad6265SDimitry Andric}]>;
183081ad6265SDimitry Andricdef sext_masked_gather_i16 :
183181ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
183281ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
183381ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
183481ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::SEXTLOAD &&
183581ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i16;
183681ad6265SDimitry Andric}]>;
183781ad6265SDimitry Andricdef sext_masked_gather_i32 :
183881ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
183981ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
184081ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
184181ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::SEXTLOAD &&
184281ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i32;
184381ad6265SDimitry Andric}]>;
184481ad6265SDimitry Andric
184581ad6265SDimitry Andric// Zero extending masked gather fragments.
184681ad6265SDimitry Andricdef zext_masked_gather_i8 :
184781ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
184881ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
184981ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
185081ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::ZEXTLOAD &&
185181ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i8;
185281ad6265SDimitry Andric}]>;
185381ad6265SDimitry Andricdef zext_masked_gather_i16 :
185481ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
185581ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
185681ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
185781ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::ZEXTLOAD &&
185881ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i16;
185981ad6265SDimitry Andric}]>;
186081ad6265SDimitry Andricdef zext_masked_gather_i32 :
186181ad6265SDimitry Andric  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
186281ad6265SDimitry Andric          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
186381ad6265SDimitry Andric  auto MGN = cast<MaskedGatherSDNode>(N);
186481ad6265SDimitry Andric  return MGN->getExtensionType() == ISD::ZEXTLOAD &&
186581ad6265SDimitry Andric         MGN->getMemoryVT().getScalarType() == MVT::i32;
186681ad6265SDimitry Andric}]>;
186781ad6265SDimitry Andric
186881ad6265SDimitry Andric// Any/Zero extending masked gather fragments.
186981ad6265SDimitry Andricdef azext_masked_gather_i8 :
187081ad6265SDimitry Andric  PatFrags<(ops node:$def, node:$pred, node:$ptr, node:$idx),
187181ad6265SDimitry Andric           [(ext_masked_gather_i8 node:$def, node:$pred, node:$ptr, node:$idx),
187281ad6265SDimitry Andric            (zext_masked_gather_i8 node:$def, node:$pred, node:$ptr, node:$idx)]>;
187381ad6265SDimitry Andricdef azext_masked_gather_i16 :
187481ad6265SDimitry Andric  PatFrags<(ops node:$def, node:$pred, node:$ptr, node:$idx),
187581ad6265SDimitry Andric           [(ext_masked_gather_i16 node:$def, node:$pred, node:$ptr, node:$idx),
187681ad6265SDimitry Andric            (zext_masked_gather_i16 node:$def, node:$pred, node:$ptr, node:$idx)]>;
187781ad6265SDimitry Andricdef azext_masked_gather_i32 :
187881ad6265SDimitry Andric  PatFrags<(ops node:$def, node:$pred, node:$ptr, node:$idx),
187981ad6265SDimitry Andric           [(ext_masked_gather_i32 node:$def, node:$pred, node:$ptr, node:$idx),
188081ad6265SDimitry Andric            (zext_masked_gather_i32 node:$def, node:$pred, node:$ptr, node:$idx)]>;
188181ad6265SDimitry Andric
188281ad6265SDimitry Andricdef nontrunc_masked_scatter :
188381ad6265SDimitry Andric  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
188481ad6265SDimitry Andric          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
188581ad6265SDimitry Andric  return !cast<MaskedScatterSDNode>(N)->isTruncatingStore();
188681ad6265SDimitry Andric}]>;
188781ad6265SDimitry Andric
188881ad6265SDimitry Andric// Truncating masked scatter fragments.
188981ad6265SDimitry Andricdef trunc_masked_scatter_i8 :
189081ad6265SDimitry Andric  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
189181ad6265SDimitry Andric          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
189281ad6265SDimitry Andric  auto MSN = cast<MaskedScatterSDNode>(N);
189381ad6265SDimitry Andric  return MSN->isTruncatingStore() &&
189481ad6265SDimitry Andric         MSN->getMemoryVT().getScalarType() == MVT::i8;
189581ad6265SDimitry Andric}]>;
189681ad6265SDimitry Andricdef trunc_masked_scatter_i16 :
189781ad6265SDimitry Andric  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
189881ad6265SDimitry Andric          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
189981ad6265SDimitry Andric  auto MSN = cast<MaskedScatterSDNode>(N);
190081ad6265SDimitry Andric  return MSN->isTruncatingStore() &&
190181ad6265SDimitry Andric         MSN->getMemoryVT().getScalarType() == MVT::i16;
190281ad6265SDimitry Andric}]>;
190381ad6265SDimitry Andricdef trunc_masked_scatter_i32 :
190481ad6265SDimitry Andric  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
190581ad6265SDimitry Andric          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
190681ad6265SDimitry Andric  auto MSN = cast<MaskedScatterSDNode>(N);
190781ad6265SDimitry Andric  return MSN->isTruncatingStore() &&
190881ad6265SDimitry Andric         MSN->getMemoryVT().getScalarType() == MVT::i32;
190981ad6265SDimitry Andric}]>;
191081ad6265SDimitry Andric
19115f757f3fSDimitry Andric
19125f757f3fSDimitry Andricdef atomic_store_8 :
19135f757f3fSDimitry Andric  PatFrag<(ops node:$val, node:$ptr),
19145f757f3fSDimitry Andric          (atomic_store node:$val, node:$ptr)> {
19155f757f3fSDimitry Andric  let IsAtomic = true;
19165f757f3fSDimitry Andric  let MemoryVT = i8;
19175f757f3fSDimitry Andric}
19185f757f3fSDimitry Andric
19195f757f3fSDimitry Andricdef atomic_store_16 :
19205f757f3fSDimitry Andric  PatFrag<(ops node:$val, node:$ptr),
19215f757f3fSDimitry Andric          (atomic_store node:$val, node:$ptr)> {
19225f757f3fSDimitry Andric  let IsAtomic = true;
19235f757f3fSDimitry Andric  let MemoryVT = i16;
19245f757f3fSDimitry Andric}
19255f757f3fSDimitry Andric
19265f757f3fSDimitry Andricdef atomic_store_32 :
19275f757f3fSDimitry Andric  PatFrag<(ops node:$val, node:$ptr),
19285f757f3fSDimitry Andric          (atomic_store node:$val, node:$ptr)> {
19295f757f3fSDimitry Andric  let IsAtomic = true;
19305f757f3fSDimitry Andric  let MemoryVT = i32;
19315f757f3fSDimitry Andric}
19325f757f3fSDimitry Andric
19335f757f3fSDimitry Andricdef atomic_store_64 :
19345f757f3fSDimitry Andric  PatFrag<(ops node:$val, node:$ptr),
19355f757f3fSDimitry Andric          (atomic_store node:$val, node:$ptr)> {
19365f757f3fSDimitry Andric  let IsAtomic = true;
19375f757f3fSDimitry Andric  let MemoryVT = i64;
19385f757f3fSDimitry Andric}
19395f757f3fSDimitry Andric
19400b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
19410b57cec5SDimitry Andric// Selection DAG Pattern Support.
19420b57cec5SDimitry Andric//
19430b57cec5SDimitry Andric// Patterns are what are actually matched against by the target-flavored
19440b57cec5SDimitry Andric// instruction selection DAG.  Instructions defined by the target implicitly
19450b57cec5SDimitry Andric// define patterns in most cases, but patterns can also be explicitly added when
19460b57cec5SDimitry Andric// an operation is defined by a sequence of instructions (e.g. loading a large
19470b57cec5SDimitry Andric// immediate value on RISC targets that do not support immediates as large as
19480b57cec5SDimitry Andric// their GPRs).
19490b57cec5SDimitry Andric//
19500b57cec5SDimitry Andric
19510b57cec5SDimitry Andricclass Pattern<dag patternToMatch, list<dag> resultInstrs> {
19520b57cec5SDimitry Andric  dag             PatternToMatch  = patternToMatch;
19530b57cec5SDimitry Andric  list<dag>       ResultInstrs    = resultInstrs;
19540b57cec5SDimitry Andric  list<Predicate> Predicates      = [];  // See class Instruction in Target.td.
19550b57cec5SDimitry Andric  int             AddedComplexity = 0;   // See class Instruction in Target.td.
19560b57cec5SDimitry Andric}
19570b57cec5SDimitry Andric
19580b57cec5SDimitry Andric// Pat - A simple (but common) form of a pattern, which produces a simple result
19590b57cec5SDimitry Andric// not needing a full list.
19600b57cec5SDimitry Andricclass Pat<dag pattern, dag result> : Pattern<pattern, [result]>;
19610b57cec5SDimitry Andric
19620b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
19630b57cec5SDimitry Andric// Complex pattern definitions.
19640b57cec5SDimitry Andric//
19650b57cec5SDimitry Andric
19660b57cec5SDimitry Andric// Complex patterns, e.g. X86 addressing mode, requires pattern matching code
196706c3fb27SDimitry Andric// in C++. Ty is the type of return value; NumOperands is the number of operands
196806c3fb27SDimitry Andric// returned by the select function; SelectFunc is the name of the function used
196906c3fb27SDimitry Andric// to pattern match the max. pattern; RootNodes are the list of possible root nodes
197006c3fb27SDimitry Andric// of the sub-dags to match.
197106c3fb27SDimitry Andric// e.g. X86 addressing mode - def addr : ComplexPattern<iPTR, 4, "SelectAddr", [add]>;
19720b57cec5SDimitry Andric//
19730b57cec5SDimitry Andricclass ComplexPattern<ValueType ty, int numops, string fn,
19740b57cec5SDimitry Andric                     list<SDNode> roots = [], list<SDNodeProperty> props = [],
19750b57cec5SDimitry Andric                     int complexity = -1> {
19760b57cec5SDimitry Andric  ValueType Ty = ty;
19770b57cec5SDimitry Andric  int NumOperands = numops;
19780b57cec5SDimitry Andric  string SelectFunc = fn;
19790b57cec5SDimitry Andric  list<SDNode> RootNodes = roots;
19800b57cec5SDimitry Andric  list<SDNodeProperty> Properties = props;
19810b57cec5SDimitry Andric  int Complexity = complexity;
19820b57cec5SDimitry Andric}
1983