xref: /freebsd/contrib/llvm-project/llvm/include/llvm/Target/TargetSelectionDAG.td (revision 415efcecd8b80f68e76376ef2b854cb6f5c84b5a)
1//===- TargetSelectionDAG.td - Common code for DAG isels ---*- tablegen -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines the target-independent interfaces used by SelectionDAG
10// instruction selection generators.
11//
12//===----------------------------------------------------------------------===//
13
14//===----------------------------------------------------------------------===//
15// Selection DAG Type Constraint definitions.
16//
17// Note that the semantics of these constraints are hard coded into tblgen.  To
18// modify or add constraints, you have to hack tblgen.
19//
20
21class SDTypeConstraint<int opnum> {
22  int OperandNum = opnum;
23}
24
25// SDTCisVT - The specified operand has exactly this VT.
26class SDTCisVT<int OpNum, ValueType vt> : SDTypeConstraint<OpNum> {
27  ValueType VT = vt;
28}
29
30class SDTCisPtrTy<int OpNum> : SDTypeConstraint<OpNum>;
31
32// SDTCisInt - The specified operand has integer type.
33class SDTCisInt<int OpNum> : SDTypeConstraint<OpNum>;
34
35// SDTCisFP - The specified operand has floating-point type.
36class SDTCisFP<int OpNum> : SDTypeConstraint<OpNum>;
37
38// SDTCisVec - The specified operand has a vector type.
39class SDTCisVec<int OpNum> : SDTypeConstraint<OpNum>;
40
41// SDTCisSameAs - The two specified operands have identical types.
42class SDTCisSameAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
43  int OtherOperandNum = OtherOp;
44}
45
46// SDTCisVTSmallerThanOp - The specified operand is a VT SDNode, and its type is
47// smaller than the 'Other' operand.
48class SDTCisVTSmallerThanOp<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
49  int OtherOperandNum = OtherOp;
50}
51
52class SDTCisOpSmallerThanOp<int SmallOp, int BigOp> : SDTypeConstraint<SmallOp>{
53  int BigOperandNum = BigOp;
54}
55
56/// SDTCisEltOfVec - This indicates that ThisOp is a scalar type of the same
57/// type as the element type of OtherOp, which is a vector type.
58class SDTCisEltOfVec<int ThisOp, int OtherOp>
59  : SDTypeConstraint<ThisOp> {
60  int OtherOpNum = OtherOp;
61}
62
63/// SDTCisSubVecOfVec - This indicates that ThisOp is a vector type
64/// with length less that of OtherOp, which is a vector type.
65class SDTCisSubVecOfVec<int ThisOp, int OtherOp>
66  : SDTypeConstraint<ThisOp> {
67  int OtherOpNum = OtherOp;
68}
69
70// SDTCVecEltisVT - The specified operand is vector type with element type
71// of VT.
72class SDTCVecEltisVT<int OpNum, ValueType vt> : SDTypeConstraint<OpNum> {
73  ValueType VT = vt;
74}
75
76// SDTCisSameNumEltsAs - The two specified operands have identical number
77// of elements.
78class SDTCisSameNumEltsAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
79  int OtherOperandNum = OtherOp;
80}
81
82// SDTCisSameSizeAs - The two specified operands have identical size.
83class SDTCisSameSizeAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> {
84  int OtherOperandNum = OtherOp;
85}
86
87//===----------------------------------------------------------------------===//
88// Selection DAG Type Profile definitions.
89//
90// These use the constraints defined above to describe the type requirements of
91// the various nodes.  These are not hard coded into tblgen, allowing targets to
92// add their own if needed.
93//
94
95// SDTypeProfile - This profile describes the type requirements of a Selection
96// DAG node.
97class SDTypeProfile<int numresults, int numoperands,
98                    list<SDTypeConstraint> constraints> {
99  int NumResults = numresults;
100  int NumOperands = numoperands;
101  list<SDTypeConstraint> Constraints = constraints;
102}
103
104// Builtin profiles.
105def SDTIntLeaf: SDTypeProfile<1, 0, [SDTCisInt<0>]>;         // for 'imm'.
106def SDTFPLeaf : SDTypeProfile<1, 0, [SDTCisFP<0>]>;          // for 'fpimm'.
107def SDTPtrLeaf: SDTypeProfile<1, 0, [SDTCisPtrTy<0>]>;       // for '&g'.
108def SDTOther  : SDTypeProfile<1, 0, [SDTCisVT<0, OtherVT>]>; // for 'vt'.
109def SDTUNDEF  : SDTypeProfile<1, 0, []>;                     // for 'undef'.
110def SDTUnaryOp  : SDTypeProfile<1, 1, []>;                   // for bitconvert.
111
112def SDTPtrAddOp : SDTypeProfile<1, 2, [     // ptradd
113  SDTCisSameAs<0, 1>, SDTCisInt<2>, SDTCisPtrTy<1>
114]>;
115def SDTIntBinOp : SDTypeProfile<1, 2, [     // add, and, or, xor, udiv, etc.
116  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0>
117]>;
118def SDTIntShiftOp : SDTypeProfile<1, 2, [   // shl, sra, srl
119  SDTCisSameAs<0, 1>, SDTCisInt<0>, SDTCisInt<2>
120]>;
121def SDTIntShiftDOp: SDTypeProfile<1, 3, [   // fshl, fshr
122  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0>, SDTCisInt<3>
123]>;
124def SDTIntSatNoShOp : SDTypeProfile<1, 2, [   // ssat with no shift
125  SDTCisSameAs<0, 1>, SDTCisInt<2>
126]>;
127def SDTIntBinHiLoOp : SDTypeProfile<2, 2, [ // mulhi, mullo, sdivrem, udivrem
128  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisSameAs<0, 3>,SDTCisInt<0>
129]>;
130def SDTIntScaledBinOp : SDTypeProfile<1, 3, [  // smulfix, sdivfix, etc
131  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0>, SDTCisInt<3>
132]>;
133
134def SDTFPBinOp : SDTypeProfile<1, 2, [      // fadd, fmul, etc.
135  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisFP<0>
136]>;
137def SDTFPSignOp : SDTypeProfile<1, 2, [     // fcopysign.
138  SDTCisSameAs<0, 1>, SDTCisFP<0>, SDTCisFP<2>
139]>;
140def SDTFPTernaryOp : SDTypeProfile<1, 3, [  // fmadd, fnmsub, etc.
141  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisSameAs<0, 3>, SDTCisFP<0>
142]>;
143def SDTIntUnaryOp : SDTypeProfile<1, 1, [ // bitreverse
144  SDTCisSameAs<0, 1>, SDTCisInt<0>
145]>;
146def SDTIntBitCountUnaryOp : SDTypeProfile<1, 1, [   // ctlz, cttz
147  SDTCisInt<0>, SDTCisInt<1>
148]>;
149def SDTIntExtendOp : SDTypeProfile<1, 1, [  // sext, zext, anyext
150  SDTCisInt<0>, SDTCisInt<1>, SDTCisOpSmallerThanOp<1, 0>, SDTCisSameNumEltsAs<0, 1>
151]>;
152def SDTIntTruncOp  : SDTypeProfile<1, 1, [  // trunc
153  SDTCisInt<0>, SDTCisInt<1>, SDTCisOpSmallerThanOp<0, 1>, SDTCisSameNumEltsAs<0, 1>
154]>;
155def SDTFPUnaryOp  : SDTypeProfile<1, 1, [   // fneg, fsqrt, etc
156  SDTCisSameAs<0, 1>, SDTCisFP<0>
157]>;
158def SDTFPRoundOp  : SDTypeProfile<1, 1, [   // fpround
159  SDTCisFP<0>, SDTCisFP<1>, SDTCisOpSmallerThanOp<0, 1>, SDTCisSameNumEltsAs<0, 1>
160]>;
161def SDTFPExtendOp  : SDTypeProfile<1, 1, [  // fpextend
162  SDTCisFP<0>, SDTCisFP<1>, SDTCisOpSmallerThanOp<1, 0>, SDTCisSameNumEltsAs<0, 1>
163]>;
164def SDIsFPClassOp : SDTypeProfile<1, 2, [   // is_fpclass
165  SDTCisInt<0>, SDTCisFP<1>, SDTCisInt<2>, SDTCisSameNumEltsAs<0, 1>
166]>;
167def SDTIntToFPOp : SDTypeProfile<1, 1, [    // [su]int_to_fp
168  SDTCisFP<0>, SDTCisInt<1>, SDTCisSameNumEltsAs<0, 1>
169]>;
170def SDTFPToIntOp : SDTypeProfile<1, 1, [    // fp_to_[su]int
171  SDTCisInt<0>, SDTCisFP<1>, SDTCisSameNumEltsAs<0, 1>
172]>;
173def SDTFPToIntSatOp : SDTypeProfile<1, 2, [    // fp_to_[su]int_sat
174  SDTCisInt<0>, SDTCisFP<1>, SDTCisSameNumEltsAs<0, 1>, SDTCisVT<2, OtherVT>
175]>;
176def SDTFPExpOp : SDTypeProfile<1, 2, [      // ldexp
177  SDTCisSameAs<0, 1>, SDTCisFP<0>, SDTCisInt<2>
178]>;
179def SDTGetFPStateOp : SDTypeProfile<1, 0, [ // get_fpenv, get_fpmode
180  SDTCisInt<0>
181]>;
182def SDTSetFPStateOp : SDTypeProfile<0, 1, [ // set_fpenv, set_fpmode
183  SDTCisInt<0>
184]>;
185def SDTExtInreg : SDTypeProfile<1, 2, [     // sext_inreg
186  SDTCisSameAs<0, 1>, SDTCisInt<0>, SDTCisVT<2, OtherVT>,
187  SDTCisVTSmallerThanOp<2, 1>
188]>;
189def SDTExtInvec : SDTypeProfile<1, 1, [     // sext_invec
190  SDTCisInt<0>, SDTCisVec<0>, SDTCisInt<1>, SDTCisVec<1>,
191  SDTCisOpSmallerThanOp<1, 0>
192]>;
193def SDTFreeze : SDTypeProfile<1, 1, [
194  SDTCisSameAs<0, 1>
195]>;
196
197def SDTSetCC : SDTypeProfile<1, 3, [        // setcc
198  SDTCisInt<0>, SDTCisSameAs<1, 2>, SDTCisVT<3, OtherVT>
199]>;
200
201def SDTSelect : SDTypeProfile<1, 3, [       // select
202  SDTCisInt<1>, SDTCisSameAs<0, 2>, SDTCisSameAs<2, 3>
203]>;
204
205def SDTVSelect : SDTypeProfile<1, 3, [       // vselect
206  SDTCisVec<0>, SDTCisInt<1>, SDTCisSameAs<0, 2>, SDTCisSameAs<2, 3>, SDTCisSameNumEltsAs<0, 1>
207]>;
208
209def SDTSelectCC : SDTypeProfile<1, 5, [     // select_cc
210  SDTCisSameAs<1, 2>, SDTCisSameAs<3, 4>, SDTCisSameAs<0, 3>,
211  SDTCisVT<5, OtherVT>
212]>;
213
214def SDTBr : SDTypeProfile<0, 1, [           // br
215  SDTCisVT<0, OtherVT>
216]>;
217
218def SDTBrCC : SDTypeProfile<0, 4, [       // brcc
219  SDTCisVT<0, OtherVT>, SDTCisSameAs<1, 2>, SDTCisVT<3, OtherVT>
220]>;
221
222def SDTBrcond : SDTypeProfile<0, 2, [       // brcond
223  SDTCisInt<0>, SDTCisVT<1, OtherVT>
224]>;
225
226def SDTBrind : SDTypeProfile<0, 1, [        // brind
227  SDTCisPtrTy<0>
228]>;
229
230def SDTCatchret : SDTypeProfile<0, 2, [     // catchret
231  SDTCisVT<0, OtherVT>, SDTCisVT<1, OtherVT>
232]>;
233
234def SDTCleanupret : SDTypeProfile<0, 1, [   // cleanupret
235  SDTCisVT<0, OtherVT>
236]>;
237
238def SDTNone : SDTypeProfile<0, 0, []>;      // ret, trap
239
240def SDTUBSANTrap : SDTypeProfile<0, 1, []>;      // ubsantrap
241
242def SDTLoad : SDTypeProfile<1, 1, [         // load
243  SDTCisPtrTy<1>
244]>;
245
246def SDTStore : SDTypeProfile<0, 2, [        // store
247  SDTCisPtrTy<1>
248]>;
249
250def SDTIStore : SDTypeProfile<1, 3, [       // indexed store
251  SDTCisSameAs<0, 2>, SDTCisPtrTy<0>, SDTCisPtrTy<3>
252]>;
253
254def SDTMaskedStore: SDTypeProfile<0, 4, [       // masked store
255  SDTCisVec<0>, SDTCisPtrTy<1>, SDTCisPtrTy<2>, SDTCisVec<3>, SDTCisSameNumEltsAs<0, 3>
256]>;
257
258def SDTMaskedLoad: SDTypeProfile<1, 4, [       // masked load
259  SDTCisVec<0>, SDTCisPtrTy<1>, SDTCisPtrTy<2>, SDTCisVec<3>, SDTCisSameAs<0, 4>,
260  SDTCisSameNumEltsAs<0, 3>
261]>;
262
263def SDTMaskedGather : SDTypeProfile<1, 4, [
264  SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisVec<2>, SDTCisPtrTy<3>, SDTCisVec<4>,
265  SDTCisSameNumEltsAs<0, 2>, SDTCisSameNumEltsAs<0, 4>
266]>;
267
268def SDTMaskedScatter : SDTypeProfile<0, 4, [
269  SDTCisVec<0>, SDTCisVec<1>, SDTCisPtrTy<2>, SDTCisVec<3>,
270  SDTCisSameNumEltsAs<0, 1>, SDTCisSameNumEltsAs<0, 3>
271]>;
272
273def SDTVectorCompress : SDTypeProfile<1, 3, [
274  SDTCisVec<0>, SDTCisSameAs<0, 1>,
275  SDTCisVec<2>, SDTCisSameNumEltsAs<1, 2>,
276  SDTCisSameAs<1, 3>
277]>;
278
279def SDTVecShuffle : SDTypeProfile<1, 2, [
280  SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>
281]>;
282def SDTVecSlice : SDTypeProfile<1, 3, [     // vector splice
283  SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>, SDTCisInt<3>
284]>;
285def SDTVecExtract : SDTypeProfile<1, 2, [   // vector extract
286  SDTCisEltOfVec<0, 1>, SDTCisPtrTy<2>
287]>;
288def SDTVecInsert : SDTypeProfile<1, 3, [    // vector insert
289  SDTCisEltOfVec<2, 1>, SDTCisSameAs<0, 1>, SDTCisPtrTy<3>
290]>;
291def SDTVecReduce : SDTypeProfile<1, 1, [    // vector reduction
292  SDTCisInt<0>, SDTCisVec<1>
293]>;
294def SDTFPVecReduce : SDTypeProfile<1, 1, [  // FP vector reduction
295  SDTCisFP<0>, SDTCisVec<1>
296]>;
297
298def SDTVecReverse : SDTypeProfile<1, 1, [  // vector reverse
299  SDTCisVec<0>, SDTCisSameAs<0,1>
300]>;
301
302def SDTSubVecExtract : SDTypeProfile<1, 2, [// subvector extract
303  SDTCisSubVecOfVec<0,1>, SDTCisInt<2>
304]>;
305def SDTSubVecInsert : SDTypeProfile<1, 3, [ // subvector insert
306  SDTCisSubVecOfVec<2, 1>, SDTCisSameAs<0,1>, SDTCisInt<3>
307]>;
308
309def SDTPrefetch : SDTypeProfile<0, 4, [     // prefetch
310  SDTCisPtrTy<0>, SDTCisSameAs<1, 2>, SDTCisSameAs<1, 3>, SDTCisInt<1>
311]>;
312
313def SDTAtomicFence : SDTypeProfile<0, 2, [
314  SDTCisSameAs<0,1>, SDTCisPtrTy<0>
315]>;
316def SDTAtomic3 : SDTypeProfile<1, 3, [
317  SDTCisSameAs<0,2>,  SDTCisSameAs<0,3>, SDTCisInt<0>, SDTCisPtrTy<1>
318]>;
319def SDTAtomic2 : SDTypeProfile<1, 2, [
320  SDTCisSameAs<0,2>, SDTCisInt<0>, SDTCisPtrTy<1>
321]>;
322
323def SDTFPAtomic2 : SDTypeProfile<1, 2, [
324  SDTCisSameAs<0,2>, SDTCisFP<0>, SDTCisPtrTy<1>
325]>;
326
327def SDTAtomicStore : SDTypeProfile<0, 2, [
328  SDTCisInt<0>, SDTCisPtrTy<1>
329]>;
330def SDTAtomicLoad : SDTypeProfile<1, 1, [
331  SDTCisPtrTy<1>
332]>;
333
334class SDCallSeqStart<list<SDTypeConstraint> constraints> :
335        SDTypeProfile<0, 2, constraints>;
336class SDCallSeqEnd<list<SDTypeConstraint> constraints> :
337        SDTypeProfile<0, 2, constraints>;
338
339//===----------------------------------------------------------------------===//
340// Selection DAG Node definitions.
341//
342class SDNode<string opcode, SDTypeProfile typeprof,
343             list<SDNodeProperty> props = [], string sdclass = "SDNode">
344             : SDPatternOperator {
345  string Opcode  = opcode;
346  string SDClass = sdclass;
347  let Properties = props;
348  SDTypeProfile TypeProfile = typeprof;
349}
350
351// Special TableGen-recognized dag nodes
352def set;
353def implicit;
354def node;
355def srcvalue;
356
357def imm        : SDNode<"ISD::Constant"  , SDTIntLeaf , [], "ConstantSDNode">;
358def timm       : SDNode<"ISD::TargetConstant",SDTIntLeaf, [], "ConstantSDNode">;
359def fpimm      : SDNode<"ISD::ConstantFP", SDTFPLeaf  , [], "ConstantFPSDNode">;
360def vt         : SDNode<"ISD::VALUETYPE" , SDTOther   , [], "VTSDNode">;
361def bb         : SDNode<"ISD::BasicBlock", SDTOther   , [], "BasicBlockSDNode">;
362def cond       : SDNode<"ISD::CONDCODE"  , SDTOther   , [], "CondCodeSDNode">;
363def undef      : SDNode<"ISD::UNDEF"     , SDTUNDEF   , []>;
364def vscale     : SDNode<"ISD::VSCALE"    , SDTIntUnaryOp, []>;
365def globaladdr : SDNode<"ISD::GlobalAddress",         SDTPtrLeaf, [],
366                        "GlobalAddressSDNode">;
367def tglobaladdr : SDNode<"ISD::TargetGlobalAddress",  SDTPtrLeaf, [],
368                         "GlobalAddressSDNode">;
369def globaltlsaddr : SDNode<"ISD::GlobalTLSAddress",         SDTPtrLeaf, [],
370                          "GlobalAddressSDNode">;
371def tglobaltlsaddr : SDNode<"ISD::TargetGlobalTLSAddress",  SDTPtrLeaf, [],
372                           "GlobalAddressSDNode">;
373def constpool   : SDNode<"ISD::ConstantPool",         SDTPtrLeaf, [],
374                         "ConstantPoolSDNode">;
375def tconstpool  : SDNode<"ISD::TargetConstantPool",   SDTPtrLeaf, [],
376                         "ConstantPoolSDNode">;
377def jumptable   : SDNode<"ISD::JumpTable",            SDTPtrLeaf, [],
378                         "JumpTableSDNode">;
379def tjumptable  : SDNode<"ISD::TargetJumpTable",      SDTPtrLeaf, [],
380                         "JumpTableSDNode">;
381def frameindex  : SDNode<"ISD::FrameIndex",           SDTPtrLeaf, [],
382                         "FrameIndexSDNode">;
383def tframeindex : SDNode<"ISD::TargetFrameIndex",     SDTPtrLeaf, [],
384                         "FrameIndexSDNode">;
385def externalsym : SDNode<"ISD::ExternalSymbol",       SDTPtrLeaf, [],
386                         "ExternalSymbolSDNode">;
387def texternalsym: SDNode<"ISD::TargetExternalSymbol", SDTPtrLeaf, [],
388                         "ExternalSymbolSDNode">;
389def mcsym: SDNode<"ISD::MCSymbol", SDTPtrLeaf, [], "MCSymbolSDNode">;
390def blockaddress : SDNode<"ISD::BlockAddress",        SDTPtrLeaf, [],
391                         "BlockAddressSDNode">;
392def tblockaddress: SDNode<"ISD::TargetBlockAddress",  SDTPtrLeaf, [],
393                         "BlockAddressSDNode">;
394
395def add        : SDNode<"ISD::ADD"       , SDTIntBinOp   ,
396                        [SDNPCommutative, SDNPAssociative]>;
397def ptradd     : SDNode<"ISD::ADD"       , SDTPtrAddOp, []>;
398def sub        : SDNode<"ISD::SUB"       , SDTIntBinOp>;
399def mul        : SDNode<"ISD::MUL"       , SDTIntBinOp,
400                        [SDNPCommutative, SDNPAssociative]>;
401def mulhs      : SDNode<"ISD::MULHS"     , SDTIntBinOp, [SDNPCommutative]>;
402def mulhu      : SDNode<"ISD::MULHU"     , SDTIntBinOp, [SDNPCommutative]>;
403def avgfloors  : SDNode<"ISD::AVGFLOORS" , SDTIntBinOp, [SDNPCommutative]>;
404def avgflooru  : SDNode<"ISD::AVGFLOORU" , SDTIntBinOp, [SDNPCommutative]>;
405def avgceils   : SDNode<"ISD::AVGCEILS"  , SDTIntBinOp, [SDNPCommutative]>;
406def avgceilu   : SDNode<"ISD::AVGCEILU"  , SDTIntBinOp, [SDNPCommutative]>;
407def abds       : SDNode<"ISD::ABDS"      , SDTIntBinOp, [SDNPCommutative]>;
408def abdu       : SDNode<"ISD::ABDU"      , SDTIntBinOp, [SDNPCommutative]>;
409def smullohi   : SDNode<"ISD::SMUL_LOHI" , SDTIntBinHiLoOp, [SDNPCommutative]>;
410def umullohi   : SDNode<"ISD::UMUL_LOHI" , SDTIntBinHiLoOp, [SDNPCommutative]>;
411def sdiv       : SDNode<"ISD::SDIV"      , SDTIntBinOp>;
412def udiv       : SDNode<"ISD::UDIV"      , SDTIntBinOp>;
413def srem       : SDNode<"ISD::SREM"      , SDTIntBinOp>;
414def urem       : SDNode<"ISD::UREM"      , SDTIntBinOp>;
415def sdivrem    : SDNode<"ISD::SDIVREM"   , SDTIntBinHiLoOp>;
416def udivrem    : SDNode<"ISD::UDIVREM"   , SDTIntBinHiLoOp>;
417def srl        : SDNode<"ISD::SRL"       , SDTIntShiftOp>;
418def sra        : SDNode<"ISD::SRA"       , SDTIntShiftOp>;
419def shl        : SDNode<"ISD::SHL"       , SDTIntShiftOp>;
420def rotl       : SDNode<"ISD::ROTL"      , SDTIntShiftOp>;
421def rotr       : SDNode<"ISD::ROTR"      , SDTIntShiftOp>;
422def fshl       : SDNode<"ISD::FSHL"      , SDTIntShiftDOp>;
423def fshr       : SDNode<"ISD::FSHR"      , SDTIntShiftDOp>;
424def and        : SDNode<"ISD::AND"       , SDTIntBinOp,
425                        [SDNPCommutative, SDNPAssociative]>;
426def or         : SDNode<"ISD::OR"        , SDTIntBinOp,
427                        [SDNPCommutative, SDNPAssociative]>;
428def xor        : SDNode<"ISD::XOR"       , SDTIntBinOp,
429                        [SDNPCommutative, SDNPAssociative]>;
430def addc       : SDNode<"ISD::ADDC"      , SDTIntBinOp,
431                        [SDNPCommutative, SDNPOutGlue]>;
432def adde       : SDNode<"ISD::ADDE"      , SDTIntBinOp,
433                        [SDNPCommutative, SDNPOutGlue, SDNPInGlue]>;
434def subc       : SDNode<"ISD::SUBC"      , SDTIntBinOp,
435                        [SDNPOutGlue]>;
436def sube       : SDNode<"ISD::SUBE"      , SDTIntBinOp,
437                        [SDNPOutGlue, SDNPInGlue]>;
438def smin       : SDNode<"ISD::SMIN"      , SDTIntBinOp,
439                                  [SDNPCommutative, SDNPAssociative]>;
440def smax       : SDNode<"ISD::SMAX"      , SDTIntBinOp,
441                                  [SDNPCommutative, SDNPAssociative]>;
442def umin       : SDNode<"ISD::UMIN"      , SDTIntBinOp,
443                                  [SDNPCommutative, SDNPAssociative]>;
444def umax       : SDNode<"ISD::UMAX"      , SDTIntBinOp,
445                                  [SDNPCommutative, SDNPAssociative]>;
446
447def scmp       : SDNode<"ISD::SCMP"      , SDTIntBinOp,
448                                  []>;
449def ucmp       : SDNode<"ISD::UCMP"      , SDTIntBinOp,
450                                  []>;
451
452def saddsat    : SDNode<"ISD::SADDSAT"   , SDTIntBinOp, [SDNPCommutative]>;
453def uaddsat    : SDNode<"ISD::UADDSAT"   , SDTIntBinOp, [SDNPCommutative]>;
454def ssubsat    : SDNode<"ISD::SSUBSAT"   , SDTIntBinOp>;
455def usubsat    : SDNode<"ISD::USUBSAT"   , SDTIntBinOp>;
456def sshlsat    : SDNode<"ISD::SSHLSAT"   , SDTIntBinOp>;
457def ushlsat    : SDNode<"ISD::USHLSAT"   , SDTIntBinOp>;
458
459def smulfix    : SDNode<"ISD::SMULFIX"   , SDTIntScaledBinOp, [SDNPCommutative]>;
460def smulfixsat : SDNode<"ISD::SMULFIXSAT", SDTIntScaledBinOp, [SDNPCommutative]>;
461def umulfix    : SDNode<"ISD::UMULFIX"   , SDTIntScaledBinOp, [SDNPCommutative]>;
462def umulfixsat : SDNode<"ISD::UMULFIXSAT", SDTIntScaledBinOp, [SDNPCommutative]>;
463def sdivfix    : SDNode<"ISD::SDIVFIX"   , SDTIntScaledBinOp>;
464def sdivfixsat : SDNode<"ISD::SDIVFIXSAT", SDTIntScaledBinOp>;
465def udivfix    : SDNode<"ISD::UDIVFIX"   , SDTIntScaledBinOp>;
466def udivfixsat : SDNode<"ISD::UDIVFIXSAT", SDTIntScaledBinOp>;
467
468def sext_inreg : SDNode<"ISD::SIGN_EXTEND_INREG", SDTExtInreg>;
469def sext_invec : SDNode<"ISD::SIGN_EXTEND_VECTOR_INREG", SDTExtInvec>;
470def zext_invec : SDNode<"ISD::ZERO_EXTEND_VECTOR_INREG", SDTExtInvec>;
471
472def abs        : SDNode<"ISD::ABS"        , SDTIntUnaryOp>;
473def bitreverse : SDNode<"ISD::BITREVERSE" , SDTIntUnaryOp>;
474def bswap      : SDNode<"ISD::BSWAP"      , SDTIntUnaryOp>;
475def ctlz       : SDNode<"ISD::CTLZ"       , SDTIntBitCountUnaryOp>;
476def cttz       : SDNode<"ISD::CTTZ"       , SDTIntBitCountUnaryOp>;
477def ctpop      : SDNode<"ISD::CTPOP"      , SDTIntBitCountUnaryOp>;
478def ctlz_zero_undef : SDNode<"ISD::CTLZ_ZERO_UNDEF", SDTIntBitCountUnaryOp>;
479def cttz_zero_undef : SDNode<"ISD::CTTZ_ZERO_UNDEF", SDTIntBitCountUnaryOp>;
480def sext       : SDNode<"ISD::SIGN_EXTEND", SDTIntExtendOp>;
481def zext       : SDNode<"ISD::ZERO_EXTEND", SDTIntExtendOp>;
482def anyext     : SDNode<"ISD::ANY_EXTEND" , SDTIntExtendOp>;
483def trunc      : SDNode<"ISD::TRUNCATE"   , SDTIntTruncOp>;
484def bitconvert : SDNode<"ISD::BITCAST"    , SDTUnaryOp>;
485def addrspacecast : SDNode<"ISD::ADDRSPACECAST", SDTUnaryOp>;
486def freeze     : SDNode<"ISD::FREEZE"     , SDTFreeze>;
487def extractelt : SDNode<"ISD::EXTRACT_VECTOR_ELT", SDTVecExtract>;
488def insertelt  : SDNode<"ISD::INSERT_VECTOR_ELT", SDTVecInsert>;
489
490def vecreduce_add  : SDNode<"ISD::VECREDUCE_ADD", SDTVecReduce>;
491def vecreduce_smax  : SDNode<"ISD::VECREDUCE_SMAX", SDTVecReduce>;
492def vecreduce_umax  : SDNode<"ISD::VECREDUCE_UMAX", SDTVecReduce>;
493def vecreduce_smin  : SDNode<"ISD::VECREDUCE_SMIN", SDTVecReduce>;
494def vecreduce_umin  : SDNode<"ISD::VECREDUCE_UMIN", SDTVecReduce>;
495def vecreduce_fadd  : SDNode<"ISD::VECREDUCE_FADD", SDTFPVecReduce>;
496def vecreduce_fmin  : SDNode<"ISD::VECREDUCE_FMIN", SDTFPVecReduce>;
497def vecreduce_fmax  : SDNode<"ISD::VECREDUCE_FMAX", SDTFPVecReduce>;
498def vecreduce_fminimum : SDNode<"ISD::VECREDUCE_FMINIMUM", SDTFPVecReduce>;
499def vecreduce_fmaximum : SDNode<"ISD::VECREDUCE_FMAXIMUM", SDTFPVecReduce>;
500
501def fadd       : SDNode<"ISD::FADD"       , SDTFPBinOp, [SDNPCommutative]>;
502def fsub       : SDNode<"ISD::FSUB"       , SDTFPBinOp>;
503def fmul       : SDNode<"ISD::FMUL"       , SDTFPBinOp, [SDNPCommutative]>;
504def fdiv       : SDNode<"ISD::FDIV"       , SDTFPBinOp>;
505def frem       : SDNode<"ISD::FREM"       , SDTFPBinOp>;
506def fma        : SDNode<"ISD::FMA"        , SDTFPTernaryOp, [SDNPCommutative]>;
507def fmad       : SDNode<"ISD::FMAD"       , SDTFPTernaryOp, [SDNPCommutative]>;
508def fabs       : SDNode<"ISD::FABS"       , SDTFPUnaryOp>;
509def fminnum    : SDNode<"ISD::FMINNUM"    , SDTFPBinOp,
510                                  [SDNPCommutative, SDNPAssociative]>;
511def fmaxnum    : SDNode<"ISD::FMAXNUM"    , SDTFPBinOp,
512                                  [SDNPCommutative, SDNPAssociative]>;
513def fminnum_ieee : SDNode<"ISD::FMINNUM_IEEE", SDTFPBinOp,
514                          [SDNPCommutative]>;
515def fmaxnum_ieee  : SDNode<"ISD::FMAXNUM_IEEE", SDTFPBinOp,
516                           [SDNPCommutative]>;
517def fminimum   : SDNode<"ISD::FMINIMUM"   , SDTFPBinOp,
518                        [SDNPCommutative, SDNPAssociative]>;
519def fmaximum   : SDNode<"ISD::FMAXIMUM"   , SDTFPBinOp,
520                        [SDNPCommutative, SDNPAssociative]>;
521def fgetsign   : SDNode<"ISD::FGETSIGN"   , SDTFPToIntOp>;
522def fcanonicalize : SDNode<"ISD::FCANONICALIZE", SDTFPUnaryOp>;
523def fneg       : SDNode<"ISD::FNEG"       , SDTFPUnaryOp>;
524def fsqrt      : SDNode<"ISD::FSQRT"      , SDTFPUnaryOp>;
525def fsin       : SDNode<"ISD::FSIN"       , SDTFPUnaryOp>;
526def fcos       : SDNode<"ISD::FCOS"       , SDTFPUnaryOp>;
527def ftan       : SDNode<"ISD::FTAN"       , SDTFPUnaryOp>;
528def fasin      : SDNode<"ISD::FASIN"      , SDTFPUnaryOp>;
529def facos      : SDNode<"ISD::FACOS"      , SDTFPUnaryOp>;
530def fatan      : SDNode<"ISD::FATAN"      , SDTFPUnaryOp>;
531def fsinh      : SDNode<"ISD::FSINH"      , SDTFPUnaryOp>;
532def fcosh      : SDNode<"ISD::FCOSH"      , SDTFPUnaryOp>;
533def ftanh      : SDNode<"ISD::FTANH"      , SDTFPUnaryOp>;
534def fexp2      : SDNode<"ISD::FEXP2"      , SDTFPUnaryOp>;
535def fexp10     : SDNode<"ISD::FEXP10"     , SDTFPUnaryOp>;
536def fpow       : SDNode<"ISD::FPOW"       , SDTFPBinOp>;
537def flog2      : SDNode<"ISD::FLOG2"      , SDTFPUnaryOp>;
538def fldexp     : SDNode<"ISD::FLDEXP"     , SDTFPExpOp>;
539def frint      : SDNode<"ISD::FRINT"      , SDTFPUnaryOp>;
540def ftrunc     : SDNode<"ISD::FTRUNC"     , SDTFPUnaryOp>;
541def fceil      : SDNode<"ISD::FCEIL"      , SDTFPUnaryOp>;
542def ffloor     : SDNode<"ISD::FFLOOR"     , SDTFPUnaryOp>;
543def fnearbyint : SDNode<"ISD::FNEARBYINT" , SDTFPUnaryOp>;
544def fround     : SDNode<"ISD::FROUND"     , SDTFPUnaryOp>;
545def froundeven : SDNode<"ISD::FROUNDEVEN" , SDTFPUnaryOp>;
546
547def lround     : SDNode<"ISD::LROUND"     , SDTFPToIntOp>;
548def llround    : SDNode<"ISD::LLROUND"    , SDTFPToIntOp>;
549def lrint      : SDNode<"ISD::LRINT"      , SDTFPToIntOp>;
550def llrint     : SDNode<"ISD::LLRINT"     , SDTFPToIntOp>;
551
552def fpround    : SDNode<"ISD::FP_ROUND"   , SDTFPRoundOp>;
553def fpextend   : SDNode<"ISD::FP_EXTEND"  , SDTFPExtendOp>;
554def fcopysign  : SDNode<"ISD::FCOPYSIGN"  , SDTFPSignOp>;
555
556def is_fpclass : SDNode<"ISD::IS_FPCLASS" , SDIsFPClassOp>;
557
558def sint_to_fp : SDNode<"ISD::SINT_TO_FP" , SDTIntToFPOp>;
559def uint_to_fp : SDNode<"ISD::UINT_TO_FP" , SDTIntToFPOp>;
560def fp_to_sint : SDNode<"ISD::FP_TO_SINT" , SDTFPToIntOp>;
561def fp_to_uint : SDNode<"ISD::FP_TO_UINT" , SDTFPToIntOp>;
562def fp_to_sint_sat : SDNode<"ISD::FP_TO_SINT_SAT" , SDTFPToIntSatOp>;
563def fp_to_uint_sat : SDNode<"ISD::FP_TO_UINT_SAT" , SDTFPToIntSatOp>;
564def f16_to_fp  : SDNode<"ISD::FP16_TO_FP" , SDTIntToFPOp>;
565def fp_to_f16  : SDNode<"ISD::FP_TO_FP16" , SDTFPToIntOp>;
566def bf16_to_fp  : SDNode<"ISD::BF16_TO_FP" , SDTIntToFPOp>;
567def fp_to_bf16  : SDNode<"ISD::FP_TO_BF16" , SDTFPToIntOp>;
568
569def strict_fadd       : SDNode<"ISD::STRICT_FADD",
570                               SDTFPBinOp, [SDNPHasChain, SDNPCommutative]>;
571def strict_fsub       : SDNode<"ISD::STRICT_FSUB",
572                               SDTFPBinOp, [SDNPHasChain]>;
573def strict_fmul       : SDNode<"ISD::STRICT_FMUL",
574                               SDTFPBinOp, [SDNPHasChain, SDNPCommutative]>;
575def strict_fdiv       : SDNode<"ISD::STRICT_FDIV",
576                               SDTFPBinOp, [SDNPHasChain]>;
577def strict_frem       : SDNode<"ISD::STRICT_FREM",
578                               SDTFPBinOp, [SDNPHasChain]>;
579def strict_fma        : SDNode<"ISD::STRICT_FMA",
580                               SDTFPTernaryOp, [SDNPHasChain, SDNPCommutative]>;
581def strict_fsqrt      : SDNode<"ISD::STRICT_FSQRT",
582                               SDTFPUnaryOp, [SDNPHasChain]>;
583def strict_fsin       : SDNode<"ISD::STRICT_FSIN",
584                               SDTFPUnaryOp, [SDNPHasChain]>;
585def strict_fcos       : SDNode<"ISD::STRICT_FCOS",
586                               SDTFPUnaryOp, [SDNPHasChain]>;
587def strict_ftan       : SDNode<"ISD::STRICT_FTAN",
588                               SDTFPUnaryOp, [SDNPHasChain]>;
589def strict_fasin      : SDNode<"ISD::STRICT_FASIN",
590                               SDTFPUnaryOp, [SDNPHasChain]>;
591def strict_facos      : SDNode<"ISD::STRICT_FACOS",
592                               SDTFPUnaryOp, [SDNPHasChain]>;
593def strict_fatan      : SDNode<"ISD::STRICT_FATAN",
594                               SDTFPUnaryOp, [SDNPHasChain]>;
595def strict_fsinh      : SDNode<"ISD::STRICT_FSINH",
596                               SDTFPUnaryOp, [SDNPHasChain]>;
597def strict_fcosh      : SDNode<"ISD::STRICT_FCOSH",
598                               SDTFPUnaryOp, [SDNPHasChain]>;
599def strict_ftanh      : SDNode<"ISD::STRICT_FTANH",
600                               SDTFPUnaryOp, [SDNPHasChain]>;
601def strict_fexp2      : SDNode<"ISD::STRICT_FEXP2",
602                               SDTFPUnaryOp, [SDNPHasChain]>;
603def strict_fpow       : SDNode<"ISD::STRICT_FPOW",
604                               SDTFPBinOp, [SDNPHasChain]>;
605def strict_fldexp     : SDNode<"ISD::STRICT_FLDEXP",
606                               SDTFPExpOp, [SDNPHasChain]>;
607def strict_flog2      : SDNode<"ISD::STRICT_FLOG2",
608                               SDTFPUnaryOp, [SDNPHasChain]>;
609def strict_frint      : SDNode<"ISD::STRICT_FRINT",
610                               SDTFPUnaryOp, [SDNPHasChain]>;
611def strict_lrint      : SDNode<"ISD::STRICT_LRINT",
612                               SDTFPToIntOp, [SDNPHasChain]>;
613def strict_llrint     : SDNode<"ISD::STRICT_LLRINT",
614                               SDTFPToIntOp, [SDNPHasChain]>;
615def strict_fnearbyint : SDNode<"ISD::STRICT_FNEARBYINT",
616                               SDTFPUnaryOp, [SDNPHasChain]>;
617def strict_fceil      : SDNode<"ISD::STRICT_FCEIL",
618                               SDTFPUnaryOp, [SDNPHasChain]>;
619def strict_ffloor     : SDNode<"ISD::STRICT_FFLOOR",
620                               SDTFPUnaryOp, [SDNPHasChain]>;
621def strict_lround     : SDNode<"ISD::STRICT_LROUND",
622                               SDTFPToIntOp, [SDNPHasChain]>;
623def strict_llround    : SDNode<"ISD::STRICT_LLROUND",
624                               SDTFPToIntOp, [SDNPHasChain]>;
625def strict_fround     : SDNode<"ISD::STRICT_FROUND",
626                               SDTFPUnaryOp, [SDNPHasChain]>;
627def strict_froundeven : SDNode<"ISD::STRICT_FROUNDEVEN",
628                               SDTFPUnaryOp, [SDNPHasChain]>;
629def strict_ftrunc     : SDNode<"ISD::STRICT_FTRUNC",
630                               SDTFPUnaryOp, [SDNPHasChain]>;
631def strict_fminnum    : SDNode<"ISD::STRICT_FMINNUM",
632                               SDTFPBinOp, [SDNPHasChain,
633                                            SDNPCommutative, SDNPAssociative]>;
634def strict_fmaxnum    : SDNode<"ISD::STRICT_FMAXNUM",
635                               SDTFPBinOp, [SDNPHasChain,
636                                            SDNPCommutative, SDNPAssociative]>;
637def strict_fminimum   : SDNode<"ISD::STRICT_FMINIMUM",
638                               SDTFPBinOp, [SDNPHasChain,
639                                            SDNPCommutative, SDNPAssociative]>;
640def strict_fmaximum   : SDNode<"ISD::STRICT_FMAXIMUM",
641                               SDTFPBinOp, [SDNPHasChain,
642                                            SDNPCommutative, SDNPAssociative]>;
643def strict_fpround    : SDNode<"ISD::STRICT_FP_ROUND",
644                               SDTFPRoundOp, [SDNPHasChain]>;
645def strict_fpextend   : SDNode<"ISD::STRICT_FP_EXTEND",
646                               SDTFPExtendOp, [SDNPHasChain]>;
647def strict_fp_to_sint : SDNode<"ISD::STRICT_FP_TO_SINT",
648                               SDTFPToIntOp, [SDNPHasChain]>;
649def strict_fp_to_uint : SDNode<"ISD::STRICT_FP_TO_UINT",
650                               SDTFPToIntOp, [SDNPHasChain]>;
651def strict_sint_to_fp : SDNode<"ISD::STRICT_SINT_TO_FP",
652                               SDTIntToFPOp, [SDNPHasChain]>;
653def strict_uint_to_fp : SDNode<"ISD::STRICT_UINT_TO_FP",
654                               SDTIntToFPOp, [SDNPHasChain]>;
655
656def strict_f16_to_fp  : SDNode<"ISD::STRICT_FP16_TO_FP",
657                               SDTIntToFPOp, [SDNPHasChain]>;
658def strict_fp_to_f16  : SDNode<"ISD::STRICT_FP_TO_FP16",
659                               SDTFPToIntOp, [SDNPHasChain]>;
660
661def strict_bf16_to_fp  : SDNode<"ISD::STRICT_BF16_TO_FP",
662                               SDTIntToFPOp, [SDNPHasChain]>;
663def strict_fp_to_bf16  : SDNode<"ISD::STRICT_FP_TO_BF16",
664                               SDTFPToIntOp, [SDNPHasChain]>;
665
666def strict_fsetcc  : SDNode<"ISD::STRICT_FSETCC",  SDTSetCC, [SDNPHasChain]>;
667def strict_fsetccs : SDNode<"ISD::STRICT_FSETCCS", SDTSetCC, [SDNPHasChain]>;
668
669def get_fpenv      : SDNode<"ISD::GET_FPENV", SDTGetFPStateOp, [SDNPHasChain]>;
670def set_fpenv      : SDNode<"ISD::SET_FPENV", SDTSetFPStateOp, [SDNPHasChain]>;
671def reset_fpenv    : SDNode<"ISD::RESET_FPENV", SDTNone, [SDNPHasChain]>;
672def get_fpmode     : SDNode<"ISD::GET_FPMODE", SDTGetFPStateOp, [SDNPHasChain]>;
673def set_fpmode     : SDNode<"ISD::SET_FPMODE", SDTSetFPStateOp, [SDNPHasChain]>;
674def reset_fpmode   : SDNode<"ISD::RESET_FPMODE", SDTNone, [SDNPHasChain]>;
675
676def setcc      : SDNode<"ISD::SETCC"      , SDTSetCC>;
677def select     : SDNode<"ISD::SELECT"     , SDTSelect>;
678def vselect    : SDNode<"ISD::VSELECT"    , SDTVSelect>;
679def selectcc   : SDNode<"ISD::SELECT_CC"  , SDTSelectCC>;
680
681def brcc       : SDNode<"ISD::BR_CC"      , SDTBrCC,   [SDNPHasChain]>;
682def brcond     : SDNode<"ISD::BRCOND"     , SDTBrcond, [SDNPHasChain]>;
683def brind      : SDNode<"ISD::BRIND"      , SDTBrind,  [SDNPHasChain]>;
684def br         : SDNode<"ISD::BR"         , SDTBr,     [SDNPHasChain]>;
685def catchret   : SDNode<"ISD::CATCHRET"   , SDTCatchret,
686                        [SDNPHasChain, SDNPSideEffect]>;
687def cleanupret : SDNode<"ISD::CLEANUPRET" , SDTCleanupret, [SDNPHasChain]>;
688
689def trap       : SDNode<"ISD::TRAP"       , SDTNone,
690                        [SDNPHasChain, SDNPSideEffect]>;
691def debugtrap  : SDNode<"ISD::DEBUGTRAP"  , SDTNone,
692                        [SDNPHasChain, SDNPSideEffect]>;
693def ubsantrap  : SDNode<"ISD::UBSANTRAP"  , SDTUBSANTrap,
694                        [SDNPHasChain, SDNPSideEffect]>;
695
696def prefetch   : SDNode<"ISD::PREFETCH"   , SDTPrefetch,
697                        [SDNPHasChain, SDNPMayLoad, SDNPMayStore,
698                         SDNPMemOperand]>;
699
700def readcyclecounter : SDNode<"ISD::READCYCLECOUNTER", SDTIntLeaf,
701                     [SDNPHasChain, SDNPSideEffect]>;
702
703def readsteadycounter : SDNode<"ISD::READSTEADYCOUNTER", SDTIntLeaf,
704                     [SDNPHasChain, SDNPSideEffect]>;
705
706def membarrier : SDNode<"ISD::MEMBARRIER", SDTNone,
707                        [SDNPHasChain, SDNPSideEffect]>;
708
709def jump_table_debug_info : SDNode<"ISD::JUMP_TABLE_DEBUG_INFO", SDTNone,
710                        [SDNPHasChain]>;
711
712def atomic_fence : SDNode<"ISD::ATOMIC_FENCE" , SDTAtomicFence,
713                          [SDNPHasChain, SDNPSideEffect]>;
714
715def atomic_cmp_swap : SDNode<"ISD::ATOMIC_CMP_SWAP" , SDTAtomic3,
716                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
717def atomic_load_add : SDNode<"ISD::ATOMIC_LOAD_ADD" , SDTAtomic2,
718                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
719def atomic_swap     : SDNode<"ISD::ATOMIC_SWAP", SDTAtomic2,
720                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
721def atomic_load_sub : SDNode<"ISD::ATOMIC_LOAD_SUB" , SDTAtomic2,
722                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
723def atomic_load_and : SDNode<"ISD::ATOMIC_LOAD_AND" , SDTAtomic2,
724                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
725def atomic_load_clr : SDNode<"ISD::ATOMIC_LOAD_CLR" , SDTAtomic2,
726                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
727def atomic_load_or  : SDNode<"ISD::ATOMIC_LOAD_OR" , SDTAtomic2,
728                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
729def atomic_load_xor : SDNode<"ISD::ATOMIC_LOAD_XOR" , SDTAtomic2,
730                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
731def atomic_load_nand: SDNode<"ISD::ATOMIC_LOAD_NAND", SDTAtomic2,
732                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
733def atomic_load_min : SDNode<"ISD::ATOMIC_LOAD_MIN", SDTAtomic2,
734                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
735def atomic_load_max : SDNode<"ISD::ATOMIC_LOAD_MAX", SDTAtomic2,
736                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
737def atomic_load_umin : SDNode<"ISD::ATOMIC_LOAD_UMIN", SDTAtomic2,
738                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
739def atomic_load_umax : SDNode<"ISD::ATOMIC_LOAD_UMAX", SDTAtomic2,
740                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
741def atomic_load_fadd : SDNode<"ISD::ATOMIC_LOAD_FADD" , SDTFPAtomic2,
742                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
743def atomic_load_fsub : SDNode<"ISD::ATOMIC_LOAD_FSUB" , SDTFPAtomic2,
744                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
745def atomic_load_fmax : SDNode<"ISD::ATOMIC_LOAD_FMAX", SDTFPAtomic2,
746                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
747def atomic_load_fmin : SDNode<"ISD::ATOMIC_LOAD_FMIN", SDTFPAtomic2,
748                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
749def atomic_load_uinc_wrap : SDNode<"ISD::ATOMIC_LOAD_UINC_WRAP", SDTAtomic2,
750                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
751def atomic_load_udec_wrap : SDNode<"ISD::ATOMIC_LOAD_UDEC_WRAP", SDTAtomic2,
752                    [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
753
754def atomic_load      : SDNode<"ISD::ATOMIC_LOAD", SDTAtomicLoad,
755                    [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
756def atomic_store     : SDNode<"ISD::ATOMIC_STORE", SDTAtomicStore,
757                    [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
758
759def masked_st    : SDNode<"ISD::MSTORE",  SDTMaskedStore,
760                       [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
761def masked_ld    : SDNode<"ISD::MLOAD",  SDTMaskedLoad,
762                       [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
763
764def masked_gather : SDNode<"ISD::MGATHER", SDTMaskedGather,
765                           [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
766
767def masked_scatter : SDNode<"ISD::MSCATTER", SDTMaskedScatter,
768                            [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
769
770def vector_compress : SDNode<"ISD::VECTOR_COMPRESS", SDTVectorCompress>;
771
772// Do not use ld, st directly. Use load, extload, sextload, zextload, store,
773// and truncst (see below).
774def ld         : SDNode<"ISD::LOAD"       , SDTLoad,
775                        [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
776def st         : SDNode<"ISD::STORE"      , SDTStore,
777                        [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
778def ist        : SDNode<"ISD::STORE"      , SDTIStore,
779                        [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;
780
781def vector_shuffle : SDNode<"ISD::VECTOR_SHUFFLE", SDTVecShuffle, []>;
782def vector_reverse : SDNode<"ISD::VECTOR_REVERSE", SDTVecReverse>;
783def vector_splice : SDNode<"ISD::VECTOR_SPLICE", SDTVecSlice, []>;
784def build_vector : SDNode<"ISD::BUILD_VECTOR", SDTypeProfile<1, -1, []>, []>;
785def splat_vector : SDNode<"ISD::SPLAT_VECTOR", SDTypeProfile<1, 1, []>, []>;
786def step_vector : SDNode<"ISD::STEP_VECTOR", SDTypeProfile<1, 1,
787                       [SDTCisVec<0>, SDTCisInt<1>]>, []>;
788def scalar_to_vector : SDNode<"ISD::SCALAR_TO_VECTOR", SDTypeProfile<1, 1, []>,
789                              []>;
790
791// vector_extract/vector_insert are deprecated. extractelt/insertelt
792// are preferred.
793def vector_extract : SDNode<"ISD::EXTRACT_VECTOR_ELT",
794    SDTypeProfile<1, 2, [SDTCisPtrTy<2>]>, []>;
795def vector_insert : SDNode<"ISD::INSERT_VECTOR_ELT",
796    SDTypeProfile<1, 3, [SDTCisSameAs<0, 1>, SDTCisPtrTy<3>]>, []>;
797def concat_vectors : SDNode<"ISD::CONCAT_VECTORS",
798    SDTypeProfile<1, 2, [SDTCisSubVecOfVec<1, 0>, SDTCisSameAs<1, 2>]>,[]>;
799
800// This operator does not do subvector type checking.  The ARM
801// backend, at least, needs it.
802def vector_extract_subvec : SDNode<"ISD::EXTRACT_SUBVECTOR",
803    SDTypeProfile<1, 2, [SDTCisInt<2>, SDTCisVec<1>, SDTCisVec<0>]>,
804    []>;
805def vector_insert_subvec : SDNode<"ISD::INSERT_SUBVECTOR",
806    SDTypeProfile<1, 3, [SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisVec<2>, SDTCisInt<3>]>,
807    []>;
808
809// This operator does subvector type checking.
810def extract_subvector : SDNode<"ISD::EXTRACT_SUBVECTOR", SDTSubVecExtract, []>;
811def insert_subvector : SDNode<"ISD::INSERT_SUBVECTOR", SDTSubVecInsert, []>;
812
813// Nodes for intrinsics, you should use the intrinsic itself and let tblgen use
814// these internally.  Don't reference these directly.
815def intrinsic_void : SDNode<"ISD::INTRINSIC_VOID",
816                            SDTypeProfile<0, -1, [SDTCisPtrTy<0>]>,
817                            [SDNPHasChain]>;
818def intrinsic_w_chain : SDNode<"ISD::INTRINSIC_W_CHAIN",
819                               SDTypeProfile<1, -1, [SDTCisPtrTy<1>]>,
820                               [SDNPHasChain]>;
821def intrinsic_wo_chain : SDNode<"ISD::INTRINSIC_WO_CHAIN",
822                                SDTypeProfile<1, -1, [SDTCisPtrTy<1>]>, []>;
823
824def SDT_assert : SDTypeProfile<1, 1,
825  [SDTCisInt<0>, SDTCisInt<1>, SDTCisSameAs<1, 0>]>;
826def assertsext : SDNode<"ISD::AssertSext", SDT_assert>;
827def assertzext : SDNode<"ISD::AssertZext", SDT_assert>;
828def assertalign : SDNode<"ISD::AssertAlign", SDT_assert>;
829
830def convergencectrl_anchor : SDNode<"ISD::CONVERGENCECTRL_ANCHOR",
831                                    SDTypeProfile<1, 0, [SDTCisVT<0,untyped>]>>;
832def convergencectrl_entry  : SDNode<"ISD::CONVERGENCECTRL_ENTRY",
833                                    SDTypeProfile<1, 0, [SDTCisVT<0,untyped>]>>;
834def convergencectrl_loop   : SDNode<"ISD::CONVERGENCECTRL_LOOP",
835                                    SDTypeProfile<1, 1,
836                                      [SDTCisVT<0,untyped>, SDTCisVT<1,untyped>]>>;
837def convergencectrl_glue   : SDNode<"ISD::CONVERGENCECTRL_GLUE",
838                                    SDTypeProfile<0, 1, [SDTCisVT<0, untyped>]>>;
839
840//===----------------------------------------------------------------------===//
841// Selection DAG Condition Codes
842
843class CondCode<string fcmpName = "", string icmpName = ""> {
844  string ICmpPredicate = icmpName;
845  string FCmpPredicate = fcmpName;
846}
847
848// ISD::CondCode enums, and mapping to CmpInst::Predicate names
849def SETOEQ : CondCode<"FCMP_OEQ">;
850def SETOGT : CondCode<"FCMP_OGT">;
851def SETOGE : CondCode<"FCMP_OGE">;
852def SETOLT : CondCode<"FCMP_OLT">;
853def SETOLE : CondCode<"FCMP_OLE">;
854def SETONE : CondCode<"FCMP_ONE">;
855def SETO   : CondCode<"FCMP_ORD">;
856def SETUO  : CondCode<"FCMP_UNO">;
857def SETUEQ : CondCode<"FCMP_UEQ">;
858def SETUGT : CondCode<"FCMP_UGT", "ICMP_UGT">;
859def SETUGE : CondCode<"FCMP_UGE", "ICMP_UGE">;
860def SETULT : CondCode<"FCMP_ULT", "ICMP_ULT">;
861def SETULE : CondCode<"FCMP_ULE", "ICMP_ULE">;
862def SETUNE : CondCode<"FCMP_UNE">;
863def SETEQ : CondCode<"", "ICMP_EQ">;
864def SETGT : CondCode<"", "ICMP_SGT">;
865def SETGE : CondCode<"", "ICMP_SGE">;
866def SETLT : CondCode<"", "ICMP_SLT">;
867def SETLE : CondCode<"", "ICMP_SLE">;
868def SETNE : CondCode<"", "ICMP_NE">;
869
870//===----------------------------------------------------------------------===//
871// Selection DAG Node Transformation Functions.
872//
873// This mechanism allows targets to manipulate nodes in the output DAG once a
874// match has been formed.  This is typically used to manipulate immediate
875// values.
876//
877class SDNodeXForm<SDNode opc, code xformFunction> {
878  SDNode Opcode = opc;
879  code XFormFunction = xformFunction;
880}
881
882def NOOP_SDNodeXForm : SDNodeXForm<imm, [{}]>;
883
884//===----------------------------------------------------------------------===//
885// Selection DAG Pattern Fragments.
886//
887// Pattern fragments are reusable chunks of dags that match specific things.
888// They can take arguments and have C++ predicates that control whether they
889// match.  They are intended to make the patterns for common instructions more
890// compact and readable.
891//
892
893/// PatFrags - Represents a set of pattern fragments.  Each single fragment
894/// can match something on the DAG, from a single node to multiple nested other
895/// fragments.   The whole set of fragments matches if any of the single
896/// fragments match.  This allows e.g. matching and "add with overflow" and
897/// a regular "add" with the same fragment set.
898///
899class PatFrags<dag ops, list<dag> frags, code pred = [{}],
900               SDNodeXForm xform = NOOP_SDNodeXForm> : SDPatternOperator {
901  dag Operands = ops;
902  list<dag> Fragments = frags;
903  code PredicateCode = pred;
904  code GISelPredicateCode = [{}];
905  code ImmediateCode = [{}];
906  SDNodeXForm OperandTransform = xform;
907
908  // When this is set, the PredicateCode may refer to a constant Operands
909  // vector which contains the captured nodes of the DAG, in the order listed
910  // by the Operands field above.
911  //
912  // This is useful when Fragments involves associative / commutative
913  // operators: a single piece of code can easily refer to all operands even
914  // when re-associated / commuted variants of the fragment are matched.
915  bit PredicateCodeUsesOperands = false;
916
917  // Define a few pre-packaged predicates. This helps GlobalISel import
918  // existing rules from SelectionDAG for many common cases.
919  // They will be tested prior to the code in pred and must not be used in
920  // ImmLeaf and its subclasses.
921
922  // If set to true, a predicate is added that checks for the absence of use of
923  // the first result.
924  bit HasNoUse = ?;
925  // If set to true, a predicate is added that checks for the sole use of
926  // the first result.
927  bit HasOneUse = ?;
928
929  // Is the desired pre-packaged predicate for a load?
930  bit IsLoad = ?;
931  // Is the desired pre-packaged predicate for a store?
932  bit IsStore = ?;
933  // Is the desired pre-packaged predicate for an atomic?
934  bit IsAtomic = ?;
935
936  // cast<LoadSDNode>(N)->getAddressingMode() == ISD::UNINDEXED;
937  // cast<StoreSDNode>(N)->getAddressingMode() == ISD::UNINDEXED;
938  bit IsUnindexed = ?;
939
940  // cast<LoadSDNode>(N)->getExtensionType() != ISD::NON_EXTLOAD
941  bit IsNonExtLoad = ?;
942  // cast<LoadSDNode>(N)->getExtensionType() == ISD::EXTLOAD;
943  bit IsAnyExtLoad = ?;
944  // cast<LoadSDNode>(N)->getExtensionType() == ISD::SEXTLOAD;
945  bit IsSignExtLoad = ?;
946  // cast<LoadSDNode>(N)->getExtensionType() == ISD::ZEXTLOAD;
947  bit IsZeroExtLoad = ?;
948  // !cast<StoreSDNode>(N)->isTruncatingStore();
949  // cast<StoreSDNode>(N)->isTruncatingStore();
950  bit IsTruncStore = ?;
951
952  // cast<MemSDNode>(N)->getAddressSpace() ==
953  // If this empty, accept any address space.
954  list<int> AddressSpaces = ?;
955
956  // cast<MemSDNode>(N)->getAlign() >=
957  // If this is empty, accept any alignment.
958  int MinAlignment = ?;
959
960  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::Monotonic
961  bit IsAtomicOrderingMonotonic = ?;
962  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::Acquire
963  bit IsAtomicOrderingAcquire = ?;
964  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::Release
965  bit IsAtomicOrderingRelease = ?;
966  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::AcquireRelease
967  bit IsAtomicOrderingAcquireRelease = ?;
968  // cast<AtomicSDNode>(N)->getOrdering() == AtomicOrdering::SequentiallyConsistent
969  bit IsAtomicOrderingSequentiallyConsistent = ?;
970
971  // isAcquireOrStronger(cast<AtomicSDNode>(N)->getOrdering())
972  // !isAcquireOrStronger(cast<AtomicSDNode>(N)->getOrdering())
973  bit IsAtomicOrderingAcquireOrStronger = ?;
974
975  // isReleaseOrStronger(cast<AtomicSDNode>(N)->getOrdering())
976  // !isReleaseOrStronger(cast<AtomicSDNode>(N)->getOrdering())
977  bit IsAtomicOrderingReleaseOrStronger = ?;
978
979  // cast<LoadSDNode>(N)->getMemoryVT() == MVT::<VT>;
980  // cast<StoreSDNode>(N)->getMemoryVT() == MVT::<VT>;
981  ValueType MemoryVT = ?;
982  // cast<LoadSDNode>(N)->getMemoryVT().getScalarType() == MVT::<VT>;
983  // cast<StoreSDNode>(N)->getMemoryVT().getScalarType() == MVT::<VT>;
984  ValueType ScalarMemoryVT = ?;
985}
986
987// Patterns and PatFrags can also subclass GISelFlags to set flags that affect
988// how GlobalISel behaves when matching them.
989class GISelFlags {
990  bit GIIgnoreCopies = ?;
991}
992
993// PatFrag - A version of PatFrags matching only a single fragment.
994class PatFrag<dag ops, dag frag, code pred = [{}],
995              SDNodeXForm xform = NOOP_SDNodeXForm>
996  : PatFrags<ops, [frag], pred, xform>;
997
998// OutPatFrag is a pattern fragment that is used as part of an output pattern
999// (not an input pattern). These do not have predicates or transforms, but are
1000// used to avoid repeated subexpressions in output patterns.
1001class OutPatFrag<dag ops, dag frag>
1002 : PatFrag<ops, frag, [{}], NOOP_SDNodeXForm>;
1003
1004// PatLeaf's are pattern fragments that have no operands.  This is just a helper
1005// to define immediates and other common things concisely.
1006class PatLeaf<dag frag, code pred = [{}], SDNodeXForm xform = NOOP_SDNodeXForm>
1007 : PatFrag<(ops), frag, pred, xform>;
1008
1009
1010// ImmLeaf is a pattern fragment with a constraint on the immediate.  The
1011// constraint is a function that is run on the immediate (always with the value
1012// sign extended out to an int64_t) as Imm.  For example:
1013//
1014//  def immSExt8 : ImmLeaf<i16, [{ return (char)Imm == Imm; }]>;
1015//
1016// this is a more convenient form to match 'imm' nodes in than PatLeaf and also
1017// is preferred over using PatLeaf because it allows the code generator to
1018// reason more about the constraint.
1019//
1020// If FastIsel should ignore all instructions that have an operand of this type,
1021// the FastIselShouldIgnore flag can be set.  This is an optimization to reduce
1022// the code size of the generated fast instruction selector.
1023class ImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm,
1024              SDNode ImmNode = imm>
1025  : PatFrag<(ops), (vt ImmNode), [{}], xform> {
1026  let ImmediateCode = pred;
1027  bit FastIselShouldIgnore = false;
1028
1029  // Is the data type of the immediate an APInt?
1030  bit IsAPInt = false;
1031
1032  // Is the data type of the immediate an APFloat?
1033  bit IsAPFloat = false;
1034}
1035
1036// Convenience wrapper for ImmLeaf to use timm/TargetConstant instead
1037// of imm/Constant.
1038class TImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm,
1039  SDNode ImmNode = timm> : ImmLeaf<vt, pred, xform, ImmNode>;
1040
1041// An ImmLeaf except that Imm is an APInt. This is useful when you need to
1042// zero-extend the immediate instead of sign-extend it.
1043//
1044// Note that FastISel does not currently understand IntImmLeaf and will not
1045// generate code for rules that make use of it. As such, it does not make sense
1046// to replace ImmLeaf with IntImmLeaf. However, replacing PatLeaf with an
1047// IntImmLeaf will allow GlobalISel to import the rule.
1048class IntImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm>
1049    : ImmLeaf<vt, pred, xform> {
1050  let IsAPInt = true;
1051  let FastIselShouldIgnore = true;
1052}
1053
1054// An ImmLeaf except that Imm is an APFloat.
1055//
1056// Note that FastISel does not currently understand FPImmLeaf and will not
1057// generate code for rules that make use of it.
1058class FPImmLeaf<ValueType vt, code pred, SDNodeXForm xform = NOOP_SDNodeXForm>
1059  : ImmLeaf<vt, pred, xform, fpimm> {
1060  let IsAPFloat = true;
1061  let FastIselShouldIgnore = true;
1062}
1063
1064// Leaf fragments.
1065
1066def vtInt      : PatLeaf<(vt),  [{ return N->getVT().isInteger(); }]>;
1067def vtFP       : PatLeaf<(vt),  [{ return N->getVT().isFloatingPoint(); }]>;
1068
1069// Use ISD::isConstantSplatVectorAllOnes or ISD::isConstantSplatVectorAllZeros
1070// to look for the corresponding build_vector or splat_vector. Will look through
1071// bitcasts and check for either opcode, except when used as a pattern root.
1072// When used as a pattern root, only fixed-length build_vector and scalable
1073// splat_vector are supported.
1074def immAllOnesV  : SDPatternOperator; // ISD::isConstantSplatVectorAllOnes
1075def immAllZerosV : SDPatternOperator; // ISD::isConstantSplatVectorAllZeros
1076
1077// Other helper fragments.
1078def not  : PatFrag<(ops node:$in), (xor node:$in, -1)>;
1079def vnot : PatFrag<(ops node:$in), (xor node:$in, immAllOnesV)>;
1080def ineg : PatFrag<(ops node:$in), (sub 0, node:$in)>;
1081
1082def zanyext : PatFrags<(ops node:$op),
1083                       [(zext node:$op),
1084                        (anyext node:$op)]>;
1085
1086// null_frag - The null pattern operator is used in multiclass instantiations
1087// which accept an SDPatternOperator for use in matching patterns for internal
1088// definitions. When expanding a pattern, if the null fragment is referenced
1089// in the expansion, the pattern is discarded and it is as-if '[]' had been
1090// specified. This allows multiclasses to have the isel patterns be optional.
1091def null_frag : SDPatternOperator;
1092
1093// load fragments.
1094def unindexedload : PatFrag<(ops node:$ptr), (ld node:$ptr)> {
1095  let IsLoad = true;
1096  let IsUnindexed = true;
1097}
1098def load : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1099  let IsLoad = true;
1100  let IsNonExtLoad = true;
1101}
1102
1103// extending load fragments.
1104def extload   : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1105  let IsLoad = true;
1106  let IsAnyExtLoad = true;
1107}
1108def sextload  : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1109  let IsLoad = true;
1110  let IsSignExtLoad = true;
1111}
1112def zextload  : PatFrag<(ops node:$ptr), (unindexedload node:$ptr)> {
1113  let IsLoad = true;
1114  let IsZeroExtLoad = true;
1115}
1116
1117def extloadi1  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1118  let IsLoad = true;
1119  let MemoryVT = i1;
1120}
1121def extloadi8  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1122  let IsLoad = true;
1123  let MemoryVT = i8;
1124}
1125def extloadi16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1126  let IsLoad = true;
1127  let MemoryVT = i16;
1128}
1129def extloadi32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1130  let IsLoad = true;
1131  let MemoryVT = i32;
1132}
1133def extloadi64 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1134  let IsLoad = true;
1135  let MemoryVT = i64;
1136}
1137def extloadf16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1138  let IsLoad = true;
1139  let MemoryVT = f16;
1140}
1141def extloadf32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1142  let IsLoad = true;
1143  let MemoryVT = f32;
1144}
1145def extloadf64 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1146  let IsLoad = true;
1147  let MemoryVT = f64;
1148}
1149
1150def sextloadi1  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1151  let IsLoad = true;
1152  let MemoryVT = i1;
1153}
1154def sextloadi8  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1155  let IsLoad = true;
1156  let MemoryVT = i8;
1157}
1158def sextloadi16 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1159  let IsLoad = true;
1160  let MemoryVT = i16;
1161}
1162def sextloadi32 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1163  let IsLoad = true;
1164  let MemoryVT = i32;
1165}
1166def sextloadi64 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1167  let IsLoad = true;
1168  let MemoryVT = i64;
1169}
1170
1171def zextloadi1  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1172  let IsLoad = true;
1173  let MemoryVT = i1;
1174}
1175def zextloadi8  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1176  let IsLoad = true;
1177  let MemoryVT = i8;
1178}
1179def zextloadi16 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1180  let IsLoad = true;
1181  let MemoryVT = i16;
1182}
1183def zextloadi32 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1184  let IsLoad = true;
1185  let MemoryVT = i32;
1186}
1187def zextloadi64 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1188  let IsLoad = true;
1189  let MemoryVT = i64;
1190}
1191
1192def extloadvi1  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1193  let IsLoad = true;
1194  let ScalarMemoryVT = i1;
1195}
1196def extloadvi8  : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1197  let IsLoad = true;
1198  let ScalarMemoryVT = i8;
1199}
1200def extloadvi16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1201  let IsLoad = true;
1202  let ScalarMemoryVT = i16;
1203}
1204def extloadvi32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1205  let IsLoad = true;
1206  let ScalarMemoryVT = i32;
1207}
1208def extloadvf16 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1209  let IsLoad = true;
1210  let ScalarMemoryVT = f16;
1211}
1212def extloadvf32 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1213  let IsLoad = true;
1214  let ScalarMemoryVT = f32;
1215}
1216def extloadvf64 : PatFrag<(ops node:$ptr), (extload node:$ptr)> {
1217  let IsLoad = true;
1218  let ScalarMemoryVT = f64;
1219}
1220
1221def sextloadvi1  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1222  let IsLoad = true;
1223  let ScalarMemoryVT = i1;
1224}
1225def sextloadvi8  : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1226  let IsLoad = true;
1227  let ScalarMemoryVT = i8;
1228}
1229def sextloadvi16 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1230  let IsLoad = true;
1231  let ScalarMemoryVT = i16;
1232}
1233def sextloadvi32 : PatFrag<(ops node:$ptr), (sextload node:$ptr)> {
1234  let IsLoad = true;
1235  let ScalarMemoryVT = i32;
1236}
1237
1238def zextloadvi1  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1239  let IsLoad = true;
1240  let ScalarMemoryVT = i1;
1241}
1242def zextloadvi8  : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1243  let IsLoad = true;
1244  let ScalarMemoryVT = i8;
1245}
1246def zextloadvi16 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1247  let IsLoad = true;
1248  let ScalarMemoryVT = i16;
1249}
1250def zextloadvi32 : PatFrag<(ops node:$ptr), (zextload node:$ptr)> {
1251  let IsLoad = true;
1252  let ScalarMemoryVT = i32;
1253}
1254
1255// store fragments.
1256def unindexedstore : PatFrag<(ops node:$val, node:$ptr),
1257                             (st node:$val, node:$ptr)> {
1258  let IsStore = true;
1259  let IsUnindexed = true;
1260}
1261def store : PatFrag<(ops node:$val, node:$ptr),
1262                    (unindexedstore node:$val, node:$ptr)> {
1263  let IsStore = true;
1264  let IsTruncStore = false;
1265}
1266
1267// truncstore fragments.
1268def truncstore : PatFrag<(ops node:$val, node:$ptr),
1269                         (unindexedstore node:$val, node:$ptr)> {
1270  let IsStore = true;
1271  let IsTruncStore = true;
1272}
1273def truncstorei8 : PatFrag<(ops node:$val, node:$ptr),
1274                           (truncstore node:$val, node:$ptr)> {
1275  let IsStore = true;
1276  let MemoryVT = i8;
1277  let IsTruncStore = true;
1278}
1279def truncstorei16 : PatFrag<(ops node:$val, node:$ptr),
1280                            (truncstore node:$val, node:$ptr)> {
1281  let IsStore = true;
1282  let MemoryVT = i16;
1283  let IsTruncStore = true;
1284}
1285def truncstorei32 : PatFrag<(ops node:$val, node:$ptr),
1286                            (truncstore node:$val, node:$ptr)> {
1287  let IsStore = true;
1288  let MemoryVT = i32;
1289  let IsTruncStore = true;
1290}
1291def truncstorei64 : PatFrag<(ops node:$val, node:$ptr),
1292                            (truncstore node:$val, node:$ptr)> {
1293  let IsStore = true;
1294  let MemoryVT = i64;
1295  let IsTruncStore = true;
1296}
1297def truncstoref16 : PatFrag<(ops node:$val, node:$ptr),
1298                            (truncstore node:$val, node:$ptr)> {
1299  let IsStore = true;
1300  let MemoryVT = f16;
1301}
1302def truncstoref32 : PatFrag<(ops node:$val, node:$ptr),
1303                            (truncstore node:$val, node:$ptr)> {
1304  let IsStore = true;
1305  let MemoryVT = f32;
1306}
1307def truncstoref64 : PatFrag<(ops node:$val, node:$ptr),
1308                            (truncstore node:$val, node:$ptr)> {
1309  let IsStore = true;
1310  let MemoryVT = f64;
1311}
1312
1313def truncstorevi8 : PatFrag<(ops node:$val, node:$ptr),
1314                            (truncstore node:$val, node:$ptr)> {
1315  let IsStore = true;
1316  let ScalarMemoryVT = i8;
1317}
1318
1319def truncstorevi16 : PatFrag<(ops node:$val, node:$ptr),
1320                             (truncstore node:$val, node:$ptr)> {
1321  let IsStore = true;
1322  let ScalarMemoryVT = i16;
1323}
1324
1325def truncstorevi32 : PatFrag<(ops node:$val, node:$ptr),
1326                             (truncstore node:$val, node:$ptr)> {
1327  let IsStore = true;
1328  let ScalarMemoryVT = i32;
1329}
1330
1331// indexed store fragments.
1332def istore : PatFrag<(ops node:$val, node:$base, node:$offset),
1333                     (ist node:$val, node:$base, node:$offset)> {
1334  let IsStore = true;
1335  let IsTruncStore = false;
1336}
1337
1338def pre_store : PatFrag<(ops node:$val, node:$base, node:$offset),
1339                        (istore node:$val, node:$base, node:$offset), [{
1340  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
1341  return AM == ISD::PRE_INC || AM == ISD::PRE_DEC;
1342}]>;
1343
1344def itruncstore : PatFrag<(ops node:$val, node:$base, node:$offset),
1345                          (ist node:$val, node:$base, node:$offset)> {
1346  let IsStore = true;
1347  let IsTruncStore = true;
1348}
1349def pre_truncst : PatFrag<(ops node:$val, node:$base, node:$offset),
1350                          (itruncstore node:$val, node:$base, node:$offset), [{
1351  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
1352  return AM == ISD::PRE_INC || AM == ISD::PRE_DEC;
1353}]>;
1354def pre_truncsti1 : PatFrag<(ops node:$val, node:$base, node:$offset),
1355                            (pre_truncst node:$val, node:$base, node:$offset)> {
1356  let IsStore = true;
1357  let MemoryVT = i1;
1358}
1359def pre_truncsti8 : PatFrag<(ops node:$val, node:$base, node:$offset),
1360                            (pre_truncst node:$val, node:$base, node:$offset)> {
1361  let IsStore = true;
1362  let MemoryVT = i8;
1363}
1364def pre_truncsti16 : PatFrag<(ops node:$val, node:$base, node:$offset),
1365                             (pre_truncst node:$val, node:$base, node:$offset)> {
1366  let IsStore = true;
1367  let MemoryVT = i16;
1368}
1369def pre_truncsti32 : PatFrag<(ops node:$val, node:$base, node:$offset),
1370                             (pre_truncst node:$val, node:$base, node:$offset)> {
1371  let IsStore = true;
1372  let MemoryVT = i32;
1373}
1374def pre_truncstf32 : PatFrag<(ops node:$val, node:$base, node:$offset),
1375                             (pre_truncst node:$val, node:$base, node:$offset)> {
1376  let IsStore = true;
1377  let MemoryVT = f32;
1378}
1379def pre_truncstvi8 : PatFrag<(ops node:$val, node:$base, node:$offset),
1380                             (pre_truncst node:$val, node:$base, node:$offset)> {
1381  let IsStore = true;
1382  let ScalarMemoryVT = i8;
1383}
1384def pre_truncstvi16 : PatFrag<(ops node:$val, node:$base, node:$offset),
1385                              (pre_truncst node:$val, node:$base, node:$offset)> {
1386  let IsStore = true;
1387  let ScalarMemoryVT = i16;
1388}
1389
1390def post_store : PatFrag<(ops node:$val, node:$ptr, node:$offset),
1391                         (istore node:$val, node:$ptr, node:$offset), [{
1392  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
1393  return AM == ISD::POST_INC || AM == ISD::POST_DEC;
1394}]>;
1395
1396def post_truncst : PatFrag<(ops node:$val, node:$base, node:$offset),
1397                           (itruncstore node:$val, node:$base, node:$offset), [{
1398  ISD::MemIndexedMode AM = cast<StoreSDNode>(N)->getAddressingMode();
1399  return AM == ISD::POST_INC || AM == ISD::POST_DEC;
1400}]>;
1401def post_truncsti1 : PatFrag<(ops node:$val, node:$base, node:$offset),
1402                             (post_truncst node:$val, node:$base, node:$offset)> {
1403  let IsStore = true;
1404  let MemoryVT = i1;
1405}
1406def post_truncsti8 : PatFrag<(ops node:$val, node:$base, node:$offset),
1407                             (post_truncst node:$val, node:$base, node:$offset)> {
1408  let IsStore = true;
1409  let MemoryVT = i8;
1410}
1411def post_truncsti16 : PatFrag<(ops node:$val, node:$base, node:$offset),
1412                              (post_truncst node:$val, node:$base, node:$offset)> {
1413  let IsStore = true;
1414  let MemoryVT = i16;
1415}
1416def post_truncsti32 : PatFrag<(ops node:$val, node:$base, node:$offset),
1417                              (post_truncst node:$val, node:$base, node:$offset)> {
1418  let IsStore = true;
1419  let MemoryVT = i32;
1420}
1421def post_truncstf32 : PatFrag<(ops node:$val, node:$base, node:$offset),
1422                              (post_truncst node:$val, node:$base, node:$offset)> {
1423  let IsStore = true;
1424  let MemoryVT = f32;
1425}
1426def post_truncstvi8 : PatFrag<(ops node:$val, node:$base, node:$offset),
1427                              (post_truncst node:$val, node:$base, node:$offset)> {
1428  let IsStore = true;
1429  let ScalarMemoryVT = i8;
1430}
1431def post_truncstvi16 : PatFrag<(ops node:$val, node:$base, node:$offset),
1432                               (post_truncst node:$val, node:$base, node:$offset)> {
1433  let IsStore = true;
1434  let ScalarMemoryVT = i16;
1435}
1436
1437// A helper for matching undef or freeze undef
1438def undef_or_freeze_undef : PatFrags<(ops), [(undef), (freeze undef)]>;
1439
1440// TODO: Split these into volatile and unordered flavors to enable
1441// selectively legal optimizations for each.  (See D66309)
1442def simple_load : PatFrag<(ops node:$ptr),
1443                          (load node:$ptr), [{
1444  return cast<LoadSDNode>(N)->isSimple();
1445}]>;
1446def simple_store : PatFrag<(ops node:$val, node:$ptr),
1447                           (store node:$val, node:$ptr), [{
1448  return cast<StoreSDNode>(N)->isSimple();
1449}]>;
1450
1451// nontemporal store fragments.
1452def nontemporalstore : PatFrag<(ops node:$val, node:$ptr),
1453                               (store node:$val, node:$ptr), [{
1454  return cast<StoreSDNode>(N)->isNonTemporal();
1455}]>;
1456
1457def alignednontemporalstore : PatFrag<(ops node:$val, node:$ptr),
1458                                      (nontemporalstore node:$val, node:$ptr), [{
1459  StoreSDNode *St = cast<StoreSDNode>(N);
1460  return St->getAlign() >= St->getMemoryVT().getStoreSize();
1461}]>;
1462
1463def unalignednontemporalstore : PatFrag<(ops node:$val, node:$ptr),
1464                                        (nontemporalstore node:$val, node:$ptr), [{
1465  StoreSDNode *St = cast<StoreSDNode>(N);
1466  return St->getAlignment() < St->getMemoryVT().getStoreSize();
1467}]>;
1468
1469// nontemporal load fragments.
1470def nontemporalload : PatFrag<(ops node:$ptr),
1471                               (load node:$ptr), [{
1472  return cast<LoadSDNode>(N)->isNonTemporal();
1473}]>;
1474
1475def alignednontemporalload : PatFrag<(ops node:$ptr),
1476                                      (nontemporalload node:$ptr), [{
1477  LoadSDNode *Ld = cast<LoadSDNode>(N);
1478  return Ld->getAlign() >= Ld->getMemoryVT().getStoreSize();
1479}]>;
1480
1481// setcc convenience fragments.
1482def setoeq : PatFrag<(ops node:$lhs, node:$rhs),
1483                     (setcc node:$lhs, node:$rhs, SETOEQ)>;
1484def setogt : PatFrag<(ops node:$lhs, node:$rhs),
1485                     (setcc node:$lhs, node:$rhs, SETOGT)>;
1486def setoge : PatFrag<(ops node:$lhs, node:$rhs),
1487                     (setcc node:$lhs, node:$rhs, SETOGE)>;
1488def setolt : PatFrag<(ops node:$lhs, node:$rhs),
1489                     (setcc node:$lhs, node:$rhs, SETOLT)>;
1490def setole : PatFrag<(ops node:$lhs, node:$rhs),
1491                     (setcc node:$lhs, node:$rhs, SETOLE)>;
1492def setone : PatFrag<(ops node:$lhs, node:$rhs),
1493                     (setcc node:$lhs, node:$rhs, SETONE)>;
1494def seto   : PatFrag<(ops node:$lhs, node:$rhs),
1495                     (setcc node:$lhs, node:$rhs, SETO)>;
1496def setuo  : PatFrag<(ops node:$lhs, node:$rhs),
1497                     (setcc node:$lhs, node:$rhs, SETUO)>;
1498def setueq : PatFrag<(ops node:$lhs, node:$rhs),
1499                     (setcc node:$lhs, node:$rhs, SETUEQ)>;
1500def setugt : PatFrag<(ops node:$lhs, node:$rhs),
1501                     (setcc node:$lhs, node:$rhs, SETUGT)>;
1502def setuge : PatFrag<(ops node:$lhs, node:$rhs),
1503                     (setcc node:$lhs, node:$rhs, SETUGE)>;
1504def setult : PatFrag<(ops node:$lhs, node:$rhs),
1505                     (setcc node:$lhs, node:$rhs, SETULT)>;
1506def setule : PatFrag<(ops node:$lhs, node:$rhs),
1507                     (setcc node:$lhs, node:$rhs, SETULE)>;
1508def setune : PatFrag<(ops node:$lhs, node:$rhs),
1509                     (setcc node:$lhs, node:$rhs, SETUNE)>;
1510def seteq  : PatFrag<(ops node:$lhs, node:$rhs),
1511                     (setcc node:$lhs, node:$rhs, SETEQ)>;
1512def setgt  : PatFrag<(ops node:$lhs, node:$rhs),
1513                     (setcc node:$lhs, node:$rhs, SETGT)>;
1514def setge  : PatFrag<(ops node:$lhs, node:$rhs),
1515                     (setcc node:$lhs, node:$rhs, SETGE)>;
1516def setlt  : PatFrag<(ops node:$lhs, node:$rhs),
1517                     (setcc node:$lhs, node:$rhs, SETLT)>;
1518def setle  : PatFrag<(ops node:$lhs, node:$rhs),
1519                     (setcc node:$lhs, node:$rhs, SETLE)>;
1520def setne  : PatFrag<(ops node:$lhs, node:$rhs),
1521                     (setcc node:$lhs, node:$rhs, SETNE)>;
1522
1523// We don't have strict FP extended loads as single DAG nodes, but we can
1524// still provide convenience fragments to match those operations.
1525def strict_extloadf32 : PatFrag<(ops node:$ptr),
1526                                (strict_fpextend (f32 (load node:$ptr)))>;
1527def strict_extloadf64 : PatFrag<(ops node:$ptr),
1528                                (strict_fpextend (f64 (load node:$ptr)))>;
1529
1530// Convenience fragments to match both strict and non-strict fp operations
1531def any_fadd       : PatFrags<(ops node:$lhs, node:$rhs),
1532                              [(strict_fadd node:$lhs, node:$rhs),
1533                               (fadd node:$lhs, node:$rhs)]>;
1534def any_fsub       : PatFrags<(ops node:$lhs, node:$rhs),
1535                              [(strict_fsub node:$lhs, node:$rhs),
1536                               (fsub node:$lhs, node:$rhs)]>;
1537def any_fmul       : PatFrags<(ops node:$lhs, node:$rhs),
1538                              [(strict_fmul node:$lhs, node:$rhs),
1539                               (fmul node:$lhs, node:$rhs)]>;
1540def any_fdiv       : PatFrags<(ops node:$lhs, node:$rhs),
1541                              [(strict_fdiv node:$lhs, node:$rhs),
1542                               (fdiv node:$lhs, node:$rhs)]>;
1543def any_frem       : PatFrags<(ops node:$lhs, node:$rhs),
1544                              [(strict_frem node:$lhs, node:$rhs),
1545                               (frem node:$lhs, node:$rhs)]>;
1546def any_fma        : PatFrags<(ops node:$src1, node:$src2, node:$src3),
1547                              [(strict_fma node:$src1, node:$src2, node:$src3),
1548                               (fma node:$src1, node:$src2, node:$src3)]>;
1549def any_fsqrt      : PatFrags<(ops node:$src),
1550                              [(strict_fsqrt node:$src),
1551                               (fsqrt node:$src)]>;
1552def any_fsin       : PatFrags<(ops node:$src),
1553                              [(strict_fsin node:$src),
1554                               (fsin node:$src)]>;
1555def any_fcos       : PatFrags<(ops node:$src),
1556                              [(strict_fcos node:$src),
1557                               (fcos node:$src)]>;
1558def any_ftan       : PatFrags<(ops node:$src),
1559                              [(strict_ftan node:$src),
1560                               (ftan node:$src)]>;
1561def any_fasin      : PatFrags<(ops node:$src),
1562                              [(strict_fasin node:$src),
1563                               (fasin node:$src)]>;
1564def any_facos      : PatFrags<(ops node:$src),
1565                              [(strict_facos node:$src),
1566                               (facos node:$src)]>;
1567def any_fatan      : PatFrags<(ops node:$src),
1568                              [(strict_fatan node:$src),
1569                               (fatan node:$src)]>;
1570def any_fsinh      : PatFrags<(ops node:$src),
1571                              [(strict_fsinh node:$src),
1572                               (fsinh node:$src)]>;
1573def any_fcosh      : PatFrags<(ops node:$src),
1574                              [(strict_fcosh node:$src),
1575                               (fcosh node:$src)]>;
1576def any_ftanh      : PatFrags<(ops node:$src),
1577                              [(strict_ftanh node:$src),
1578                               (ftanh node:$src)]>;
1579def any_fexp2      : PatFrags<(ops node:$src),
1580                              [(strict_fexp2 node:$src),
1581                               (fexp2 node:$src)]>;
1582def any_fpow       : PatFrags<(ops node:$lhs, node:$rhs),
1583                              [(strict_fpow node:$lhs, node:$rhs),
1584                               (fpow node:$lhs, node:$rhs)]>;
1585def any_fldexp      : PatFrags<(ops node:$lhs, node:$rhs),
1586                              [(strict_fldexp node:$lhs, node:$rhs),
1587                               (fldexp node:$lhs, node:$rhs)]>;
1588def any_flog2      : PatFrags<(ops node:$src),
1589                              [(strict_flog2 node:$src),
1590                               (flog2 node:$src)]>;
1591def any_frint      : PatFrags<(ops node:$src),
1592                              [(strict_frint node:$src),
1593                               (frint node:$src)]>;
1594def any_lrint      : PatFrags<(ops node:$src),
1595                              [(strict_lrint node:$src),
1596                               (lrint node:$src)]>;
1597def any_llrint     : PatFrags<(ops node:$src),
1598                              [(strict_llrint node:$src),
1599                               (llrint node:$src)]>;
1600def any_fnearbyint : PatFrags<(ops node:$src),
1601                              [(strict_fnearbyint node:$src),
1602                               (fnearbyint node:$src)]>;
1603def any_fceil      : PatFrags<(ops node:$src),
1604                              [(strict_fceil node:$src),
1605                               (fceil node:$src)]>;
1606def any_ffloor     : PatFrags<(ops node:$src),
1607                              [(strict_ffloor node:$src),
1608                               (ffloor node:$src)]>;
1609def any_lround     : PatFrags<(ops node:$src),
1610                              [(strict_lround node:$src),
1611                               (lround node:$src)]>;
1612def any_llround    : PatFrags<(ops node:$src),
1613                              [(strict_llround node:$src),
1614                               (llround node:$src)]>;
1615def any_fround     : PatFrags<(ops node:$src),
1616                              [(strict_fround node:$src),
1617                               (fround node:$src)]>;
1618def any_froundeven : PatFrags<(ops node:$src),
1619                              [(strict_froundeven node:$src),
1620                               (froundeven node:$src)]>;
1621def any_ftrunc     : PatFrags<(ops node:$src),
1622                              [(strict_ftrunc node:$src),
1623                               (ftrunc node:$src)]>;
1624def any_fmaxnum    : PatFrags<(ops node:$lhs, node:$rhs),
1625                              [(strict_fmaxnum node:$lhs, node:$rhs),
1626                               (fmaxnum node:$lhs, node:$rhs)]>;
1627def any_fminnum    : PatFrags<(ops node:$lhs, node:$rhs),
1628                              [(strict_fminnum node:$lhs, node:$rhs),
1629                               (fminnum node:$lhs, node:$rhs)]>;
1630def any_fmaximum   : PatFrags<(ops node:$lhs, node:$rhs),
1631                              [(strict_fmaximum node:$lhs, node:$rhs),
1632                               (fmaximum node:$lhs, node:$rhs)]>;
1633def any_fminimum   : PatFrags<(ops node:$lhs, node:$rhs),
1634                              [(strict_fminimum node:$lhs, node:$rhs),
1635                               (fminimum node:$lhs, node:$rhs)]>;
1636def any_fpround    : PatFrags<(ops node:$src),
1637                              [(strict_fpround node:$src),
1638                               (fpround node:$src)]>;
1639def any_fpextend   : PatFrags<(ops node:$src),
1640                              [(strict_fpextend node:$src),
1641                               (fpextend node:$src)]>;
1642def any_extloadf32 : PatFrags<(ops node:$ptr),
1643                              [(strict_extloadf32 node:$ptr),
1644                               (extloadf32 node:$ptr)]>;
1645def any_extloadf64 : PatFrags<(ops node:$ptr),
1646                              [(strict_extloadf64 node:$ptr),
1647                               (extloadf64 node:$ptr)]>;
1648def any_fp_to_sint : PatFrags<(ops node:$src),
1649                              [(strict_fp_to_sint node:$src),
1650                               (fp_to_sint node:$src)]>;
1651def any_fp_to_uint : PatFrags<(ops node:$src),
1652                              [(strict_fp_to_uint node:$src),
1653                               (fp_to_uint node:$src)]>;
1654def any_sint_to_fp : PatFrags<(ops node:$src),
1655                              [(strict_sint_to_fp node:$src),
1656                               (sint_to_fp node:$src)]>;
1657def any_uint_to_fp : PatFrags<(ops node:$src),
1658                              [(strict_uint_to_fp node:$src),
1659                               (uint_to_fp node:$src)]>;
1660def any_fsetcc : PatFrags<(ops node:$lhs, node:$rhs, node:$pred),
1661                          [(strict_fsetcc node:$lhs, node:$rhs, node:$pred),
1662                           (setcc node:$lhs, node:$rhs, node:$pred)]>;
1663def any_fsetccs : PatFrags<(ops node:$lhs, node:$rhs, node:$pred),
1664                          [(strict_fsetccs node:$lhs, node:$rhs, node:$pred),
1665                           (setcc node:$lhs, node:$rhs, node:$pred)]>;
1666
1667def any_f16_to_fp : PatFrags<(ops node:$src),
1668                              [(f16_to_fp node:$src),
1669                               (strict_f16_to_fp node:$src)]>;
1670def any_fp_to_f16 : PatFrags<(ops node:$src),
1671                              [(fp_to_f16 node:$src),
1672                               (strict_fp_to_f16 node:$src)]>;
1673def any_bf16_to_fp : PatFrags<(ops node:$src),
1674                               [(bf16_to_fp node:$src),
1675                                (strict_bf16_to_fp node:$src)]>;
1676def any_fp_to_bf16 : PatFrags<(ops node:$src),
1677                               [(fp_to_bf16 node:$src),
1678                                (strict_fp_to_bf16 node:$src)]>;
1679
1680multiclass binary_atomic_op_ord {
1681  def NAME#_monotonic : PatFrag<(ops node:$ptr, node:$val),
1682      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1683    let IsAtomic = true;
1684    let IsAtomicOrderingMonotonic = true;
1685  }
1686  def NAME#_acquire : PatFrag<(ops node:$ptr, node:$val),
1687      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1688    let IsAtomic = true;
1689    let IsAtomicOrderingAcquire = true;
1690  }
1691  def NAME#_release : PatFrag<(ops node:$ptr, node:$val),
1692      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1693    let IsAtomic = true;
1694    let IsAtomicOrderingRelease = true;
1695  }
1696  def NAME#_acq_rel : PatFrag<(ops node:$ptr, node:$val),
1697      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1698    let IsAtomic = true;
1699    let IsAtomicOrderingAcquireRelease = true;
1700  }
1701  def NAME#_seq_cst : PatFrag<(ops node:$ptr, node:$val),
1702      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$val)> {
1703    let IsAtomic = true;
1704    let IsAtomicOrderingSequentiallyConsistent = true;
1705  }
1706}
1707
1708multiclass ternary_atomic_op_ord {
1709  def NAME#_monotonic : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
1710      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1711    let IsAtomic = true;
1712    let IsAtomicOrderingMonotonic = true;
1713  }
1714  def NAME#_acquire : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
1715      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1716    let IsAtomic = true;
1717    let IsAtomicOrderingAcquire = true;
1718  }
1719  def NAME#_release : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
1720      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1721    let IsAtomic = true;
1722    let IsAtomicOrderingRelease = true;
1723  }
1724  def NAME#_acq_rel : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
1725      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1726    let IsAtomic = true;
1727    let IsAtomicOrderingAcquireRelease = true;
1728  }
1729  def NAME#_seq_cst : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
1730      (!cast<SDPatternOperator>(NAME) node:$ptr, node:$cmp, node:$val)> {
1731    let IsAtomic = true;
1732    let IsAtomicOrderingSequentiallyConsistent = true;
1733  }
1734}
1735
1736multiclass binary_atomic_op<SDNode atomic_op> {
1737  foreach vt = [ i8, i16, i32, i64 ] in {
1738    def _#vt : PatFrag<(ops node:$ptr, node:$val),
1739                       (atomic_op  node:$ptr, node:$val)> {
1740      let IsAtomic = true;
1741      let MemoryVT = vt;
1742    }
1743
1744    defm NAME#_#vt  : binary_atomic_op_ord;
1745  }
1746}
1747
1748multiclass binary_atomic_op_fp<SDNode atomic_op> {
1749  foreach vt = [ f16, bf16, v2f16, v2bf16, f32, f64 ] in {
1750    def _#vt : PatFrag<(ops node:$ptr, node:$val),
1751                       (atomic_op node:$ptr, node:$val)> {
1752      let IsAtomic = true;
1753      let MemoryVT = vt;
1754    }
1755  }
1756}
1757
1758multiclass ternary_atomic_op<SDNode atomic_op> {
1759  foreach vt = [ i8, i16, i32, i64 ] in {
1760    def _#vt : PatFrag<(ops node:$ptr, node:$cmp, node:$val),
1761                       (atomic_op node:$ptr, node:$cmp, node:$val)> {
1762      let IsAtomic = true;
1763      let MemoryVT = vt;
1764    }
1765
1766    defm NAME#_#vt  : ternary_atomic_op_ord;
1767  }
1768}
1769
1770defm atomic_load_add  : binary_atomic_op<atomic_load_add>;
1771defm atomic_swap      : binary_atomic_op<atomic_swap>;
1772defm atomic_load_sub  : binary_atomic_op<atomic_load_sub>;
1773defm atomic_load_and  : binary_atomic_op<atomic_load_and>;
1774defm atomic_load_clr  : binary_atomic_op<atomic_load_clr>;
1775defm atomic_load_or   : binary_atomic_op<atomic_load_or>;
1776defm atomic_load_xor  : binary_atomic_op<atomic_load_xor>;
1777defm atomic_load_nand : binary_atomic_op<atomic_load_nand>;
1778defm atomic_load_min  : binary_atomic_op<atomic_load_min>;
1779defm atomic_load_max  : binary_atomic_op<atomic_load_max>;
1780defm atomic_load_umin : binary_atomic_op<atomic_load_umin>;
1781defm atomic_load_umax : binary_atomic_op<atomic_load_umax>;
1782defm atomic_cmp_swap  : ternary_atomic_op<atomic_cmp_swap>;
1783
1784/// Atomic load which zeroes the excess high bits.
1785def atomic_load_zext :
1786  PatFrag<(ops node:$ptr), (atomic_load node:$ptr)> {
1787  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1788  let IsZeroExtLoad = true;
1789}
1790
1791/// Atomic load which sign extends the excess high bits.
1792def atomic_load_sext :
1793  PatFrag<(ops node:$ptr), (atomic_load node:$ptr)> {
1794  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1795  let IsSignExtLoad = true;
1796}
1797
1798def atomic_load_8 :
1799  PatFrag<(ops node:$ptr),
1800          (atomic_load node:$ptr)> {
1801  let IsAtomic = true;
1802  let MemoryVT = i8;
1803}
1804
1805def atomic_load_16 :
1806  PatFrag<(ops node:$ptr),
1807          (atomic_load node:$ptr)> {
1808  let IsAtomic = true;
1809  let MemoryVT = i16;
1810}
1811
1812def atomic_load_32 :
1813  PatFrag<(ops node:$ptr),
1814          (atomic_load node:$ptr)> {
1815  let IsAtomic = true;
1816  let MemoryVT = i32;
1817}
1818def atomic_load_64 :
1819  PatFrag<(ops node:$ptr),
1820          (atomic_load node:$ptr)> {
1821  let IsAtomic = true;
1822  let MemoryVT = i64;
1823}
1824
1825def atomic_load_zext_8 :
1826  PatFrag<(ops node:$ptr), (atomic_load_zext node:$ptr)> {
1827  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1828  let MemoryVT = i8;
1829}
1830
1831def atomic_load_zext_16 :
1832  PatFrag<(ops node:$ptr), (atomic_load_zext node:$ptr)> {
1833  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1834  let MemoryVT = i16;
1835}
1836
1837def atomic_load_sext_8 :
1838  PatFrag<(ops node:$ptr), (atomic_load_sext node:$ptr)> {
1839  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1840  let MemoryVT = i8;
1841}
1842
1843def atomic_load_sext_16 :
1844  PatFrag<(ops node:$ptr), (atomic_load_sext node:$ptr)> {
1845  let IsAtomic = true; // FIXME: Should be IsLoad and/or IsAtomic?
1846  let MemoryVT = i16;
1847}
1848
1849// Atomic load which zeroes or anyextends the high bits.
1850def atomic_load_az_8 : PatFrags<(ops node:$op),
1851                                [(atomic_load_8 node:$op),
1852                                 (atomic_load_zext_8 node:$op)]>;
1853
1854// Atomic load which zeroes or anyextends the high bits.
1855def atomic_load_az_16 : PatFrags<(ops node:$op),
1856                                 [(atomic_load_16 node:$op),
1857                                  (atomic_load_zext_16 node:$op)]>;
1858
1859def nonext_masked_gather :
1860  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1861          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1862  return cast<MaskedGatherSDNode>(N)->getExtensionType() == ISD::NON_EXTLOAD;
1863}]>;
1864
1865// Any extending masked gather fragments.
1866def ext_masked_gather_i8 :
1867  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1868          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1869  auto MGN = cast<MaskedGatherSDNode>(N);
1870  return MGN->getExtensionType() == ISD::EXTLOAD &&
1871         MGN->getMemoryVT().getScalarType() == MVT::i8;
1872}]>;
1873def ext_masked_gather_i16 :
1874  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1875          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1876  auto MGN = cast<MaskedGatherSDNode>(N);
1877  return MGN->getExtensionType() == ISD::EXTLOAD &&
1878         MGN->getMemoryVT().getScalarType() == MVT::i16;
1879}]>;
1880def ext_masked_gather_i32 :
1881  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1882          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1883  auto MGN = cast<MaskedGatherSDNode>(N);
1884  return MGN->getExtensionType() == ISD::EXTLOAD &&
1885         MGN->getMemoryVT().getScalarType() == MVT::i32;
1886}]>;
1887
1888// Sign extending masked gather fragments.
1889def sext_masked_gather_i8 :
1890  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1891          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1892  auto MGN = cast<MaskedGatherSDNode>(N);
1893  return MGN->getExtensionType() == ISD::SEXTLOAD &&
1894         MGN->getMemoryVT().getScalarType() == MVT::i8;
1895}]>;
1896def sext_masked_gather_i16 :
1897  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1898          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1899  auto MGN = cast<MaskedGatherSDNode>(N);
1900  return MGN->getExtensionType() == ISD::SEXTLOAD &&
1901         MGN->getMemoryVT().getScalarType() == MVT::i16;
1902}]>;
1903def sext_masked_gather_i32 :
1904  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1905          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1906  auto MGN = cast<MaskedGatherSDNode>(N);
1907  return MGN->getExtensionType() == ISD::SEXTLOAD &&
1908         MGN->getMemoryVT().getScalarType() == MVT::i32;
1909}]>;
1910
1911// Zero extending masked gather fragments.
1912def zext_masked_gather_i8 :
1913  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1914          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1915  auto MGN = cast<MaskedGatherSDNode>(N);
1916  return MGN->getExtensionType() == ISD::ZEXTLOAD &&
1917         MGN->getMemoryVT().getScalarType() == MVT::i8;
1918}]>;
1919def zext_masked_gather_i16 :
1920  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1921          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1922  auto MGN = cast<MaskedGatherSDNode>(N);
1923  return MGN->getExtensionType() == ISD::ZEXTLOAD &&
1924         MGN->getMemoryVT().getScalarType() == MVT::i16;
1925}]>;
1926def zext_masked_gather_i32 :
1927  PatFrag<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1928          (masked_gather node:$def, node:$pred, node:$ptr, node:$idx), [{
1929  auto MGN = cast<MaskedGatherSDNode>(N);
1930  return MGN->getExtensionType() == ISD::ZEXTLOAD &&
1931         MGN->getMemoryVT().getScalarType() == MVT::i32;
1932}]>;
1933
1934// Any/Zero extending masked gather fragments.
1935def azext_masked_gather_i8 :
1936  PatFrags<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1937           [(ext_masked_gather_i8 node:$def, node:$pred, node:$ptr, node:$idx),
1938            (zext_masked_gather_i8 node:$def, node:$pred, node:$ptr, node:$idx)]>;
1939def azext_masked_gather_i16 :
1940  PatFrags<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1941           [(ext_masked_gather_i16 node:$def, node:$pred, node:$ptr, node:$idx),
1942            (zext_masked_gather_i16 node:$def, node:$pred, node:$ptr, node:$idx)]>;
1943def azext_masked_gather_i32 :
1944  PatFrags<(ops node:$def, node:$pred, node:$ptr, node:$idx),
1945           [(ext_masked_gather_i32 node:$def, node:$pred, node:$ptr, node:$idx),
1946            (zext_masked_gather_i32 node:$def, node:$pred, node:$ptr, node:$idx)]>;
1947
1948def nontrunc_masked_scatter :
1949  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
1950          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
1951  return !cast<MaskedScatterSDNode>(N)->isTruncatingStore();
1952}]>;
1953
1954// Truncating masked scatter fragments.
1955def trunc_masked_scatter_i8 :
1956  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
1957          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
1958  auto MSN = cast<MaskedScatterSDNode>(N);
1959  return MSN->isTruncatingStore() &&
1960         MSN->getMemoryVT().getScalarType() == MVT::i8;
1961}]>;
1962def trunc_masked_scatter_i16 :
1963  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
1964          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
1965  auto MSN = cast<MaskedScatterSDNode>(N);
1966  return MSN->isTruncatingStore() &&
1967         MSN->getMemoryVT().getScalarType() == MVT::i16;
1968}]>;
1969def trunc_masked_scatter_i32 :
1970  PatFrag<(ops node:$val, node:$pred, node:$ptr, node:$idx),
1971          (masked_scatter node:$val, node:$pred, node:$ptr, node:$idx), [{
1972  auto MSN = cast<MaskedScatterSDNode>(N);
1973  return MSN->isTruncatingStore() &&
1974         MSN->getMemoryVT().getScalarType() == MVT::i32;
1975}]>;
1976
1977
1978def atomic_store_8 :
1979  PatFrag<(ops node:$val, node:$ptr),
1980          (atomic_store node:$val, node:$ptr)> {
1981  let IsAtomic = true;
1982  let MemoryVT = i8;
1983}
1984
1985def atomic_store_16 :
1986  PatFrag<(ops node:$val, node:$ptr),
1987          (atomic_store node:$val, node:$ptr)> {
1988  let IsAtomic = true;
1989  let MemoryVT = i16;
1990}
1991
1992def atomic_store_32 :
1993  PatFrag<(ops node:$val, node:$ptr),
1994          (atomic_store node:$val, node:$ptr)> {
1995  let IsAtomic = true;
1996  let MemoryVT = i32;
1997}
1998
1999def atomic_store_64 :
2000  PatFrag<(ops node:$val, node:$ptr),
2001          (atomic_store node:$val, node:$ptr)> {
2002  let IsAtomic = true;
2003  let MemoryVT = i64;
2004}
2005
2006//===----------------------------------------------------------------------===//
2007// Selection DAG Pattern Support.
2008//
2009// Patterns are what are actually matched against by the target-flavored
2010// instruction selection DAG.  Instructions defined by the target implicitly
2011// define patterns in most cases, but patterns can also be explicitly added when
2012// an operation is defined by a sequence of instructions (e.g. loading a large
2013// immediate value on RISC targets that do not support immediates as large as
2014// their GPRs).
2015//
2016
2017class Pattern<dag patternToMatch, list<dag> resultInstrs> {
2018  dag             PatternToMatch  = patternToMatch;
2019  list<dag>       ResultInstrs    = resultInstrs;
2020  list<Predicate> Predicates      = [];  // See class Instruction in Target.td.
2021  int             AddedComplexity = 0;   // See class Instruction in Target.td.
2022  bit           GISelShouldIgnore = 0;
2023}
2024
2025// Pat - A simple (but common) form of a pattern, which produces a simple result
2026// not needing a full list.
2027class Pat<dag pattern, dag result> : Pattern<pattern, [result]>;
2028
2029//===----------------------------------------------------------------------===//
2030// Complex pattern definitions.
2031//
2032
2033// Complex patterns, e.g. X86 addressing mode, requires pattern matching code
2034// in C++. Ty is the type of return value; NumOperands is the number of operands
2035// returned by the select function; SelectFunc is the name of the function used
2036// to pattern match the max. pattern; RootNodes are the list of possible root nodes
2037// of the sub-dags to match.
2038// e.g. X86 addressing mode - def addr : ComplexPattern<iPTR, 4, "SelectAddr", [add]>;
2039//
2040class ComplexPattern<ValueType ty, int numops, string fn,
2041                     list<SDNode> roots = [], list<SDNodeProperty> props = [],
2042                     int complexity = -1> {
2043  ValueType Ty = ty;
2044  int NumOperands = numops;
2045  string SelectFunc = fn;
2046  list<SDNode> RootNodes = roots;
2047  list<SDNodeProperty> Properties = props;
2048  int Complexity = complexity;
2049}
2050