1//===-- PPCInstrInfo.td - The PowerPC Instruction Set ------*- 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 describes the subset of the 32-bit PowerPC instruction set, as used
10// by the PowerPC instruction selector.
11//
12//===----------------------------------------------------------------------===//
13
14include "PPCInstrFormats.td"
15
16//===----------------------------------------------------------------------===//
17// PowerPC specific type constraints.
18//
19def SDT_PPCstfiwx : SDTypeProfile<0, 2, [ // stfiwx
20  SDTCisVT<0, f64>, SDTCisPtrTy<1>
21]>;
22def SDT_PPClfiwx : SDTypeProfile<1, 1, [ // lfiw[az]x
23  SDTCisVT<0, f64>, SDTCisPtrTy<1>
24]>;
25def SDT_PPCLxsizx : SDTypeProfile<1, 2, [
26  SDTCisVT<0, f64>, SDTCisPtrTy<1>, SDTCisPtrTy<2>
27]>;
28def SDT_PPCstxsix : SDTypeProfile<0, 3, [
29  SDTCisVT<0, f64>, SDTCisPtrTy<1>, SDTCisPtrTy<2>
30]>;
31def SDT_PPCcv_fp_to_int  : SDTypeProfile<1, 1, [
32  SDTCisFP<0>, SDTCisFP<1>
33  ]>;
34def SDT_PPCstore_scal_int_from_vsr : SDTypeProfile<0, 3, [
35  SDTCisVT<0, f64>, SDTCisPtrTy<1>, SDTCisPtrTy<2>
36]>;
37def SDT_PPCVexts  : SDTypeProfile<1, 2, [
38  SDTCisVT<0, f64>, SDTCisVT<1, f64>, SDTCisPtrTy<2>
39]>;
40
41def SDT_PPCCallSeqStart : SDCallSeqStart<[ SDTCisVT<0, i32>,
42                                           SDTCisVT<1, i32> ]>;
43def SDT_PPCCallSeqEnd   : SDCallSeqEnd<[ SDTCisVT<0, i32>,
44                                         SDTCisVT<1, i32> ]>;
45def SDT_PPCvperm   : SDTypeProfile<1, 3, [
46  SDTCisVT<3, v16i8>, SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>
47]>;
48
49def SDT_PPCVecSplat : SDTypeProfile<1, 2, [ SDTCisVec<0>,
50  SDTCisVec<1>, SDTCisInt<2>
51]>;
52
53def SDT_PPCSpToDp : SDTypeProfile<1, 1, [ SDTCisVT<0, v2f64>,
54  SDTCisInt<1>
55]>;
56
57def SDT_PPCVecShift : SDTypeProfile<1, 3, [ SDTCisVec<0>,
58  SDTCisVec<1>, SDTCisVec<2>, SDTCisPtrTy<3>
59]>;
60
61def SDT_PPCVecInsert : SDTypeProfile<1, 3, [ SDTCisVec<0>,
62  SDTCisVec<1>, SDTCisVec<2>, SDTCisInt<3>
63]>;
64
65def SDT_PPCxxpermdi: SDTypeProfile<1, 3, [ SDTCisVec<0>,
66  SDTCisVec<1>, SDTCisVec<2>, SDTCisInt<3>
67]>;
68
69def SDT_PPCvcmp : SDTypeProfile<1, 3, [
70  SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>, SDTCisVT<3, i32>
71]>;
72
73def SDT_PPCcondbr : SDTypeProfile<0, 3, [
74  SDTCisVT<0, i32>, SDTCisVT<2, OtherVT>
75]>;
76
77def SDT_PPCFtsqrt : SDTypeProfile<1, 1, [
78  SDTCisVT<0, i32>]>;
79
80def SDT_PPClbrx : SDTypeProfile<1, 2, [
81  SDTCisInt<0>, SDTCisPtrTy<1>, SDTCisVT<2, OtherVT>
82]>;
83def SDT_PPCstbrx : SDTypeProfile<0, 3, [
84  SDTCisInt<0>, SDTCisPtrTy<1>, SDTCisVT<2, OtherVT>
85]>;
86
87def SDT_PPCTC_ret : SDTypeProfile<0, 2, [
88  SDTCisPtrTy<0>, SDTCisVT<1, i32>
89]>;
90
91def tocentry32 : Operand<iPTR> {
92  let MIOperandInfo = (ops i32imm:$imm);
93}
94
95def SDT_PPCqvfperm   : SDTypeProfile<1, 3, [
96  SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisVec<3>
97]>;
98def SDT_PPCqvgpci   : SDTypeProfile<1, 1, [
99  SDTCisVec<0>, SDTCisInt<1>
100]>;
101def SDT_PPCqvaligni   : SDTypeProfile<1, 3, [
102  SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<3>
103]>;
104def SDT_PPCqvesplati   : SDTypeProfile<1, 2, [
105  SDTCisVec<0>, SDTCisSameAs<0, 1>, SDTCisInt<2>
106]>;
107
108def SDT_PPCqbflt : SDTypeProfile<1, 1, [
109  SDTCisVec<0>, SDTCisVec<1>
110]>;
111
112def SDT_PPCqvlfsb : SDTypeProfile<1, 1, [
113  SDTCisVec<0>, SDTCisPtrTy<1>
114]>;
115
116def SDT_PPCextswsli : SDTypeProfile<1, 2, [  // extswsli
117  SDTCisInt<0>, SDTCisInt<1>, SDTCisOpSmallerThanOp<1, 0>, SDTCisInt<2>
118]>;
119
120def SDT_PPCFPMinMax : SDTypeProfile<1, 2, [
121  SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisFP<0>
122]>;
123
124//===----------------------------------------------------------------------===//
125// PowerPC specific DAG Nodes.
126//
127
128def PPCfre    : SDNode<"PPCISD::FRE",     SDTFPUnaryOp, []>;
129def PPCfrsqrte: SDNode<"PPCISD::FRSQRTE", SDTFPUnaryOp, []>;
130def PPCfsqrt  : SDNode<"PPCISD::FSQRT",   SDTFPUnaryOp, []>;
131def PPCftsqrt : SDNode<"PPCISD::FTSQRT",  SDT_PPCFtsqrt,[]>;
132
133def PPCfcfid  : SDNode<"PPCISD::FCFID",   SDTFPUnaryOp, []>;
134def PPCfcfidu : SDNode<"PPCISD::FCFIDU",  SDTFPUnaryOp, []>;
135def PPCfcfids : SDNode<"PPCISD::FCFIDS",  SDTFPRoundOp, []>;
136def PPCfcfidus: SDNode<"PPCISD::FCFIDUS", SDTFPRoundOp, []>;
137def PPCfctidz : SDNode<"PPCISD::FCTIDZ", SDTFPUnaryOp, []>;
138def PPCfctiwz : SDNode<"PPCISD::FCTIWZ", SDTFPUnaryOp, []>;
139def PPCfctiduz: SDNode<"PPCISD::FCTIDUZ",SDTFPUnaryOp, []>;
140def PPCfctiwuz: SDNode<"PPCISD::FCTIWUZ",SDTFPUnaryOp, []>;
141
142def PPCstrict_fcfid : SDNode<"PPCISD::STRICT_FCFID",
143                             SDTFPUnaryOp, [SDNPHasChain]>;
144def PPCstrict_fcfidu : SDNode<"PPCISD::STRICT_FCFIDU",
145                              SDTFPUnaryOp, [SDNPHasChain]>;
146def PPCstrict_fcfids : SDNode<"PPCISD::STRICT_FCFIDS",
147                             SDTFPRoundOp, [SDNPHasChain]>;
148def PPCstrict_fcfidus : SDNode<"PPCISD::STRICT_FCFIDUS",
149                              SDTFPRoundOp, [SDNPHasChain]>;
150
151def PPCany_fcfid : PatFrags<(ops node:$op),
152                             [(PPCfcfid node:$op),
153                              (PPCstrict_fcfid node:$op)]>;
154def PPCany_fcfidu : PatFrags<(ops node:$op),
155                             [(PPCfcfidu node:$op),
156                              (PPCstrict_fcfidu node:$op)]>;
157def PPCany_fcfids : PatFrags<(ops node:$op),
158                              [(PPCfcfids node:$op),
159                               (PPCstrict_fcfids node:$op)]>;
160def PPCany_fcfidus : PatFrags<(ops node:$op),
161                              [(PPCfcfidus node:$op),
162                               (PPCstrict_fcfidus node:$op)]>;
163
164def PPCcv_fp_to_uint_in_vsr:
165    SDNode<"PPCISD::FP_TO_UINT_IN_VSR", SDT_PPCcv_fp_to_int, []>;
166def PPCcv_fp_to_sint_in_vsr:
167    SDNode<"PPCISD::FP_TO_SINT_IN_VSR", SDT_PPCcv_fp_to_int, []>;
168def PPCstore_scal_int_from_vsr:
169   SDNode<"PPCISD::ST_VSR_SCAL_INT", SDT_PPCstore_scal_int_from_vsr,
170           [SDNPHasChain, SDNPMayStore]>;
171def PPCstfiwx : SDNode<"PPCISD::STFIWX", SDT_PPCstfiwx,
172                       [SDNPHasChain, SDNPMayStore]>;
173def PPClfiwax : SDNode<"PPCISD::LFIWAX", SDT_PPClfiwx,
174                       [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
175def PPClfiwzx : SDNode<"PPCISD::LFIWZX", SDT_PPClfiwx,
176                       [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
177def PPClxsizx : SDNode<"PPCISD::LXSIZX", SDT_PPCLxsizx,
178                       [SDNPHasChain, SDNPMayLoad]>;
179def PPCstxsix : SDNode<"PPCISD::STXSIX", SDT_PPCstxsix,
180                       [SDNPHasChain, SDNPMayStore]>;
181def PPCVexts  : SDNode<"PPCISD::VEXTS", SDT_PPCVexts, []>;
182
183// Extract FPSCR (not modeled at the DAG level).
184def PPCmffs   : SDNode<"PPCISD::MFFS",
185                       SDTypeProfile<1, 0, [SDTCisVT<0, f64>]>,
186                       [SDNPHasChain]>;
187
188// Perform FADD in round-to-zero mode.
189def PPCfaddrtz: SDNode<"PPCISD::FADDRTZ", SDTFPBinOp, []>;
190def PPCstrict_faddrtz: SDNode<"PPCISD::STRICT_FADDRTZ", SDTFPBinOp,
191                              [SDNPHasChain]>;
192
193def PPCany_faddrtz: PatFrags<(ops node:$lhs, node:$rhs),
194                             [(PPCfaddrtz node:$lhs, node:$rhs),
195                              (PPCstrict_faddrtz node:$lhs, node:$rhs)]>;
196
197def PPCfsel   : SDNode<"PPCISD::FSEL",
198   // Type constraint for fsel.
199   SDTypeProfile<1, 3, [SDTCisSameAs<0, 2>, SDTCisSameAs<0, 3>,
200                        SDTCisFP<0>, SDTCisVT<1, f64>]>, []>;
201def PPCxsmaxc : SDNode<"PPCISD::XSMAXCDP", SDT_PPCFPMinMax, []>;
202def PPCxsminc : SDNode<"PPCISD::XSMINCDP", SDT_PPCFPMinMax, []>;
203def PPChi       : SDNode<"PPCISD::Hi", SDTIntBinOp, []>;
204def PPClo       : SDNode<"PPCISD::Lo", SDTIntBinOp, []>;
205def PPCtoc_entry: SDNode<"PPCISD::TOC_ENTRY", SDTIntBinOp,
206                         [SDNPMayLoad, SDNPMemOperand]>;
207
208def PPCppc32GOT : SDNode<"PPCISD::PPC32_GOT", SDTIntLeaf, []>;
209
210def PPCaddisGotTprelHA : SDNode<"PPCISD::ADDIS_GOT_TPREL_HA", SDTIntBinOp>;
211def PPCldGotTprelL : SDNode<"PPCISD::LD_GOT_TPREL_L", SDTIntBinOp,
212                            [SDNPMayLoad]>;
213def PPCaddTls     : SDNode<"PPCISD::ADD_TLS", SDTIntBinOp, []>;
214def PPCaddisTlsgdHA : SDNode<"PPCISD::ADDIS_TLSGD_HA", SDTIntBinOp>;
215def PPCaddiTlsgdL   : SDNode<"PPCISD::ADDI_TLSGD_L", SDTIntBinOp>;
216def PPCgetTlsAddr   : SDNode<"PPCISD::GET_TLS_ADDR", SDTIntBinOp>;
217def PPCaddiTlsgdLAddr : SDNode<"PPCISD::ADDI_TLSGD_L_ADDR",
218                               SDTypeProfile<1, 3, [
219                                 SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>,
220                                 SDTCisSameAs<0, 3>, SDTCisInt<0> ]>>;
221def PPCaddisTlsldHA : SDNode<"PPCISD::ADDIS_TLSLD_HA", SDTIntBinOp>;
222def PPCaddiTlsldL   : SDNode<"PPCISD::ADDI_TLSLD_L", SDTIntBinOp>;
223def PPCgetTlsldAddr : SDNode<"PPCISD::GET_TLSLD_ADDR", SDTIntBinOp>;
224def PPCaddiTlsldLAddr : SDNode<"PPCISD::ADDI_TLSLD_L_ADDR",
225                               SDTypeProfile<1, 3, [
226                                 SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>,
227                                 SDTCisSameAs<0, 3>, SDTCisInt<0> ]>>;
228def PPCaddisDtprelHA : SDNode<"PPCISD::ADDIS_DTPREL_HA", SDTIntBinOp>;
229def PPCaddiDtprelL   : SDNode<"PPCISD::ADDI_DTPREL_L", SDTIntBinOp>;
230def PPCpaddiDtprel   : SDNode<"PPCISD::PADDI_DTPREL", SDTIntBinOp>;
231
232def PPCvperm     : SDNode<"PPCISD::VPERM", SDT_PPCvperm, []>;
233def PPCxxsplt    : SDNode<"PPCISD::XXSPLT", SDT_PPCVecSplat, []>;
234def PPCxxspltidp : SDNode<"PPCISD::XXSPLTI_SP_TO_DP", SDT_PPCSpToDp, []>;
235def PPCvecinsert : SDNode<"PPCISD::VECINSERT", SDT_PPCVecInsert, []>;
236def PPCxxpermdi  : SDNode<"PPCISD::XXPERMDI", SDT_PPCxxpermdi, []>;
237def PPCvecshl    : SDNode<"PPCISD::VECSHL", SDT_PPCVecShift, []>;
238
239def PPCcmpb     : SDNode<"PPCISD::CMPB", SDTIntBinOp, []>;
240
241// These nodes represent the 32-bit PPC shifts that operate on 6-bit shift
242// amounts.  These nodes are generated by the multi-precision shift code.
243def PPCsrl        : SDNode<"PPCISD::SRL"       , SDTIntShiftOp>;
244def PPCsra        : SDNode<"PPCISD::SRA"       , SDTIntShiftOp>;
245def PPCshl        : SDNode<"PPCISD::SHL"       , SDTIntShiftOp>;
246
247def PPCfnmsub     : SDNode<"PPCISD::FNMSUB"    , SDTFPTernaryOp>;
248
249def PPCextswsli : SDNode<"PPCISD::EXTSWSLI" , SDT_PPCextswsli>;
250
251def PPCstrict_fctidz : SDNode<"PPCISD::STRICT_FCTIDZ",
252                              SDTFPUnaryOp, [SDNPHasChain]>;
253def PPCstrict_fctiwz : SDNode<"PPCISD::STRICT_FCTIWZ",
254                              SDTFPUnaryOp, [SDNPHasChain]>;
255def PPCstrict_fctiduz : SDNode<"PPCISD::STRICT_FCTIDUZ",
256                               SDTFPUnaryOp, [SDNPHasChain]>;
257def PPCstrict_fctiwuz : SDNode<"PPCISD::STRICT_FCTIWUZ",
258                                SDTFPUnaryOp, [SDNPHasChain]>;
259
260def PPCany_fctidz : PatFrags<(ops node:$op),
261                             [(PPCstrict_fctidz node:$op),
262                              (PPCfctidz node:$op)]>;
263def PPCany_fctiwz : PatFrags<(ops node:$op),
264                             [(PPCstrict_fctiwz node:$op),
265                              (PPCfctiwz node:$op)]>;
266def PPCany_fctiduz : PatFrags<(ops node:$op),
267                              [(PPCstrict_fctiduz node:$op),
268                               (PPCfctiduz node:$op)]>;
269def PPCany_fctiwuz : PatFrags<(ops node:$op),
270                              [(PPCstrict_fctiwuz node:$op),
271                               (PPCfctiwuz node:$op)]>;
272
273// Move 2 i64 values into a VSX register
274def PPCbuild_fp128: SDNode<"PPCISD::BUILD_FP128",
275                           SDTypeProfile<1, 2,
276                             [SDTCisFP<0>, SDTCisSameSizeAs<1,2>,
277                              SDTCisSameAs<1,2>]>,
278                           []>;
279
280def PPCbuild_spe64: SDNode<"PPCISD::BUILD_SPE64",
281                           SDTypeProfile<1, 2,
282                             [SDTCisVT<0, f64>, SDTCisVT<1,i32>,
283                             SDTCisVT<1,i32>]>,
284                           []>;
285
286def PPCextract_spe : SDNode<"PPCISD::EXTRACT_SPE",
287                            SDTypeProfile<1, 2,
288                              [SDTCisVT<0, i32>, SDTCisVT<1, f64>,
289                              SDTCisPtrTy<2>]>,
290                              []>;
291
292// These are target-independent nodes, but have target-specific formats.
293def callseq_start : SDNode<"ISD::CALLSEQ_START", SDT_PPCCallSeqStart,
294                           [SDNPHasChain, SDNPOutGlue]>;
295def callseq_end   : SDNode<"ISD::CALLSEQ_END",   SDT_PPCCallSeqEnd,
296                           [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue]>;
297
298def SDT_PPCCall   : SDTypeProfile<0, -1, [SDTCisInt<0>]>;
299def PPCcall  : SDNode<"PPCISD::CALL", SDT_PPCCall,
300                      [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue,
301                       SDNPVariadic]>;
302def PPCcall_nop  : SDNode<"PPCISD::CALL_NOP", SDT_PPCCall,
303                          [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue,
304                           SDNPVariadic]>;
305def PPCcall_notoc : SDNode<"PPCISD::CALL_NOTOC", SDT_PPCCall,
306                           [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue,
307                            SDNPVariadic]>;
308def PPCmtctr      : SDNode<"PPCISD::MTCTR", SDT_PPCCall,
309                           [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue]>;
310def PPCbctrl : SDNode<"PPCISD::BCTRL", SDTNone,
311                      [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue,
312                       SDNPVariadic]>;
313def PPCbctrl_load_toc : SDNode<"PPCISD::BCTRL_LOAD_TOC",
314                               SDTypeProfile<0, 1, []>,
315                               [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue,
316                                SDNPVariadic]>;
317
318def retflag       : SDNode<"PPCISD::RET_FLAG", SDTNone,
319                           [SDNPHasChain, SDNPOptInGlue, SDNPVariadic]>;
320
321def PPCtc_return : SDNode<"PPCISD::TC_RETURN", SDT_PPCTC_ret,
322                        [SDNPHasChain,  SDNPOptInGlue, SDNPVariadic]>;
323
324def PPCeh_sjlj_setjmp  : SDNode<"PPCISD::EH_SJLJ_SETJMP",
325                                SDTypeProfile<1, 1, [SDTCisInt<0>,
326                                                     SDTCisPtrTy<1>]>,
327                                [SDNPHasChain, SDNPSideEffect]>;
328def PPCeh_sjlj_longjmp : SDNode<"PPCISD::EH_SJLJ_LONGJMP",
329                                SDTypeProfile<0, 1, [SDTCisPtrTy<0>]>,
330                                [SDNPHasChain, SDNPSideEffect]>;
331
332def SDT_PPCsc     : SDTypeProfile<0, 1, [SDTCisInt<0>]>;
333def PPCsc         : SDNode<"PPCISD::SC", SDT_PPCsc,
334                           [SDNPHasChain, SDNPSideEffect]>;
335
336def PPCclrbhrb    : SDNode<"PPCISD::CLRBHRB", SDTNone,
337                           [SDNPHasChain, SDNPSideEffect]>;
338def PPCmfbhrbe    : SDNode<"PPCISD::MFBHRBE", SDTIntBinOp, [SDNPHasChain]>;
339def PPCrfebb      : SDNode<"PPCISD::RFEBB", SDT_PPCsc,
340                           [SDNPHasChain, SDNPSideEffect]>;
341
342def PPCvcmp       : SDNode<"PPCISD::VCMP" , SDT_PPCvcmp, []>;
343def PPCvcmp_rec   : SDNode<"PPCISD::VCMP_rec", SDT_PPCvcmp, [SDNPOutGlue]>;
344
345def PPCcondbranch : SDNode<"PPCISD::COND_BRANCH", SDT_PPCcondbr,
346                           [SDNPHasChain, SDNPOptInGlue]>;
347
348// PPC-specific atomic operations.
349def PPCatomicCmpSwap_8 :
350  SDNode<"PPCISD::ATOMIC_CMP_SWAP_8", SDTAtomic3,
351         [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
352def PPCatomicCmpSwap_16 :
353  SDNode<"PPCISD::ATOMIC_CMP_SWAP_16", SDTAtomic3,
354         [SDNPHasChain, SDNPMayStore, SDNPMayLoad, SDNPMemOperand]>;
355def PPClbrx       : SDNode<"PPCISD::LBRX", SDT_PPClbrx,
356                           [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>;
357def PPCstbrx      : SDNode<"PPCISD::STBRX", SDT_PPCstbrx,
358                           [SDNPHasChain, SDNPMayStore]>;
359
360// Instructions to set/unset CR bit 6 for SVR4 vararg calls
361def PPCcr6set   : SDNode<"PPCISD::CR6SET", SDTNone,
362                         [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue]>;
363def PPCcr6unset : SDNode<"PPCISD::CR6UNSET", SDTNone,
364                         [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue]>;
365
366// Instructions to support dynamic alloca.
367def SDTDynOp  : SDTypeProfile<1, 2, []>;
368def SDTDynAreaOp  : SDTypeProfile<1, 1, []>;
369def PPCdynalloc   : SDNode<"PPCISD::DYNALLOC", SDTDynOp, [SDNPHasChain]>;
370def PPCdynareaoffset   : SDNode<"PPCISD::DYNAREAOFFSET", SDTDynAreaOp, [SDNPHasChain]>;
371def PPCprobedalloca : SDNode<"PPCISD::PROBED_ALLOCA", SDTDynOp, [SDNPHasChain]>;
372
373// PC Relative Specific Nodes
374def PPCmatpcreladdr : SDNode<"PPCISD::MAT_PCREL_ADDR", SDTIntUnaryOp, []>;
375def PPCtlsdynamatpcreladdr : SDNode<"PPCISD::TLS_DYNAMIC_MAT_PCREL_ADDR",
376                                    SDTIntUnaryOp, []>;
377def PPCtlslocalexecmataddr : SDNode<"PPCISD::TLS_LOCAL_EXEC_MAT_ADDR",
378                                    SDTIntUnaryOp, []>;
379
380//===----------------------------------------------------------------------===//
381// PowerPC specific transformation functions and pattern fragments.
382//
383
384// A floating point immediate that is not a positive zero and can be converted
385// to a single precision floating point non-denormal immediate without loss of
386// information.
387def nzFPImmAsi32 : PatLeaf<(fpimm), [{
388  APFloat APFloatOfN = N->getValueAPF();
389  return convertToNonDenormSingle(APFloatOfN) && !N->isExactlyValue(+0.0);
390}]>;
391
392// Convert the floating point immediate into a 32 bit floating point immediate
393// and get a i32 with the resulting bits.
394def getFPAs32BitInt : SDNodeXForm<fpimm, [{
395  APFloat APFloatOfN = N->getValueAPF();
396  convertToNonDenormSingle(APFloatOfN);
397  return CurDAG->getTargetConstant(APFloatOfN.bitcastToAPInt().getZExtValue(),
398                                   SDLoc(N), MVT::i32);
399}]>;
400
401def SHL32 : SDNodeXForm<imm, [{
402  // Transformation function: 31 - imm
403  return getI32Imm(31 - N->getZExtValue(), SDLoc(N));
404}]>;
405
406def SRL32 : SDNodeXForm<imm, [{
407  // Transformation function: 32 - imm
408  return N->getZExtValue() ? getI32Imm(32 - N->getZExtValue(), SDLoc(N))
409                           : getI32Imm(0, SDLoc(N));
410}]>;
411
412def LO16 : SDNodeXForm<imm, [{
413  // Transformation function: get the low 16 bits.
414  return getI32Imm((unsigned short)N->getZExtValue(), SDLoc(N));
415}]>;
416
417def HI16 : SDNodeXForm<imm, [{
418  // Transformation function: shift the immediate value down into the low bits.
419  return getI32Imm((unsigned)N->getZExtValue() >> 16, SDLoc(N));
420}]>;
421
422def HA16 : SDNodeXForm<imm, [{
423  // Transformation function: shift the immediate value down into the low bits.
424  long Val = N->getZExtValue();
425  return getI32Imm((Val - (signed short)Val) >> 16, SDLoc(N));
426}]>;
427def MB : SDNodeXForm<imm, [{
428  // Transformation function: get the start bit of a mask
429  unsigned mb = 0, me;
430  (void)isRunOfOnes((unsigned)N->getZExtValue(), mb, me);
431  return getI32Imm(mb, SDLoc(N));
432}]>;
433
434def ME : SDNodeXForm<imm, [{
435  // Transformation function: get the end bit of a mask
436  unsigned mb, me = 0;
437  (void)isRunOfOnes((unsigned)N->getZExtValue(), mb, me);
438  return getI32Imm(me, SDLoc(N));
439}]>;
440def maskimm32 : PatLeaf<(imm), [{
441  // maskImm predicate - True if immediate is a run of ones.
442  unsigned mb, me;
443  if (N->getValueType(0) == MVT::i32)
444    return isRunOfOnes((unsigned)N->getZExtValue(), mb, me);
445  else
446    return false;
447}]>;
448
449def imm32SExt16  : Operand<i32>, ImmLeaf<i32, [{
450  // imm32SExt16 predicate - True if the i32 immediate fits in a 16-bit
451  // sign extended field.  Used by instructions like 'addi'.
452  return (int32_t)Imm == (short)Imm;
453}]>;
454def imm64SExt16  : Operand<i64>, ImmLeaf<i64, [{
455  // imm64SExt16 predicate - True if the i64 immediate fits in a 16-bit
456  // sign extended field.  Used by instructions like 'addi'.
457  return (int64_t)Imm == (short)Imm;
458}]>;
459def immZExt16  : PatLeaf<(imm), [{
460  // immZExt16 predicate - True if the immediate fits in a 16-bit zero extended
461  // field.  Used by instructions like 'ori'.
462  return (uint64_t)N->getZExtValue() == (unsigned short)N->getZExtValue();
463}], LO16>;
464def immNonAllOneAnyExt8 : ImmLeaf<i32, [{
465  return (isInt<8>(Imm) && (Imm != -1)) || (isUInt<8>(Imm) && (Imm != 0xFF));
466}]>;
467def i32immNonAllOneNonZero : ImmLeaf<i32, [{ return Imm && (Imm != -1); }]>;
468def immSExt5NonZero : ImmLeaf<i32, [{ return Imm && isInt<5>(Imm); }]>;
469
470// imm16Shifted* - These match immediates where the low 16-bits are zero.  There
471// are two forms: imm16ShiftedSExt and imm16ShiftedZExt.  These two forms are
472// identical in 32-bit mode, but in 64-bit mode, they return true if the
473// immediate fits into a sign/zero extended 32-bit immediate (with the low bits
474// clear).
475def imm16ShiftedZExt : PatLeaf<(imm), [{
476  // imm16ShiftedZExt predicate - True if only bits in the top 16-bits of the
477  // immediate are set.  Used by instructions like 'xoris'.
478  return (N->getZExtValue() & ~uint64_t(0xFFFF0000)) == 0;
479}], HI16>;
480
481def imm16ShiftedSExt : PatLeaf<(imm), [{
482  // imm16ShiftedSExt predicate - True if only bits in the top 16-bits of the
483  // immediate are set.  Used by instructions like 'addis'.  Identical to
484  // imm16ShiftedZExt in 32-bit mode.
485  if (N->getZExtValue() & 0xFFFF) return false;
486  if (N->getValueType(0) == MVT::i32)
487    return true;
488  // For 64-bit, make sure it is sext right.
489  return N->getZExtValue() == (uint64_t)(int)N->getZExtValue();
490}], HI16>;
491
492def imm64ZExt32  : Operand<i64>, ImmLeaf<i64, [{
493  // imm64ZExt32 predicate - True if the i64 immediate fits in a 32-bit
494  // zero extended field.
495  return isUInt<32>(Imm);
496}]>;
497
498// Some r+i load/store instructions (such as LD, STD, LDU, etc.) that require
499// restricted memrix (4-aligned) constants are alignment sensitive. If these
500// offsets are hidden behind TOC entries than the values of the lower-order
501// bits cannot be checked directly. As a result, we need to also incorporate
502// an alignment check into the relevant patterns.
503
504def aligned4load : PatFrag<(ops node:$ptr), (load node:$ptr), [{
505  return cast<LoadSDNode>(N)->getAlignment() >= 4;
506}]>;
507def aligned4store : PatFrag<(ops node:$val, node:$ptr),
508                            (store node:$val, node:$ptr), [{
509  return cast<StoreSDNode>(N)->getAlignment() >= 4;
510}]>;
511def aligned4sextloadi32 : PatFrag<(ops node:$ptr), (sextloadi32 node:$ptr), [{
512  return cast<LoadSDNode>(N)->getAlignment() >= 4;
513}]>;
514def aligned4pre_store : PatFrag<
515                          (ops node:$val, node:$base, node:$offset),
516                          (pre_store node:$val, node:$base, node:$offset), [{
517  return cast<StoreSDNode>(N)->getAlignment() >= 4;
518}]>;
519
520def unaligned4load : PatFrag<(ops node:$ptr), (load node:$ptr), [{
521  return cast<LoadSDNode>(N)->getAlignment() < 4;
522}]>;
523def unaligned4store : PatFrag<(ops node:$val, node:$ptr),
524                              (store node:$val, node:$ptr), [{
525  return cast<StoreSDNode>(N)->getAlignment() < 4;
526}]>;
527def unaligned4sextloadi32 : PatFrag<(ops node:$ptr), (sextloadi32 node:$ptr), [{
528  return cast<LoadSDNode>(N)->getAlignment() < 4;
529}]>;
530
531// This is a somewhat weaker condition than actually checking for 16-byte
532// alignment. It is simply checking that the displacement can be represented
533// as an immediate that is a multiple of 16 (i.e. the requirements for DQ-Form
534// instructions).
535def quadwOffsetLoad : PatFrag<(ops node:$ptr), (load node:$ptr), [{
536  return isOffsetMultipleOf(N, 16);
537}]>;
538def quadwOffsetStore : PatFrag<(ops node:$val, node:$ptr),
539                               (store node:$val, node:$ptr), [{
540  return isOffsetMultipleOf(N, 16);
541}]>;
542def nonQuadwOffsetLoad : PatFrag<(ops node:$ptr), (load node:$ptr), [{
543  return !isOffsetMultipleOf(N, 16);
544}]>;
545def nonQuadwOffsetStore : PatFrag<(ops node:$val, node:$ptr),
546                                  (store node:$val, node:$ptr), [{
547  return !isOffsetMultipleOf(N, 16);
548}]>;
549
550// PatFrag for binary operation whose operands are both non-constant
551class BinOpWithoutSImm16Operand<SDNode opcode> :
552  PatFrag<(ops node:$left, node:$right), (opcode node:$left, node:$right), [{
553    int16_t Imm;
554    return !isIntS16Immediate(N->getOperand(0), Imm)
555             && !isIntS16Immediate(N->getOperand(1), Imm);
556}]>;
557
558def add_without_simm16 : BinOpWithoutSImm16Operand<add>;
559def mul_without_simm16 : BinOpWithoutSImm16Operand<mul>;
560
561//===----------------------------------------------------------------------===//
562// PowerPC Flag Definitions.
563
564class isPPC64 { bit PPC64 = 1; }
565class isRecordForm   { bit RC = 1; }
566
567class RegConstraint<string C> {
568  string Constraints = C;
569}
570class NoEncode<string E> {
571  string DisableEncoding = E;
572}
573
574
575//===----------------------------------------------------------------------===//
576// PowerPC Operand Definitions.
577
578// In the default PowerPC assembler syntax, registers are specified simply
579// by number, so they cannot be distinguished from immediate values (without
580// looking at the opcode).  This means that the default operand matching logic
581// for the asm parser does not work, and we need to specify custom matchers.
582// Since those can only be specified with RegisterOperand classes and not
583// directly on the RegisterClass, all instructions patterns used by the asm
584// parser need to use a RegisterOperand (instead of a RegisterClass) for
585// all their register operands.
586// For this purpose, we define one RegisterOperand for each RegisterClass,
587// using the same name as the class, just in lower case.
588
589def PPCRegGPRCAsmOperand : AsmOperandClass {
590  let Name = "RegGPRC"; let PredicateMethod = "isRegNumber";
591}
592def gprc : RegisterOperand<GPRC> {
593  let ParserMatchClass = PPCRegGPRCAsmOperand;
594}
595def PPCRegG8RCAsmOperand : AsmOperandClass {
596  let Name = "RegG8RC"; let PredicateMethod = "isRegNumber";
597}
598def g8rc : RegisterOperand<G8RC> {
599  let ParserMatchClass = PPCRegG8RCAsmOperand;
600}
601def PPCRegGPRCNoR0AsmOperand : AsmOperandClass {
602  let Name = "RegGPRCNoR0"; let PredicateMethod = "isRegNumber";
603}
604def gprc_nor0 : RegisterOperand<GPRC_NOR0> {
605  let ParserMatchClass = PPCRegGPRCNoR0AsmOperand;
606}
607def PPCRegG8RCNoX0AsmOperand : AsmOperandClass {
608  let Name = "RegG8RCNoX0"; let PredicateMethod = "isRegNumber";
609}
610def g8rc_nox0 : RegisterOperand<G8RC_NOX0> {
611  let ParserMatchClass = PPCRegG8RCNoX0AsmOperand;
612}
613def PPCRegF8RCAsmOperand : AsmOperandClass {
614  let Name = "RegF8RC"; let PredicateMethod = "isRegNumber";
615}
616def f8rc : RegisterOperand<F8RC> {
617  let ParserMatchClass = PPCRegF8RCAsmOperand;
618}
619def PPCRegF4RCAsmOperand : AsmOperandClass {
620  let Name = "RegF4RC"; let PredicateMethod = "isRegNumber";
621}
622def f4rc : RegisterOperand<F4RC> {
623  let ParserMatchClass = PPCRegF4RCAsmOperand;
624}
625def PPCRegVRRCAsmOperand : AsmOperandClass {
626  let Name = "RegVRRC"; let PredicateMethod = "isRegNumber";
627}
628def vrrc : RegisterOperand<VRRC> {
629  let ParserMatchClass = PPCRegVRRCAsmOperand;
630}
631def PPCRegVFRCAsmOperand : AsmOperandClass {
632  let Name = "RegVFRC"; let PredicateMethod = "isRegNumber";
633}
634def vfrc : RegisterOperand<VFRC> {
635  let ParserMatchClass = PPCRegVFRCAsmOperand;
636}
637def PPCRegCRBITRCAsmOperand : AsmOperandClass {
638  let Name = "RegCRBITRC"; let PredicateMethod = "isCRBitNumber";
639}
640def crbitrc : RegisterOperand<CRBITRC> {
641  let ParserMatchClass = PPCRegCRBITRCAsmOperand;
642}
643def PPCRegCRRCAsmOperand : AsmOperandClass {
644  let Name = "RegCRRC"; let PredicateMethod = "isCCRegNumber";
645}
646def crrc : RegisterOperand<CRRC> {
647  let ParserMatchClass = PPCRegCRRCAsmOperand;
648}
649def PPCRegSPERCAsmOperand : AsmOperandClass {
650  let Name = "RegSPERC"; let PredicateMethod = "isRegNumber";
651}
652def sperc : RegisterOperand<SPERC> {
653  let ParserMatchClass = PPCRegSPERCAsmOperand;
654}
655def PPCRegSPE4RCAsmOperand : AsmOperandClass {
656  let Name = "RegSPE4RC"; let PredicateMethod = "isRegNumber";
657}
658def spe4rc : RegisterOperand<GPRC> {
659  let ParserMatchClass = PPCRegSPE4RCAsmOperand;
660}
661
662def PPCU1ImmAsmOperand : AsmOperandClass {
663  let Name = "U1Imm"; let PredicateMethod = "isU1Imm";
664  let RenderMethod = "addImmOperands";
665}
666def u1imm   : Operand<i32> {
667  let PrintMethod = "printU1ImmOperand";
668  let ParserMatchClass = PPCU1ImmAsmOperand;
669  let OperandType = "OPERAND_IMMEDIATE";
670}
671
672def PPCU2ImmAsmOperand : AsmOperandClass {
673  let Name = "U2Imm"; let PredicateMethod = "isU2Imm";
674  let RenderMethod = "addImmOperands";
675}
676def u2imm   : Operand<i32> {
677  let PrintMethod = "printU2ImmOperand";
678  let ParserMatchClass = PPCU2ImmAsmOperand;
679  let OperandType = "OPERAND_IMMEDIATE";
680}
681
682def PPCATBitsAsHintAsmOperand : AsmOperandClass {
683  let Name = "ATBitsAsHint"; let PredicateMethod = "isATBitsAsHint";
684  let RenderMethod = "addImmOperands"; // Irrelevant, predicate always fails.
685}
686def atimm   : Operand<i32> {
687  let PrintMethod = "printATBitsAsHint";
688  let ParserMatchClass = PPCATBitsAsHintAsmOperand;
689  let OperandType = "OPERAND_IMMEDIATE";
690}
691
692def PPCU3ImmAsmOperand : AsmOperandClass {
693  let Name = "U3Imm"; let PredicateMethod = "isU3Imm";
694  let RenderMethod = "addImmOperands";
695}
696def u3imm   : Operand<i32> {
697  let PrintMethod = "printU3ImmOperand";
698  let ParserMatchClass = PPCU3ImmAsmOperand;
699  let OperandType = "OPERAND_IMMEDIATE";
700}
701
702def PPCU4ImmAsmOperand : AsmOperandClass {
703  let Name = "U4Imm"; let PredicateMethod = "isU4Imm";
704  let RenderMethod = "addImmOperands";
705}
706def u4imm   : Operand<i32> {
707  let PrintMethod = "printU4ImmOperand";
708  let ParserMatchClass = PPCU4ImmAsmOperand;
709  let OperandType = "OPERAND_IMMEDIATE";
710}
711def PPCS5ImmAsmOperand : AsmOperandClass {
712  let Name = "S5Imm"; let PredicateMethod = "isS5Imm";
713  let RenderMethod = "addImmOperands";
714}
715def s5imm   : Operand<i32> {
716  let PrintMethod = "printS5ImmOperand";
717  let ParserMatchClass = PPCS5ImmAsmOperand;
718  let DecoderMethod = "decodeSImmOperand<5>";
719  let OperandType = "OPERAND_IMMEDIATE";
720}
721def PPCU5ImmAsmOperand : AsmOperandClass {
722  let Name = "U5Imm"; let PredicateMethod = "isU5Imm";
723  let RenderMethod = "addImmOperands";
724}
725def u5imm   : Operand<i32> {
726  let PrintMethod = "printU5ImmOperand";
727  let ParserMatchClass = PPCU5ImmAsmOperand;
728  let DecoderMethod = "decodeUImmOperand<5>";
729  let OperandType = "OPERAND_IMMEDIATE";
730}
731def PPCU6ImmAsmOperand : AsmOperandClass {
732  let Name = "U6Imm"; let PredicateMethod = "isU6Imm";
733  let RenderMethod = "addImmOperands";
734}
735def u6imm   : Operand<i32> {
736  let PrintMethod = "printU6ImmOperand";
737  let ParserMatchClass = PPCU6ImmAsmOperand;
738  let DecoderMethod = "decodeUImmOperand<6>";
739  let OperandType = "OPERAND_IMMEDIATE";
740}
741def PPCU7ImmAsmOperand : AsmOperandClass {
742  let Name = "U7Imm"; let PredicateMethod = "isU7Imm";
743  let RenderMethod = "addImmOperands";
744}
745def u7imm   : Operand<i32> {
746  let PrintMethod = "printU7ImmOperand";
747  let ParserMatchClass = PPCU7ImmAsmOperand;
748  let DecoderMethod = "decodeUImmOperand<7>";
749  let OperandType = "OPERAND_IMMEDIATE";
750}
751def PPCU8ImmAsmOperand : AsmOperandClass {
752  let Name = "U8Imm"; let PredicateMethod = "isU8Imm";
753  let RenderMethod = "addImmOperands";
754}
755def u8imm   : Operand<i32> {
756  let PrintMethod = "printU8ImmOperand";
757  let ParserMatchClass = PPCU8ImmAsmOperand;
758  let DecoderMethod = "decodeUImmOperand<8>";
759  let OperandType = "OPERAND_IMMEDIATE";
760}
761def PPCU10ImmAsmOperand : AsmOperandClass {
762  let Name = "U10Imm"; let PredicateMethod = "isU10Imm";
763  let RenderMethod = "addImmOperands";
764}
765def u10imm  : Operand<i32> {
766  let PrintMethod = "printU10ImmOperand";
767  let ParserMatchClass = PPCU10ImmAsmOperand;
768  let DecoderMethod = "decodeUImmOperand<10>";
769  let OperandType = "OPERAND_IMMEDIATE";
770}
771def PPCU12ImmAsmOperand : AsmOperandClass {
772  let Name = "U12Imm"; let PredicateMethod = "isU12Imm";
773  let RenderMethod = "addImmOperands";
774}
775def u12imm  : Operand<i32> {
776  let PrintMethod = "printU12ImmOperand";
777  let ParserMatchClass = PPCU12ImmAsmOperand;
778  let DecoderMethod = "decodeUImmOperand<12>";
779  let OperandType = "OPERAND_IMMEDIATE";
780}
781def PPCS16ImmAsmOperand : AsmOperandClass {
782  let Name = "S16Imm"; let PredicateMethod = "isS16Imm";
783  let RenderMethod = "addS16ImmOperands";
784}
785def s16imm  : Operand<i32> {
786  let PrintMethod = "printS16ImmOperand";
787  let EncoderMethod = "getImm16Encoding";
788  let ParserMatchClass = PPCS16ImmAsmOperand;
789  let DecoderMethod = "decodeSImmOperand<16>";
790  let OperandType = "OPERAND_IMMEDIATE";
791}
792def PPCU16ImmAsmOperand : AsmOperandClass {
793  let Name = "U16Imm"; let PredicateMethod = "isU16Imm";
794  let RenderMethod = "addU16ImmOperands";
795}
796def u16imm  : Operand<i32> {
797  let PrintMethod = "printU16ImmOperand";
798  let EncoderMethod = "getImm16Encoding";
799  let ParserMatchClass = PPCU16ImmAsmOperand;
800  let DecoderMethod = "decodeUImmOperand<16>";
801  let OperandType = "OPERAND_IMMEDIATE";
802}
803def PPCS17ImmAsmOperand : AsmOperandClass {
804  let Name = "S17Imm"; let PredicateMethod = "isS17Imm";
805  let RenderMethod = "addS16ImmOperands";
806}
807def s17imm  : Operand<i32> {
808  // This operand type is used for addis/lis to allow the assembler parser
809  // to accept immediates in the range -65536..65535 for compatibility with
810  // the GNU assembler.  The operand is treated as 16-bit otherwise.
811  let PrintMethod = "printS16ImmOperand";
812  let EncoderMethod = "getImm16Encoding";
813  let ParserMatchClass = PPCS17ImmAsmOperand;
814  let DecoderMethod = "decodeSImmOperand<16>";
815  let OperandType = "OPERAND_IMMEDIATE";
816}
817def PPCS34ImmAsmOperand : AsmOperandClass {
818  let Name = "S34Imm";
819  let PredicateMethod = "isS34Imm";
820  let RenderMethod = "addImmOperands";
821}
822def s34imm : Operand<i64> {
823  let PrintMethod = "printS34ImmOperand";
824  let EncoderMethod = "getImm34EncodingNoPCRel";
825  let ParserMatchClass = PPCS34ImmAsmOperand;
826  let DecoderMethod = "decodeSImmOperand<34>";
827  let OperandType = "OPERAND_IMMEDIATE";
828}
829def s34imm_pcrel : Operand<i64> {
830  let PrintMethod = "printS34ImmOperand";
831  let EncoderMethod = "getImm34EncodingPCRel";
832  let ParserMatchClass = PPCS34ImmAsmOperand;
833  let DecoderMethod = "decodeSImmOperand<34>";
834  let OperandType = "OPERAND_IMMEDIATE";
835}
836def PPCImmZeroAsmOperand : AsmOperandClass {
837  let Name = "ImmZero";
838  let PredicateMethod = "isImmZero";
839  let RenderMethod = "addImmOperands";
840}
841def immZero : Operand<i32> {
842  let PrintMethod = "printImmZeroOperand";
843  let ParserMatchClass = PPCImmZeroAsmOperand;
844  let DecoderMethod = "decodeImmZeroOperand";
845  let OperandType = "OPERAND_IMMEDIATE";
846}
847
848def fpimm0 : PatLeaf<(fpimm), [{ return N->isExactlyValue(+0.0); }]>;
849
850def PPCDirectBrAsmOperand : AsmOperandClass {
851  let Name = "DirectBr"; let PredicateMethod = "isDirectBr";
852  let RenderMethod = "addBranchTargetOperands";
853}
854def directbrtarget : Operand<OtherVT> {
855  let PrintMethod = "printBranchOperand";
856  let EncoderMethod = "getDirectBrEncoding";
857  let DecoderMethod = "decodeDirectBrTarget";
858  let ParserMatchClass = PPCDirectBrAsmOperand;
859  let OperandType = "OPERAND_PCREL";
860}
861def absdirectbrtarget : Operand<OtherVT> {
862  let PrintMethod = "printAbsBranchOperand";
863  let EncoderMethod = "getAbsDirectBrEncoding";
864  let ParserMatchClass = PPCDirectBrAsmOperand;
865}
866def PPCCondBrAsmOperand : AsmOperandClass {
867  let Name = "CondBr"; let PredicateMethod = "isCondBr";
868  let RenderMethod = "addBranchTargetOperands";
869}
870def condbrtarget : Operand<OtherVT> {
871  let PrintMethod = "printBranchOperand";
872  let EncoderMethod = "getCondBrEncoding";
873  let DecoderMethod = "decodeCondBrTarget";
874  let ParserMatchClass = PPCCondBrAsmOperand;
875  let OperandType = "OPERAND_PCREL";
876}
877def abscondbrtarget : Operand<OtherVT> {
878  let PrintMethod = "printAbsBranchOperand";
879  let EncoderMethod = "getAbsCondBrEncoding";
880  let ParserMatchClass = PPCCondBrAsmOperand;
881}
882def calltarget : Operand<iPTR> {
883  let PrintMethod = "printBranchOperand";
884  let EncoderMethod = "getDirectBrEncoding";
885  let DecoderMethod = "decodeDirectBrTarget";
886  let ParserMatchClass = PPCDirectBrAsmOperand;
887  let OperandType = "OPERAND_PCREL";
888}
889def abscalltarget : Operand<iPTR> {
890  let PrintMethod = "printAbsBranchOperand";
891  let EncoderMethod = "getAbsDirectBrEncoding";
892  let ParserMatchClass = PPCDirectBrAsmOperand;
893}
894def PPCCRBitMaskOperand : AsmOperandClass {
895 let Name = "CRBitMask"; let PredicateMethod = "isCRBitMask";
896}
897def crbitm: Operand<i8> {
898  let PrintMethod = "printcrbitm";
899  let EncoderMethod = "get_crbitm_encoding";
900  let DecoderMethod = "decodeCRBitMOperand";
901  let ParserMatchClass = PPCCRBitMaskOperand;
902}
903// Address operands
904// A version of ptr_rc which excludes R0 (or X0 in 64-bit mode).
905def PPCRegGxRCNoR0Operand : AsmOperandClass {
906  let Name = "RegGxRCNoR0"; let PredicateMethod = "isRegNumber";
907}
908def ptr_rc_nor0 : Operand<iPTR>, PointerLikeRegClass<1> {
909  let ParserMatchClass = PPCRegGxRCNoR0Operand;
910}
911
912// New addressing modes with 34 bit immediates.
913def PPCDispRI34Operand : AsmOperandClass {
914  let Name = "DispRI34"; let PredicateMethod = "isS34Imm";
915  let RenderMethod = "addImmOperands";
916}
917def dispRI34 : Operand<iPTR> {
918  let ParserMatchClass = PPCDispRI34Operand;
919}
920def memri34 : Operand<iPTR> { // memri, imm is a 34-bit value.
921  let PrintMethod = "printMemRegImm34";
922  let MIOperandInfo = (ops dispRI34:$imm, ptr_rc_nor0:$reg);
923  let EncoderMethod = "getMemRI34Encoding";
924  let DecoderMethod = "decodeMemRI34Operands";
925}
926// memri, imm is a 34-bit value for pc-relative instructions where
927// base register is set to zero.
928def memri34_pcrel : Operand<iPTR> { // memri, imm is a 34-bit value.
929  let PrintMethod = "printMemRegImm34PCRel";
930  let MIOperandInfo = (ops dispRI34:$imm, immZero:$reg);
931  let EncoderMethod = "getMemRI34PCRelEncoding";
932  let DecoderMethod = "decodeMemRI34PCRelOperands";
933}
934
935// A version of ptr_rc usable with the asm parser.
936def PPCRegGxRCOperand : AsmOperandClass {
937  let Name = "RegGxRC"; let PredicateMethod = "isRegNumber";
938}
939def ptr_rc_idx : Operand<iPTR>, PointerLikeRegClass<0> {
940  let ParserMatchClass = PPCRegGxRCOperand;
941}
942
943def PPCDispRIOperand : AsmOperandClass {
944 let Name = "DispRI"; let PredicateMethod = "isS16Imm";
945 let RenderMethod = "addS16ImmOperands";
946}
947def dispRI : Operand<iPTR> {
948  let ParserMatchClass = PPCDispRIOperand;
949}
950def PPCDispRIXOperand : AsmOperandClass {
951 let Name = "DispRIX"; let PredicateMethod = "isS16ImmX4";
952 let RenderMethod = "addImmOperands";
953}
954def dispRIX : Operand<iPTR> {
955  let ParserMatchClass = PPCDispRIXOperand;
956}
957def PPCDispRIX16Operand : AsmOperandClass {
958 let Name = "DispRIX16"; let PredicateMethod = "isS16ImmX16";
959 let RenderMethod = "addImmOperands";
960}
961def dispRIX16 : Operand<iPTR> {
962  let ParserMatchClass = PPCDispRIX16Operand;
963}
964def PPCDispSPE8Operand : AsmOperandClass {
965 let Name = "DispSPE8"; let PredicateMethod = "isU8ImmX8";
966 let RenderMethod = "addImmOperands";
967}
968def dispSPE8 : Operand<iPTR> {
969  let ParserMatchClass = PPCDispSPE8Operand;
970}
971def PPCDispSPE4Operand : AsmOperandClass {
972 let Name = "DispSPE4"; let PredicateMethod = "isU7ImmX4";
973 let RenderMethod = "addImmOperands";
974}
975def dispSPE4 : Operand<iPTR> {
976  let ParserMatchClass = PPCDispSPE4Operand;
977}
978def PPCDispSPE2Operand : AsmOperandClass {
979 let Name = "DispSPE2"; let PredicateMethod = "isU6ImmX2";
980 let RenderMethod = "addImmOperands";
981}
982def dispSPE2 : Operand<iPTR> {
983  let ParserMatchClass = PPCDispSPE2Operand;
984}
985
986def memri : Operand<iPTR> {
987  let PrintMethod = "printMemRegImm";
988  let MIOperandInfo = (ops dispRI:$imm, ptr_rc_nor0:$reg);
989  let EncoderMethod = "getMemRIEncoding";
990  let DecoderMethod = "decodeMemRIOperands";
991  let OperandType = "OPERAND_MEMORY";
992}
993def memrr : Operand<iPTR> {
994  let PrintMethod = "printMemRegReg";
995  let MIOperandInfo = (ops ptr_rc_nor0:$ptrreg, ptr_rc_idx:$offreg);
996  let OperandType = "OPERAND_MEMORY";
997}
998def memrix : Operand<iPTR> {   // memri where the imm is 4-aligned.
999  let PrintMethod = "printMemRegImm";
1000  let MIOperandInfo = (ops dispRIX:$imm, ptr_rc_nor0:$reg);
1001  let EncoderMethod = "getMemRIXEncoding";
1002  let DecoderMethod = "decodeMemRIXOperands";
1003  let OperandType = "OPERAND_MEMORY";
1004}
1005def memrix16 : Operand<iPTR> { // memri, imm is 16-aligned, 12-bit, Inst{16:27}
1006  let PrintMethod = "printMemRegImm";
1007  let MIOperandInfo = (ops dispRIX16:$imm, ptr_rc_nor0:$reg);
1008  let EncoderMethod = "getMemRIX16Encoding";
1009  let DecoderMethod = "decodeMemRIX16Operands";
1010  let OperandType = "OPERAND_MEMORY";
1011}
1012def spe8dis : Operand<iPTR> {   // SPE displacement where the imm is 8-aligned.
1013  let PrintMethod = "printMemRegImm";
1014  let MIOperandInfo = (ops dispSPE8:$imm, ptr_rc_nor0:$reg);
1015  let EncoderMethod = "getSPE8DisEncoding";
1016  let DecoderMethod = "decodeSPE8Operands";
1017  let OperandType = "OPERAND_MEMORY";
1018}
1019def spe4dis : Operand<iPTR> {   // SPE displacement where the imm is 4-aligned.
1020  let PrintMethod = "printMemRegImm";
1021  let MIOperandInfo = (ops dispSPE4:$imm, ptr_rc_nor0:$reg);
1022  let EncoderMethod = "getSPE4DisEncoding";
1023  let DecoderMethod = "decodeSPE4Operands";
1024  let OperandType = "OPERAND_MEMORY";
1025}
1026def spe2dis : Operand<iPTR> {   // SPE displacement where the imm is 2-aligned.
1027  let PrintMethod = "printMemRegImm";
1028  let MIOperandInfo = (ops dispSPE2:$imm, ptr_rc_nor0:$reg);
1029  let EncoderMethod = "getSPE2DisEncoding";
1030  let DecoderMethod = "decodeSPE2Operands";
1031  let OperandType = "OPERAND_MEMORY";
1032}
1033
1034// A single-register address. This is used with the SjLj
1035// pseudo-instructions which translates to LD/LWZ.  These instructions requires
1036// G8RC_NOX0 registers.
1037def memr : Operand<iPTR> {
1038  let MIOperandInfo = (ops ptr_rc_nor0:$ptrreg);
1039  let OperandType = "OPERAND_MEMORY";
1040}
1041def PPCTLSRegOperand : AsmOperandClass {
1042  let Name = "TLSReg"; let PredicateMethod = "isTLSReg";
1043  let RenderMethod = "addTLSRegOperands";
1044}
1045def tlsreg32 : Operand<i32> {
1046  let EncoderMethod = "getTLSRegEncoding";
1047  let ParserMatchClass = PPCTLSRegOperand;
1048}
1049def tlsgd32 : Operand<i32> {}
1050def tlscall32 : Operand<i32> {
1051  let PrintMethod = "printTLSCall";
1052  let MIOperandInfo = (ops calltarget:$func, tlsgd32:$sym);
1053  let EncoderMethod = "getTLSCallEncoding";
1054}
1055
1056// PowerPC Predicate operand.
1057def pred : Operand<OtherVT> {
1058  let PrintMethod = "printPredicateOperand";
1059  let MIOperandInfo = (ops i32imm:$bibo, crrc:$reg);
1060}
1061
1062// Define PowerPC specific addressing mode.
1063
1064// d-form
1065def iaddr    : ComplexPattern<iPTR, 2, "SelectAddrImm",     [], []>; // "stb"
1066// ds-form
1067def iaddrX4  : ComplexPattern<iPTR, 2, "SelectAddrImmX4",   [], []>; // "std"
1068// dq-form
1069def iaddrX16 : ComplexPattern<iPTR, 2, "SelectAddrImmX16",  [], []>; // "stxv"
1070// 8LS:d-form
1071def iaddrX34 : ComplexPattern<iPTR, 2, "SelectAddrImmX34",  [], []>; // "pstxvp"
1072
1073// Below forms are all x-form addressing mode, use three different ones so we
1074// can make a accurate check for x-form instructions in ISEL.
1075// x-form addressing mode whose associated displacement form is D.
1076def xaddr  : ComplexPattern<iPTR, 2, "SelectAddrIdx",     [], []>;    // "stbx"
1077// x-form addressing mode whose associated displacement form is DS.
1078def xaddrX4 : ComplexPattern<iPTR, 2, "SelectAddrIdxX4",    [], []>;  // "stdx"
1079// x-form addressing mode whose associated displacement form is DQ.
1080def xaddrX16 : ComplexPattern<iPTR, 2, "SelectAddrIdxX16",   [], []>; // "stxvx"
1081
1082def xoaddr : ComplexPattern<iPTR, 2, "SelectAddrIdxOnly",[], []>;
1083
1084// The address in a single register. This is used with the SjLj
1085// pseudo-instructions.
1086def addr   : ComplexPattern<iPTR, 1, "SelectAddr",[], []>;
1087
1088/// This is just the offset part of iaddr, used for preinc.
1089def iaddroff : ComplexPattern<iPTR, 1, "SelectAddrImmOffs", [], []>;
1090
1091// PC Relative Address
1092def pcreladdr : ComplexPattern<iPTR, 1, "SelectAddrPCRel", [], []>;
1093
1094//===----------------------------------------------------------------------===//
1095// PowerPC Instruction Predicate Definitions.
1096def In32BitMode  : Predicate<"!Subtarget->isPPC64()">;
1097def In64BitMode  : Predicate<"Subtarget->isPPC64()">;
1098def IsBookE  : Predicate<"Subtarget->isBookE()">;
1099def IsNotBookE  : Predicate<"!Subtarget->isBookE()">;
1100def HasOnlyMSYNC : Predicate<"Subtarget->hasOnlyMSYNC()">;
1101def HasSYNC   : Predicate<"!Subtarget->hasOnlyMSYNC()">;
1102def IsPPC4xx  : Predicate<"Subtarget->isPPC4xx()">;
1103def IsPPC6xx  : Predicate<"Subtarget->isPPC6xx()">;
1104def IsE500  : Predicate<"Subtarget->isE500()">;
1105def HasSPE  : Predicate<"Subtarget->hasSPE()">;
1106def HasICBT : Predicate<"Subtarget->hasICBT()">;
1107def HasPartwordAtomics : Predicate<"Subtarget->hasPartwordAtomics()">;
1108def NoNaNsFPMath
1109    : Predicate<"Subtarget->getTargetMachine().Options.NoNaNsFPMath">;
1110def NaNsFPMath
1111    : Predicate<"!Subtarget->getTargetMachine().Options.NoNaNsFPMath">;
1112def HasBPERMD : Predicate<"Subtarget->hasBPERMD()">;
1113def HasExtDiv : Predicate<"Subtarget->hasExtDiv()">;
1114def IsISA3_0 : Predicate<"Subtarget->isISA3_0()">;
1115def HasFPU : Predicate<"Subtarget->hasFPU()">;
1116def PCRelativeMemops : Predicate<"Subtarget->hasPCRelativeMemops()">;
1117def IsNotISA3_1 : Predicate<"!Subtarget->isISA3_1()">;
1118
1119//===----------------------------------------------------------------------===//
1120// PowerPC Multiclass Definitions.
1121
1122multiclass XForm_6r<bits<6> opcode, bits<10> xo, dag OOL, dag IOL,
1123                    string asmbase, string asmstr, InstrItinClass itin,
1124                    list<dag> pattern> {
1125  let BaseName = asmbase in {
1126    def NAME : XForm_6<opcode, xo, OOL, IOL,
1127                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1128                       pattern>, RecFormRel;
1129    let Defs = [CR0] in
1130    def _rec    : XForm_6<opcode, xo, OOL, IOL,
1131                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1132                       []>, isRecordForm, RecFormRel;
1133  }
1134}
1135
1136multiclass XForm_6rc<bits<6> opcode, bits<10> xo, dag OOL, dag IOL,
1137                     string asmbase, string asmstr, InstrItinClass itin,
1138                     list<dag> pattern> {
1139  let BaseName = asmbase in {
1140    let Defs = [CARRY] in
1141    def NAME : XForm_6<opcode, xo, OOL, IOL,
1142                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1143                       pattern>, RecFormRel;
1144    let Defs = [CARRY, CR0] in
1145    def _rec    : XForm_6<opcode, xo, OOL, IOL,
1146                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1147                       []>, isRecordForm, RecFormRel;
1148  }
1149}
1150
1151multiclass XForm_10rc<bits<6> opcode, bits<10> xo, dag OOL, dag IOL,
1152                      string asmbase, string asmstr, InstrItinClass itin,
1153                      list<dag> pattern> {
1154  let BaseName = asmbase in {
1155    let Defs = [CARRY] in
1156    def NAME : XForm_10<opcode, xo, OOL, IOL,
1157                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1158                       pattern>, RecFormRel;
1159    let Defs = [CARRY, CR0] in
1160    def _rec    : XForm_10<opcode, xo, OOL, IOL,
1161                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1162                       []>, isRecordForm, RecFormRel;
1163  }
1164}
1165
1166multiclass XForm_11r<bits<6> opcode, bits<10> xo, dag OOL, dag IOL,
1167                    string asmbase, string asmstr, InstrItinClass itin,
1168                    list<dag> pattern> {
1169  let BaseName = asmbase in {
1170    def NAME : XForm_11<opcode, xo, OOL, IOL,
1171                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1172                       pattern>, RecFormRel;
1173    let Defs = [CR0] in
1174    def _rec    : XForm_11<opcode, xo, OOL, IOL,
1175                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1176                       []>, isRecordForm, RecFormRel;
1177  }
1178}
1179
1180multiclass XOForm_1r<bits<6> opcode, bits<9> xo, bit oe, dag OOL, dag IOL,
1181                    string asmbase, string asmstr, InstrItinClass itin,
1182                    list<dag> pattern> {
1183  let BaseName = asmbase in {
1184    def NAME : XOForm_1<opcode, xo, oe, OOL, IOL,
1185                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1186                       pattern>, RecFormRel;
1187    let Defs = [CR0] in
1188    def _rec    : XOForm_1<opcode, xo, oe, OOL, IOL,
1189                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1190                       []>, isRecordForm, RecFormRel;
1191  }
1192}
1193
1194// Multiclass for instructions which have a record overflow form as well
1195// as a record form but no carry (i.e. mulld, mulldo, subf, subfo, etc.)
1196multiclass XOForm_1rx<bits<6> opcode, bits<9> xo, bit oe, dag OOL, dag IOL,
1197                      string asmbase, string asmstr, InstrItinClass itin,
1198                      list<dag> pattern> {
1199  let BaseName = asmbase in {
1200    def NAME : XOForm_1<opcode, xo, 0, OOL, IOL,
1201                        !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1202                        pattern>, RecFormRel;
1203    let Defs = [CR0] in
1204    def _rec    : XOForm_1<opcode, xo, 0, OOL, IOL,
1205                        !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1206                        []>, isRecordForm, RecFormRel;
1207  }
1208  let BaseName = !strconcat(asmbase, "O") in {
1209    let Defs = [XER] in
1210    def O    : XOForm_1<opcode, xo, 1, OOL, IOL,
1211                        !strconcat(asmbase, !strconcat("o ", asmstr)), itin,
1212                        []>, RecFormRel;
1213    let Defs = [XER, CR0] in
1214    def O_rec    : XOForm_1<opcode, xo, 1, OOL, IOL,
1215                         !strconcat(asmbase, !strconcat("o. ", asmstr)), itin,
1216                         []>, isRecordForm, RecFormRel;
1217  }
1218}
1219
1220// Multiclass for instructions for which the non record form is not cracked
1221// and the record form is cracked (i.e. divw, mullw, etc.)
1222multiclass XOForm_1rcr<bits<6> opcode, bits<9> xo, bit oe, dag OOL, dag IOL,
1223                      string asmbase, string asmstr, InstrItinClass itin,
1224                      list<dag> pattern> {
1225  let BaseName = asmbase in {
1226    def NAME : XOForm_1<opcode, xo, oe, OOL, IOL,
1227                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1228                       pattern>, RecFormRel;
1229    let Defs = [CR0] in
1230    def _rec    : XOForm_1<opcode, xo, oe, OOL, IOL,
1231                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1232                       []>, isRecordForm, RecFormRel, PPC970_DGroup_First,
1233                       PPC970_DGroup_Cracked;
1234  }
1235  let BaseName = !strconcat(asmbase, "O") in {
1236    let Defs = [XER] in
1237    def O    : XOForm_1<opcode, xo, 1, OOL, IOL,
1238                        !strconcat(asmbase, !strconcat("o ", asmstr)), itin,
1239                        []>, RecFormRel;
1240    let Defs = [XER, CR0] in
1241    def O_rec   : XOForm_1<opcode, xo, 1, OOL, IOL,
1242                        !strconcat(asmbase, !strconcat("o. ", asmstr)), itin,
1243                        []>, isRecordForm, RecFormRel;
1244  }
1245}
1246
1247multiclass XOForm_1rc<bits<6> opcode, bits<9> xo, bit oe, dag OOL, dag IOL,
1248                      string asmbase, string asmstr, InstrItinClass itin,
1249                      list<dag> pattern> {
1250  let BaseName = asmbase in {
1251    let Defs = [CARRY] in
1252    def NAME : XOForm_1<opcode, xo, oe, OOL, IOL,
1253                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1254                       pattern>, RecFormRel;
1255    let Defs = [CARRY, CR0] in
1256    def _rec    : XOForm_1<opcode, xo, oe, OOL, IOL,
1257                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1258                       []>, isRecordForm, RecFormRel;
1259  }
1260  let BaseName = !strconcat(asmbase, "O") in {
1261    let Defs = [CARRY, XER] in
1262    def O    : XOForm_1<opcode, xo, 1, OOL, IOL,
1263                        !strconcat(asmbase, !strconcat("o ", asmstr)), itin,
1264                        []>, RecFormRel;
1265    let Defs = [CARRY, XER, CR0] in
1266    def O_rec   : XOForm_1<opcode, xo, 1, OOL, IOL,
1267                        !strconcat(asmbase, !strconcat("o. ", asmstr)), itin,
1268                        []>, isRecordForm, RecFormRel;
1269  }
1270}
1271
1272multiclass XOForm_3r<bits<6> opcode, bits<9> xo, bit oe, dag OOL, dag IOL,
1273                    string asmbase, string asmstr, InstrItinClass itin,
1274                    list<dag> pattern> {
1275  let BaseName = asmbase in {
1276    def NAME : XOForm_3<opcode, xo, oe, OOL, IOL,
1277                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1278                       pattern>, RecFormRel;
1279    let Defs = [CR0] in
1280    def _rec    : XOForm_3<opcode, xo, oe, OOL, IOL,
1281                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1282                       []>, isRecordForm, RecFormRel;
1283  }
1284  let BaseName = !strconcat(asmbase, "O") in {
1285    let Defs = [XER] in
1286    def O    : XOForm_3<opcode, xo, 1, OOL, IOL,
1287                        !strconcat(asmbase, !strconcat("o ", asmstr)), itin,
1288                        []>, RecFormRel;
1289    let Defs = [XER, CR0] in
1290    def O_rec   : XOForm_3<opcode, xo, 1, OOL, IOL,
1291                        !strconcat(asmbase, !strconcat("o. ", asmstr)), itin,
1292                        []>, isRecordForm, RecFormRel;
1293  }
1294}
1295
1296multiclass XOForm_3rc<bits<6> opcode, bits<9> xo, bit oe, dag OOL, dag IOL,
1297                      string asmbase, string asmstr, InstrItinClass itin,
1298                      list<dag> pattern> {
1299  let BaseName = asmbase in {
1300    let Defs = [CARRY] in
1301    def NAME : XOForm_3<opcode, xo, oe, OOL, IOL,
1302                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1303                       pattern>, RecFormRel;
1304    let Defs = [CARRY, CR0] in
1305    def _rec    : XOForm_3<opcode, xo, oe, OOL, IOL,
1306                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1307                       []>, isRecordForm, RecFormRel;
1308  }
1309  let BaseName = !strconcat(asmbase, "O") in {
1310    let Defs = [CARRY, XER] in
1311    def O    : XOForm_3<opcode, xo, 1, OOL, IOL,
1312                        !strconcat(asmbase, !strconcat("o ", asmstr)), itin,
1313                        []>, RecFormRel;
1314    let Defs = [CARRY, XER, CR0] in
1315    def O_rec   : XOForm_3<opcode, xo, 1, OOL, IOL,
1316                        !strconcat(asmbase, !strconcat("o. ", asmstr)), itin,
1317                        []>, isRecordForm, RecFormRel;
1318  }
1319}
1320
1321multiclass MForm_2r<bits<6> opcode, dag OOL, dag IOL,
1322                    string asmbase, string asmstr, InstrItinClass itin,
1323                    list<dag> pattern> {
1324  let BaseName = asmbase in {
1325    def NAME : MForm_2<opcode, OOL, IOL,
1326                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1327                       pattern>, RecFormRel;
1328    let Defs = [CR0] in
1329    def _rec    : MForm_2<opcode, OOL, IOL,
1330                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1331                       []>, isRecordForm, RecFormRel;
1332  }
1333}
1334
1335multiclass MDForm_1r<bits<6> opcode, bits<3> xo, dag OOL, dag IOL,
1336                    string asmbase, string asmstr, InstrItinClass itin,
1337                    list<dag> pattern> {
1338  let BaseName = asmbase in {
1339    def NAME : MDForm_1<opcode, xo, OOL, IOL,
1340                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1341                       pattern>, RecFormRel;
1342    let Defs = [CR0] in
1343    def _rec    : MDForm_1<opcode, xo, OOL, IOL,
1344                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1345                       []>, isRecordForm, RecFormRel;
1346  }
1347}
1348
1349multiclass MDSForm_1r<bits<6> opcode, bits<4> xo, dag OOL, dag IOL,
1350                     string asmbase, string asmstr, InstrItinClass itin,
1351                     list<dag> pattern> {
1352  let BaseName = asmbase in {
1353    def NAME : MDSForm_1<opcode, xo, OOL, IOL,
1354                        !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1355                        pattern>, RecFormRel;
1356    let Defs = [CR0] in
1357    def _rec    : MDSForm_1<opcode, xo, OOL, IOL,
1358                        !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1359                        []>, isRecordForm, RecFormRel;
1360  }
1361}
1362
1363multiclass XSForm_1rc<bits<6> opcode, bits<9> xo, dag OOL, dag IOL,
1364                      string asmbase, string asmstr, InstrItinClass itin,
1365                      list<dag> pattern> {
1366  let BaseName = asmbase in {
1367    let Defs = [CARRY] in
1368    def NAME : XSForm_1<opcode, xo, OOL, IOL,
1369                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1370                       pattern>, RecFormRel;
1371    let Defs = [CARRY, CR0] in
1372    def _rec    : XSForm_1<opcode, xo, OOL, IOL,
1373                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1374                       []>, isRecordForm, RecFormRel;
1375  }
1376}
1377
1378multiclass XSForm_1r<bits<6> opcode, bits<9> xo, dag OOL, dag IOL,
1379                    string asmbase, string asmstr, InstrItinClass itin,
1380                    list<dag> pattern> {
1381  let BaseName = asmbase in {
1382    def NAME : XSForm_1<opcode, xo, OOL, IOL,
1383                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1384                       pattern>, RecFormRel;
1385    let Defs = [CR0] in
1386    def _rec    : XSForm_1<opcode, xo, OOL, IOL,
1387                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1388                       []>, isRecordForm, RecFormRel;
1389  }
1390}
1391
1392multiclass XForm_26r<bits<6> opcode, bits<10> xo, dag OOL, dag IOL,
1393                    string asmbase, string asmstr, InstrItinClass itin,
1394                    list<dag> pattern> {
1395  let BaseName = asmbase in {
1396    def NAME : XForm_26<opcode, xo, OOL, IOL,
1397                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1398                       pattern>, RecFormRel;
1399    let Defs = [CR1] in
1400    def _rec    : XForm_26<opcode, xo, OOL, IOL,
1401                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1402                       []>, isRecordForm, RecFormRel;
1403  }
1404}
1405
1406multiclass XForm_28r<bits<6> opcode, bits<10> xo, dag OOL, dag IOL,
1407                    string asmbase, string asmstr, InstrItinClass itin,
1408                    list<dag> pattern> {
1409  let BaseName = asmbase in {
1410    def NAME : XForm_28<opcode, xo, OOL, IOL,
1411                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1412                       pattern>, RecFormRel;
1413    let Defs = [CR1] in
1414    def _rec    : XForm_28<opcode, xo, OOL, IOL,
1415                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1416                       []>, isRecordForm, RecFormRel;
1417  }
1418}
1419
1420multiclass AForm_1r<bits<6> opcode, bits<5> xo, dag OOL, dag IOL,
1421                    string asmbase, string asmstr, InstrItinClass itin,
1422                    list<dag> pattern> {
1423  let BaseName = asmbase in {
1424    def NAME : AForm_1<opcode, xo, OOL, IOL,
1425                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1426                       pattern>, RecFormRel;
1427    let Defs = [CR1] in
1428    def _rec    : AForm_1<opcode, xo, OOL, IOL,
1429                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1430                       []>, isRecordForm, RecFormRel;
1431  }
1432}
1433
1434multiclass AForm_2r<bits<6> opcode, bits<5> xo, dag OOL, dag IOL,
1435                    string asmbase, string asmstr, InstrItinClass itin,
1436                    list<dag> pattern> {
1437  let BaseName = asmbase in {
1438    def NAME : AForm_2<opcode, xo, OOL, IOL,
1439                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1440                       pattern>, RecFormRel;
1441    let Defs = [CR1] in
1442    def _rec    : AForm_2<opcode, xo, OOL, IOL,
1443                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1444                       []>, isRecordForm, RecFormRel;
1445  }
1446}
1447
1448multiclass AForm_3r<bits<6> opcode, bits<5> xo, dag OOL, dag IOL,
1449                    string asmbase, string asmstr, InstrItinClass itin,
1450                    list<dag> pattern> {
1451  let BaseName = asmbase in {
1452    def NAME : AForm_3<opcode, xo, OOL, IOL,
1453                       !strconcat(asmbase, !strconcat(" ", asmstr)), itin,
1454                       pattern>, RecFormRel;
1455    let Defs = [CR1] in
1456    def _rec    : AForm_3<opcode, xo, OOL, IOL,
1457                       !strconcat(asmbase, !strconcat(". ", asmstr)), itin,
1458                       []>, isRecordForm, RecFormRel;
1459  }
1460}
1461
1462//===----------------------------------------------------------------------===//
1463// PowerPC Instruction Definitions.
1464
1465// Pseudo instructions:
1466
1467let hasCtrlDep = 1 in {
1468let Defs = [R1], Uses = [R1] in {
1469def ADJCALLSTACKDOWN : PPCEmitTimePseudo<(outs), (ins u16imm:$amt1, u16imm:$amt2),
1470                              "#ADJCALLSTACKDOWN $amt1 $amt2",
1471                              [(callseq_start timm:$amt1, timm:$amt2)]>;
1472def ADJCALLSTACKUP   : PPCEmitTimePseudo<(outs), (ins u16imm:$amt1, u16imm:$amt2),
1473                              "#ADJCALLSTACKUP $amt1 $amt2",
1474                              [(callseq_end timm:$amt1, timm:$amt2)]>;
1475}
1476} // hasCtrlDep
1477
1478let Defs = [R1], Uses = [R1] in
1479def DYNALLOC : PPCEmitTimePseudo<(outs gprc:$result), (ins gprc:$negsize, memri:$fpsi), "#DYNALLOC",
1480                       [(set i32:$result,
1481                             (PPCdynalloc i32:$negsize, iaddr:$fpsi))]>;
1482def DYNAREAOFFSET : PPCEmitTimePseudo<(outs i32imm:$result), (ins memri:$fpsi), "#DYNAREAOFFSET",
1483                       [(set i32:$result, (PPCdynareaoffset iaddr:$fpsi))]>;
1484// Probed alloca to support stack clash protection.
1485let Defs = [R1], Uses = [R1], hasNoSchedulingInfo = 1 in {
1486def PROBED_ALLOCA_32 : PPCCustomInserterPseudo<(outs gprc:$result),
1487                         (ins gprc:$negsize, memri:$fpsi), "#PROBED_ALLOCA_32",
1488                           [(set i32:$result,
1489                             (PPCprobedalloca i32:$negsize, iaddr:$fpsi))]>;
1490def PREPARE_PROBED_ALLOCA_32 : PPCEmitTimePseudo<(outs
1491    gprc:$fp, gprc:$actual_negsize),
1492    (ins gprc:$negsize, memri:$fpsi), "#PREPARE_PROBED_ALLOCA_32", []>;
1493def PREPARE_PROBED_ALLOCA_NEGSIZE_SAME_REG_32 : PPCEmitTimePseudo<(outs
1494    gprc:$fp, gprc:$actual_negsize),
1495    (ins gprc:$negsize, memri:$fpsi),
1496    "#PREPARE_PROBED_ALLOCA_NEGSIZE_SAME_REG_32", []>,
1497    RegConstraint<"$actual_negsize = $negsize">;
1498def PROBED_STACKALLOC_32 : PPCEmitTimePseudo<(outs gprc:$scratch, gprc:$temp),
1499    (ins i64imm:$stacksize),
1500    "#PROBED_STACKALLOC_32", []>;
1501}
1502
1503// SELECT_CC_* - Used to implement the SELECT_CC DAG operation.  Expanded after
1504// instruction selection into a branch sequence.
1505let PPC970_Single = 1 in {
1506  // Note that SELECT_CC_I4 and SELECT_CC_I8 use the no-r0 register classes
1507  // because either operand might become the first operand in an isel, and
1508  // that operand cannot be r0.
1509  def SELECT_CC_I4 : PPCCustomInserterPseudo<(outs gprc:$dst), (ins crrc:$cond,
1510                              gprc_nor0:$T, gprc_nor0:$F,
1511                              i32imm:$BROPC), "#SELECT_CC_I4",
1512                              []>;
1513  def SELECT_CC_I8 : PPCCustomInserterPseudo<(outs g8rc:$dst), (ins crrc:$cond,
1514                              g8rc_nox0:$T, g8rc_nox0:$F,
1515                              i32imm:$BROPC), "#SELECT_CC_I8",
1516                              []>;
1517  def SELECT_CC_F4  : PPCCustomInserterPseudo<(outs f4rc:$dst), (ins crrc:$cond, f4rc:$T, f4rc:$F,
1518                              i32imm:$BROPC), "#SELECT_CC_F4",
1519                              []>;
1520  def SELECT_CC_F8  : PPCCustomInserterPseudo<(outs f8rc:$dst), (ins crrc:$cond, f8rc:$T, f8rc:$F,
1521                              i32imm:$BROPC), "#SELECT_CC_F8",
1522                              []>;
1523  def SELECT_CC_F16  : PPCCustomInserterPseudo<(outs vrrc:$dst), (ins crrc:$cond, vrrc:$T, vrrc:$F,
1524                              i32imm:$BROPC), "#SELECT_CC_F16",
1525                              []>;
1526  def SELECT_CC_VRRC: PPCCustomInserterPseudo<(outs vrrc:$dst), (ins crrc:$cond, vrrc:$T, vrrc:$F,
1527                              i32imm:$BROPC), "#SELECT_CC_VRRC",
1528                              []>;
1529
1530  // SELECT_* pseudo instructions, like SELECT_CC_* but taking condition
1531  // register bit directly.
1532  def SELECT_I4 : PPCCustomInserterPseudo<(outs gprc:$dst), (ins crbitrc:$cond,
1533                          gprc_nor0:$T, gprc_nor0:$F), "#SELECT_I4",
1534                          [(set i32:$dst, (select i1:$cond, i32:$T, i32:$F))]>;
1535  def SELECT_I8 : PPCCustomInserterPseudo<(outs g8rc:$dst), (ins crbitrc:$cond,
1536                          g8rc_nox0:$T, g8rc_nox0:$F), "#SELECT_I8",
1537                          [(set i64:$dst, (select i1:$cond, i64:$T, i64:$F))]>;
1538let Predicates = [HasFPU] in {
1539  def SELECT_F4  : PPCCustomInserterPseudo<(outs f4rc:$dst), (ins crbitrc:$cond,
1540                          f4rc:$T, f4rc:$F), "#SELECT_F4",
1541                          [(set f32:$dst, (select i1:$cond, f32:$T, f32:$F))]>;
1542  def SELECT_F8  : PPCCustomInserterPseudo<(outs f8rc:$dst), (ins crbitrc:$cond,
1543                          f8rc:$T, f8rc:$F), "#SELECT_F8",
1544                          [(set f64:$dst, (select i1:$cond, f64:$T, f64:$F))]>;
1545  def SELECT_F16  : PPCCustomInserterPseudo<(outs vrrc:$dst), (ins crbitrc:$cond,
1546                          vrrc:$T, vrrc:$F), "#SELECT_F16",
1547                          [(set f128:$dst, (select i1:$cond, f128:$T, f128:$F))]>;
1548}
1549  def SELECT_VRRC: PPCCustomInserterPseudo<(outs vrrc:$dst), (ins crbitrc:$cond,
1550                          vrrc:$T, vrrc:$F), "#SELECT_VRRC",
1551                          [(set v4i32:$dst,
1552                                (select i1:$cond, v4i32:$T, v4i32:$F))]>;
1553}
1554
1555// SPILL_CR - Indicate that we're dumping the CR register, so we'll need to
1556// scavenge a register for it.
1557let mayStore = 1 in {
1558def SPILL_CR : PPCEmitTimePseudo<(outs), (ins crrc:$cond, memri:$F),
1559                     "#SPILL_CR", []>;
1560def SPILL_CRBIT : PPCEmitTimePseudo<(outs), (ins crbitrc:$cond, memri:$F),
1561                         "#SPILL_CRBIT", []>;
1562}
1563
1564// RESTORE_CR - Indicate that we're restoring the CR register (previously
1565// spilled), so we'll need to scavenge a register for it.
1566let mayLoad = 1 in {
1567def RESTORE_CR : PPCEmitTimePseudo<(outs crrc:$cond), (ins memri:$F),
1568                     "#RESTORE_CR", []>;
1569def RESTORE_CRBIT : PPCEmitTimePseudo<(outs crbitrc:$cond), (ins memri:$F),
1570                           "#RESTORE_CRBIT", []>;
1571}
1572
1573let isTerminator = 1, isBarrier = 1, PPC970_Unit = 7 in {
1574  let isPredicable = 1, isReturn = 1, Uses = [LR, RM] in
1575    def BLR : XLForm_2_ext<19, 16, 20, 0, 0, (outs), (ins), "blr", IIC_BrB,
1576                           [(retflag)]>, Requires<[In32BitMode]>;
1577  let isBranch = 1, isIndirectBranch = 1, Uses = [CTR] in {
1578    let isPredicable = 1 in
1579      def BCTR : XLForm_2_ext<19, 528, 20, 0, 0, (outs), (ins), "bctr", IIC_BrB,
1580                              []>;
1581
1582    let isCodeGenOnly = 1 in {
1583      def BCCCTR : XLForm_2_br<19, 528, 0, (outs), (ins pred:$cond),
1584                               "b${cond:cc}ctr${cond:pm} ${cond:reg}", IIC_BrB,
1585                               []>;
1586
1587      def BCCTR :  XLForm_2_br2<19, 528, 12, 0, (outs), (ins crbitrc:$bi),
1588                                "bcctr 12, $bi, 0", IIC_BrB, []>;
1589      def BCCTRn : XLForm_2_br2<19, 528, 4, 0, (outs), (ins crbitrc:$bi),
1590                                "bcctr 4, $bi, 0", IIC_BrB, []>;
1591    }
1592  }
1593}
1594
1595// Set the float rounding mode.
1596let Uses = [RM], Defs = [RM] in {
1597def SETRNDi : PPCCustomInserterPseudo<(outs f8rc:$FRT), (ins u2imm:$RND),
1598                    "#SETRNDi", [(set f64:$FRT, (int_ppc_setrnd (i32 imm:$RND)))]>;
1599
1600def SETRND : PPCCustomInserterPseudo<(outs f8rc:$FRT), (ins gprc:$in),
1601                    "#SETRND", [(set f64:$FRT, (int_ppc_setrnd gprc :$in))]>;
1602
1603def SETFLM : PPCCustomInserterPseudo<(outs f8rc:$FRT), (ins f8rc:$FLM),
1604                    "#SETFLM", [(set f64:$FRT, (int_ppc_setflm f8rc:$FLM))]>;
1605}
1606
1607let Defs = [LR] in
1608  def MovePCtoLR : PPCEmitTimePseudo<(outs), (ins), "#MovePCtoLR", []>,
1609                   PPC970_Unit_BRU;
1610let Defs = [LR] in
1611  def MoveGOTtoLR : PPCEmitTimePseudo<(outs), (ins), "#MoveGOTtoLR", []>,
1612                    PPC970_Unit_BRU;
1613
1614let isBranch = 1, isTerminator = 1, hasCtrlDep = 1, PPC970_Unit = 7 in {
1615  let isBarrier = 1 in {
1616    let isPredicable = 1 in
1617      def B : IForm<18, 0, 0, (outs), (ins directbrtarget:$dst),
1618                    "b $dst", IIC_BrB,
1619                    [(br bb:$dst)]>;
1620  def BA  : IForm<18, 1, 0, (outs), (ins absdirectbrtarget:$dst),
1621                  "ba $dst", IIC_BrB, []>;
1622  }
1623
1624  // BCC represents an arbitrary conditional branch on a predicate.
1625  // FIXME: should be able to write a pattern for PPCcondbranch, but can't use
1626  // a two-value operand where a dag node expects two operands. :(
1627  let isCodeGenOnly = 1 in {
1628    class BCC_class : BForm<16, 0, 0, (outs), (ins pred:$cond, condbrtarget:$dst),
1629                            "b${cond:cc}${cond:pm} ${cond:reg}, $dst"
1630                            /*[(PPCcondbranch crrc:$crS, imm:$opc, bb:$dst)]*/>;
1631    def BCC : BCC_class;
1632
1633    // The same as BCC, except that it's not a terminator. Used for introducing
1634    // control flow dependency without creating new blocks.
1635    let isTerminator = 0 in def CTRL_DEP : BCC_class;
1636
1637    def BCCA : BForm<16, 1, 0, (outs), (ins pred:$cond, abscondbrtarget:$dst),
1638                     "b${cond:cc}a${cond:pm} ${cond:reg}, $dst">;
1639
1640    let isReturn = 1, Uses = [LR, RM] in
1641    def BCCLR : XLForm_2_br<19, 16, 0, (outs), (ins pred:$cond),
1642                           "b${cond:cc}lr${cond:pm} ${cond:reg}", IIC_BrB, []>;
1643  }
1644
1645  let isCodeGenOnly = 1 in {
1646    let Pattern = [(brcond i1:$bi, bb:$dst)] in
1647    def BC  : BForm_4<16, 12, 0, 0, (outs), (ins crbitrc:$bi, condbrtarget:$dst),
1648             "bc 12, $bi, $dst">;
1649
1650    let Pattern = [(brcond (not i1:$bi), bb:$dst)] in
1651    def BCn : BForm_4<16, 4, 0, 0, (outs), (ins crbitrc:$bi, condbrtarget:$dst),
1652             "bc 4, $bi, $dst">;
1653
1654    let isReturn = 1, Uses = [LR, RM] in {
1655    def BCLR  : XLForm_2_br2<19, 16, 12, 0, (outs), (ins crbitrc:$bi),
1656                             "bclr 12, $bi, 0", IIC_BrB, []>;
1657    def BCLRn : XLForm_2_br2<19, 16, 4, 0, (outs), (ins crbitrc:$bi),
1658                             "bclr 4, $bi, 0", IIC_BrB, []>;
1659    }
1660  }
1661
1662  let isReturn = 1, Defs = [CTR], Uses = [CTR, LR, RM] in {
1663   def BDZLR  : XLForm_2_ext<19, 16, 18, 0, 0, (outs), (ins),
1664                             "bdzlr", IIC_BrB, []>;
1665   def BDNZLR : XLForm_2_ext<19, 16, 16, 0, 0, (outs), (ins),
1666                             "bdnzlr", IIC_BrB, []>;
1667   def BDZLRp : XLForm_2_ext<19, 16, 27, 0, 0, (outs), (ins),
1668                             "bdzlr+", IIC_BrB, []>;
1669   def BDNZLRp: XLForm_2_ext<19, 16, 25, 0, 0, (outs), (ins),
1670                             "bdnzlr+", IIC_BrB, []>;
1671   def BDZLRm : XLForm_2_ext<19, 16, 26, 0, 0, (outs), (ins),
1672                             "bdzlr-", IIC_BrB, []>;
1673   def BDNZLRm: XLForm_2_ext<19, 16, 24, 0, 0, (outs), (ins),
1674                             "bdnzlr-", IIC_BrB, []>;
1675  }
1676
1677  let Defs = [CTR], Uses = [CTR] in {
1678    def BDZ  : BForm_1<16, 18, 0, 0, (outs), (ins condbrtarget:$dst),
1679                       "bdz $dst">;
1680    def BDNZ : BForm_1<16, 16, 0, 0, (outs), (ins condbrtarget:$dst),
1681                       "bdnz $dst">;
1682    def BDZA  : BForm_1<16, 18, 1, 0, (outs), (ins abscondbrtarget:$dst),
1683                        "bdza $dst">;
1684    def BDNZA : BForm_1<16, 16, 1, 0, (outs), (ins abscondbrtarget:$dst),
1685                        "bdnza $dst">;
1686    def BDZp : BForm_1<16, 27, 0, 0, (outs), (ins condbrtarget:$dst),
1687                       "bdz+ $dst">;
1688    def BDNZp: BForm_1<16, 25, 0, 0, (outs), (ins condbrtarget:$dst),
1689                       "bdnz+ $dst">;
1690    def BDZAp : BForm_1<16, 27, 1, 0, (outs), (ins abscondbrtarget:$dst),
1691                        "bdza+ $dst">;
1692    def BDNZAp: BForm_1<16, 25, 1, 0, (outs), (ins abscondbrtarget:$dst),
1693                        "bdnza+ $dst">;
1694    def BDZm : BForm_1<16, 26, 0, 0, (outs), (ins condbrtarget:$dst),
1695                       "bdz- $dst">;
1696    def BDNZm: BForm_1<16, 24, 0, 0, (outs), (ins condbrtarget:$dst),
1697                       "bdnz- $dst">;
1698    def BDZAm : BForm_1<16, 26, 1, 0, (outs), (ins abscondbrtarget:$dst),
1699                        "bdza- $dst">;
1700    def BDNZAm: BForm_1<16, 24, 1, 0, (outs), (ins abscondbrtarget:$dst),
1701                        "bdnza- $dst">;
1702  }
1703}
1704
1705// The unconditional BCL used by the SjLj setjmp code.
1706let isCall = 1, hasCtrlDep = 1, isCodeGenOnly = 1, PPC970_Unit = 7 in {
1707  let Defs = [LR], Uses = [RM] in {
1708    def BCLalways  : BForm_2<16, 20, 31, 0, 1, (outs), (ins condbrtarget:$dst),
1709                            "bcl 20, 31, $dst">;
1710  }
1711}
1712
1713let isCall = 1, PPC970_Unit = 7, Defs = [LR] in {
1714  // Convenient aliases for call instructions
1715  let Uses = [RM] in {
1716    def BL  : IForm<18, 0, 1, (outs), (ins calltarget:$func),
1717                    "bl $func", IIC_BrB, []>;  // See Pat patterns below.
1718    def BLA : IForm<18, 1, 1, (outs), (ins abscalltarget:$func),
1719                    "bla $func", IIC_BrB, [(PPCcall (i32 imm:$func))]>;
1720
1721    let isCodeGenOnly = 1 in {
1722      def BL_TLS  : IForm<18, 0, 1, (outs), (ins tlscall32:$func),
1723                          "bl $func", IIC_BrB, []>;
1724      def BCCL : BForm<16, 0, 1, (outs), (ins pred:$cond, condbrtarget:$dst),
1725                       "b${cond:cc}l${cond:pm} ${cond:reg}, $dst">;
1726      def BCCLA : BForm<16, 1, 1, (outs), (ins pred:$cond, abscondbrtarget:$dst),
1727                        "b${cond:cc}la${cond:pm} ${cond:reg}, $dst">;
1728
1729      def BCL  : BForm_4<16, 12, 0, 1, (outs),
1730                         (ins crbitrc:$bi, condbrtarget:$dst),
1731                         "bcl 12, $bi, $dst">;
1732      def BCLn : BForm_4<16, 4, 0, 1, (outs),
1733                         (ins crbitrc:$bi, condbrtarget:$dst),
1734                         "bcl 4, $bi, $dst">;
1735      def BL_NOP  : IForm_and_DForm_4_zero<18, 0, 1, 24,
1736                                           (outs), (ins calltarget:$func),
1737                                           "bl $func\n\tnop", IIC_BrB, []>;
1738    }
1739  }
1740  let Uses = [CTR, RM] in {
1741    let isPredicable = 1 in
1742      def BCTRL : XLForm_2_ext<19, 528, 20, 0, 1, (outs), (ins),
1743                              "bctrl", IIC_BrB, [(PPCbctrl)]>,
1744                  Requires<[In32BitMode]>;
1745
1746    let isCodeGenOnly = 1 in {
1747      def BCCCTRL : XLForm_2_br<19, 528, 1, (outs), (ins pred:$cond),
1748                                "b${cond:cc}ctrl${cond:pm} ${cond:reg}", IIC_BrB,
1749                                []>;
1750
1751      def BCCTRL  : XLForm_2_br2<19, 528, 12, 1, (outs), (ins crbitrc:$bi),
1752                                 "bcctrl 12, $bi, 0", IIC_BrB, []>;
1753      def BCCTRLn : XLForm_2_br2<19, 528, 4, 1, (outs), (ins crbitrc:$bi),
1754                                 "bcctrl 4, $bi, 0", IIC_BrB, []>;
1755    }
1756  }
1757  let Uses = [LR, RM] in {
1758    def BLRL : XLForm_2_ext<19, 16, 20, 0, 1, (outs), (ins),
1759                            "blrl", IIC_BrB, []>;
1760
1761    let isCodeGenOnly = 1 in {
1762      def BCCLRL : XLForm_2_br<19, 16, 1, (outs), (ins pred:$cond),
1763                              "b${cond:cc}lrl${cond:pm} ${cond:reg}", IIC_BrB,
1764                              []>;
1765
1766      def BCLRL  : XLForm_2_br2<19, 16, 12, 1, (outs), (ins crbitrc:$bi),
1767                                "bclrl 12, $bi, 0", IIC_BrB, []>;
1768      def BCLRLn : XLForm_2_br2<19, 16, 4, 1, (outs), (ins crbitrc:$bi),
1769                                "bclrl 4, $bi, 0", IIC_BrB, []>;
1770    }
1771  }
1772  let Defs = [CTR], Uses = [CTR, RM] in {
1773    def BDZL  : BForm_1<16, 18, 0, 1, (outs), (ins condbrtarget:$dst),
1774                        "bdzl $dst">;
1775    def BDNZL : BForm_1<16, 16, 0, 1, (outs), (ins condbrtarget:$dst),
1776                        "bdnzl $dst">;
1777    def BDZLA  : BForm_1<16, 18, 1, 1, (outs), (ins abscondbrtarget:$dst),
1778                         "bdzla $dst">;
1779    def BDNZLA : BForm_1<16, 16, 1, 1, (outs), (ins abscondbrtarget:$dst),
1780                         "bdnzla $dst">;
1781    def BDZLp : BForm_1<16, 27, 0, 1, (outs), (ins condbrtarget:$dst),
1782                        "bdzl+ $dst">;
1783    def BDNZLp: BForm_1<16, 25, 0, 1, (outs), (ins condbrtarget:$dst),
1784                        "bdnzl+ $dst">;
1785    def BDZLAp : BForm_1<16, 27, 1, 1, (outs), (ins abscondbrtarget:$dst),
1786                         "bdzla+ $dst">;
1787    def BDNZLAp: BForm_1<16, 25, 1, 1, (outs), (ins abscondbrtarget:$dst),
1788                         "bdnzla+ $dst">;
1789    def BDZLm : BForm_1<16, 26, 0, 1, (outs), (ins condbrtarget:$dst),
1790                        "bdzl- $dst">;
1791    def BDNZLm: BForm_1<16, 24, 0, 1, (outs), (ins condbrtarget:$dst),
1792                        "bdnzl- $dst">;
1793    def BDZLAm : BForm_1<16, 26, 1, 1, (outs), (ins abscondbrtarget:$dst),
1794                         "bdzla- $dst">;
1795    def BDNZLAm: BForm_1<16, 24, 1, 1, (outs), (ins abscondbrtarget:$dst),
1796                         "bdnzla- $dst">;
1797  }
1798  let Defs = [CTR], Uses = [CTR, LR, RM] in {
1799    def BDZLRL  : XLForm_2_ext<19, 16, 18, 0, 1, (outs), (ins),
1800                               "bdzlrl", IIC_BrB, []>;
1801    def BDNZLRL : XLForm_2_ext<19, 16, 16, 0, 1, (outs), (ins),
1802                               "bdnzlrl", IIC_BrB, []>;
1803    def BDZLRLp : XLForm_2_ext<19, 16, 27, 0, 1, (outs), (ins),
1804                               "bdzlrl+", IIC_BrB, []>;
1805    def BDNZLRLp: XLForm_2_ext<19, 16, 25, 0, 1, (outs), (ins),
1806                               "bdnzlrl+", IIC_BrB, []>;
1807    def BDZLRLm : XLForm_2_ext<19, 16, 26, 0, 1, (outs), (ins),
1808                               "bdzlrl-", IIC_BrB, []>;
1809    def BDNZLRLm: XLForm_2_ext<19, 16, 24, 0, 1, (outs), (ins),
1810                               "bdnzlrl-", IIC_BrB, []>;
1811  }
1812}
1813
1814let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1, Uses = [RM] in
1815def TCRETURNdi :PPCEmitTimePseudo< (outs),
1816                        (ins calltarget:$dst, i32imm:$offset),
1817                 "#TC_RETURNd $dst $offset",
1818                 []>;
1819
1820
1821let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1, Uses = [RM] in
1822def TCRETURNai :PPCEmitTimePseudo<(outs), (ins abscalltarget:$func, i32imm:$offset),
1823                 "#TC_RETURNa $func $offset",
1824                 [(PPCtc_return (i32 imm:$func), imm:$offset)]>;
1825
1826let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1, Uses = [RM] in
1827def TCRETURNri : PPCEmitTimePseudo<(outs), (ins CTRRC:$dst, i32imm:$offset),
1828                 "#TC_RETURNr $dst $offset",
1829                 []>;
1830
1831let isCall = 1, PPC970_Unit = 7, isCodeGenOnly = 1,
1832    Defs = [LR, R2], Uses = [CTR, RM], RST = 2 in {
1833  def BCTRL_LWZinto_toc:
1834    XLForm_2_ext_and_DForm_1<19, 528, 20, 0, 1, 32, (outs),
1835     (ins memri:$src), "bctrl\n\tlwz 2, $src", IIC_BrB,
1836     [(PPCbctrl_load_toc iaddr:$src)]>, Requires<[In32BitMode]>;
1837
1838}
1839
1840
1841let isCodeGenOnly = 1 in {
1842
1843let isTerminator = 1, isBarrier = 1, PPC970_Unit = 7, isBranch = 1,
1844    isIndirectBranch = 1, isCall = 1, isReturn = 1, Uses = [CTR, RM]  in
1845def TAILBCTR : XLForm_2_ext<19, 528, 20, 0, 0, (outs), (ins), "bctr", IIC_BrB,
1846                            []>, Requires<[In32BitMode]>;
1847
1848let isBranch = 1, isTerminator = 1, hasCtrlDep = 1, PPC970_Unit = 7,
1849    isBarrier = 1, isCall = 1, isReturn = 1, Uses = [RM] in
1850def TAILB   : IForm<18, 0, 0, (outs), (ins calltarget:$dst),
1851                  "b $dst", IIC_BrB,
1852                  []>;
1853
1854let isBranch = 1, isTerminator = 1, hasCtrlDep = 1, PPC970_Unit = 7,
1855    isBarrier = 1, isCall = 1, isReturn = 1, Uses = [RM] in
1856def TAILBA   : IForm<18, 0, 0, (outs), (ins abscalltarget:$dst),
1857                  "ba $dst", IIC_BrB,
1858                  []>;
1859
1860}
1861
1862// While longjmp is a control-flow barrier (fallthrough isn't allowed), setjmp
1863// is not.
1864let hasSideEffects = 1 in {
1865  let Defs = [CTR] in
1866  def EH_SjLj_SetJmp32  : PPCCustomInserterPseudo<(outs gprc:$dst), (ins memr:$buf),
1867                            "#EH_SJLJ_SETJMP32",
1868                            [(set i32:$dst, (PPCeh_sjlj_setjmp addr:$buf))]>,
1869                          Requires<[In32BitMode]>;
1870}
1871
1872let hasSideEffects = 1, isBarrier = 1 in {
1873  let isTerminator = 1 in
1874  def EH_SjLj_LongJmp32 : PPCCustomInserterPseudo<(outs), (ins memr:$buf),
1875                            "#EH_SJLJ_LONGJMP32",
1876                            [(PPCeh_sjlj_longjmp addr:$buf)]>,
1877                          Requires<[In32BitMode]>;
1878}
1879
1880// This pseudo is never removed from the function, as it serves as
1881// a terminator.  Size is set to 0 to prevent the builtin assembler
1882// from emitting it.
1883let isBranch = 1, isTerminator = 1, Size = 0 in {
1884  def EH_SjLj_Setup : PPCEmitTimePseudo<(outs), (ins directbrtarget:$dst),
1885                        "#EH_SjLj_Setup\t$dst", []>;
1886}
1887
1888// System call.
1889let PPC970_Unit = 7 in {
1890  def SC     : SCForm<17, 1, (outs), (ins i32imm:$lev),
1891                      "sc $lev", IIC_BrB, [(PPCsc (i32 imm:$lev))]>;
1892}
1893
1894// Branch history rolling buffer.
1895def CLRBHRB : XForm_0<31, 430, (outs), (ins), "clrbhrb", IIC_BrB,
1896                      [(PPCclrbhrb)]>,
1897                      PPC970_DGroup_Single;
1898// The $dmy argument used for MFBHRBE is not needed; however, including
1899// it avoids automatic generation of PPCFastISel::fastEmit_i(), which
1900// interferes with necessary special handling (see PPCFastISel.cpp).
1901def MFBHRBE : XFXForm_3p<31, 302, (outs gprc:$rD),
1902                         (ins u10imm:$imm, u10imm:$dmy),
1903                         "mfbhrbe $rD, $imm", IIC_BrB,
1904                         [(set i32:$rD,
1905                               (PPCmfbhrbe imm:$imm, imm:$dmy))]>,
1906                         PPC970_DGroup_First;
1907
1908def RFEBB : XLForm_S<19, 146, (outs), (ins u1imm:$imm), "rfebb $imm",
1909                     IIC_BrB, [(PPCrfebb (i32 imm:$imm))]>,
1910                     PPC970_DGroup_Single;
1911
1912def : InstAlias<"rfebb", (RFEBB 1)>;
1913
1914// DCB* instructions.
1915def DCBA   : DCB_Form<758, 0, (outs), (ins memrr:$dst), "dcba $dst",
1916                      IIC_LdStDCBF, [(int_ppc_dcba xoaddr:$dst)]>,
1917                      PPC970_DGroup_Single;
1918def DCBI   : DCB_Form<470, 0, (outs), (ins memrr:$dst), "dcbi $dst",
1919                      IIC_LdStDCBF, [(int_ppc_dcbi xoaddr:$dst)]>,
1920                      PPC970_DGroup_Single;
1921def DCBST  : DCB_Form<54, 0, (outs), (ins memrr:$dst), "dcbst $dst",
1922                      IIC_LdStDCBF, [(int_ppc_dcbst xoaddr:$dst)]>,
1923                      PPC970_DGroup_Single;
1924def DCBZ   : DCB_Form<1014, 0, (outs), (ins memrr:$dst), "dcbz $dst",
1925                      IIC_LdStDCBF, [(int_ppc_dcbz xoaddr:$dst)]>,
1926                      PPC970_DGroup_Single;
1927def DCBZL  : DCB_Form<1014, 1, (outs), (ins memrr:$dst), "dcbzl $dst",
1928                      IIC_LdStDCBF, [(int_ppc_dcbzl xoaddr:$dst)]>,
1929                      PPC970_DGroup_Single;
1930
1931def DCBF   : DCB_Form_hint<86, (outs), (ins u3imm:$TH, memrr:$dst),
1932                      "dcbf $dst, $TH", IIC_LdStDCBF, []>,
1933                      PPC970_DGroup_Single;
1934
1935let hasSideEffects = 0, mayLoad = 1, mayStore = 1 in {
1936def DCBT   : DCB_Form_hint<278, (outs), (ins u5imm:$TH, memrr:$dst),
1937                      "dcbt $dst, $TH", IIC_LdStDCBF, []>,
1938                      PPC970_DGroup_Single;
1939def DCBTST : DCB_Form_hint<246, (outs), (ins u5imm:$TH, memrr:$dst),
1940                      "dcbtst $dst, $TH", IIC_LdStDCBF, []>,
1941                      PPC970_DGroup_Single;
1942} // hasSideEffects = 0
1943
1944def ICBLC  : XForm_icbt<31, 230, (outs), (ins u4imm:$CT, memrr:$src),
1945                       "icblc $CT, $src", IIC_LdStStore>, Requires<[HasICBT]>;
1946def ICBLQ  : XForm_icbt<31, 198, (outs), (ins u4imm:$CT, memrr:$src),
1947                       "icblq. $CT, $src", IIC_LdStLoad>, Requires<[HasICBT]>;
1948def ICBT  : XForm_icbt<31, 22, (outs), (ins u4imm:$CT, memrr:$src),
1949                       "icbt $CT, $src", IIC_LdStLoad>, Requires<[HasICBT]>;
1950def ICBTLS : XForm_icbt<31, 486, (outs), (ins u4imm:$CT, memrr:$src),
1951                       "icbtls $CT, $src", IIC_LdStLoad>, Requires<[HasICBT]>;
1952
1953def : Pat<(int_ppc_dcbt xoaddr:$dst),
1954          (DCBT 0, xoaddr:$dst)>;
1955def : Pat<(int_ppc_dcbtst xoaddr:$dst),
1956          (DCBTST 0, xoaddr:$dst)>;
1957def : Pat<(int_ppc_dcbf xoaddr:$dst),
1958          (DCBF 0, xoaddr:$dst)>;
1959
1960def : Pat<(prefetch xoaddr:$dst, (i32 0), imm, (i32 1)),
1961          (DCBT 0, xoaddr:$dst)>;   // data prefetch for loads
1962def : Pat<(prefetch xoaddr:$dst, (i32 1), imm, (i32 1)),
1963          (DCBTST 0, xoaddr:$dst)>; // data prefetch for stores
1964def : Pat<(prefetch xoaddr:$dst, (i32 0), imm, (i32 0)),
1965          (ICBT 0, xoaddr:$dst)>, Requires<[HasICBT]>; // inst prefetch (for read)
1966
1967def : Pat<(int_ppc_dcbt_with_hint xoaddr:$dst, i32:$TH),
1968          (DCBT i32:$TH, xoaddr:$dst)>;
1969def : Pat<(int_ppc_dcbtst_with_hint xoaddr:$dst, i32:$TH),
1970          (DCBTST i32:$TH, xoaddr:$dst)>;
1971
1972// Atomic operations
1973// FIXME: some of these might be used with constant operands. This will result
1974// in constant materialization instructions that may be redundant. We currently
1975// clean this up in PPCMIPeephole with calls to
1976// PPCInstrInfo::convertToImmediateForm() but we should probably not emit them
1977// in the first place.
1978let Defs = [CR0] in {
1979  def ATOMIC_LOAD_ADD_I8 : PPCCustomInserterPseudo<
1980    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_ADD_I8",
1981    [(set i32:$dst, (atomic_load_add_8 xoaddr:$ptr, i32:$incr))]>;
1982  def ATOMIC_LOAD_SUB_I8 : PPCCustomInserterPseudo<
1983    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_SUB_I8",
1984    [(set i32:$dst, (atomic_load_sub_8 xoaddr:$ptr, i32:$incr))]>;
1985  def ATOMIC_LOAD_AND_I8 : PPCCustomInserterPseudo<
1986    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_AND_I8",
1987    [(set i32:$dst, (atomic_load_and_8 xoaddr:$ptr, i32:$incr))]>;
1988  def ATOMIC_LOAD_OR_I8 : PPCCustomInserterPseudo<
1989    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_OR_I8",
1990    [(set i32:$dst, (atomic_load_or_8 xoaddr:$ptr, i32:$incr))]>;
1991  def ATOMIC_LOAD_XOR_I8 : PPCCustomInserterPseudo<
1992    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "ATOMIC_LOAD_XOR_I8",
1993    [(set i32:$dst, (atomic_load_xor_8 xoaddr:$ptr, i32:$incr))]>;
1994  def ATOMIC_LOAD_NAND_I8 : PPCCustomInserterPseudo<
1995    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_NAND_I8",
1996    [(set i32:$dst, (atomic_load_nand_8 xoaddr:$ptr, i32:$incr))]>;
1997  def ATOMIC_LOAD_MIN_I8 : PPCCustomInserterPseudo<
1998    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_MIN_I8",
1999    [(set i32:$dst, (atomic_load_min_8 xoaddr:$ptr, i32:$incr))]>;
2000  def ATOMIC_LOAD_MAX_I8 : PPCCustomInserterPseudo<
2001    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_MAX_I8",
2002    [(set i32:$dst, (atomic_load_max_8 xoaddr:$ptr, i32:$incr))]>;
2003  def ATOMIC_LOAD_UMIN_I8 : PPCCustomInserterPseudo<
2004    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_UMIN_I8",
2005    [(set i32:$dst, (atomic_load_umin_8 xoaddr:$ptr, i32:$incr))]>;
2006  def ATOMIC_LOAD_UMAX_I8 : PPCCustomInserterPseudo<
2007    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_UMAX_I8",
2008    [(set i32:$dst, (atomic_load_umax_8 xoaddr:$ptr, i32:$incr))]>;
2009  def ATOMIC_LOAD_ADD_I16 : PPCCustomInserterPseudo<
2010    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_ADD_I16",
2011    [(set i32:$dst, (atomic_load_add_16 xoaddr:$ptr, i32:$incr))]>;
2012  def ATOMIC_LOAD_SUB_I16 : PPCCustomInserterPseudo<
2013    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_SUB_I16",
2014    [(set i32:$dst, (atomic_load_sub_16 xoaddr:$ptr, i32:$incr))]>;
2015  def ATOMIC_LOAD_AND_I16 : PPCCustomInserterPseudo<
2016    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_AND_I16",
2017    [(set i32:$dst, (atomic_load_and_16 xoaddr:$ptr, i32:$incr))]>;
2018  def ATOMIC_LOAD_OR_I16 : PPCCustomInserterPseudo<
2019    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_OR_I16",
2020    [(set i32:$dst, (atomic_load_or_16 xoaddr:$ptr, i32:$incr))]>;
2021  def ATOMIC_LOAD_XOR_I16 : PPCCustomInserterPseudo<
2022    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_XOR_I16",
2023    [(set i32:$dst, (atomic_load_xor_16 xoaddr:$ptr, i32:$incr))]>;
2024  def ATOMIC_LOAD_NAND_I16 : PPCCustomInserterPseudo<
2025    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_NAND_I16",
2026    [(set i32:$dst, (atomic_load_nand_16 xoaddr:$ptr, i32:$incr))]>;
2027  def ATOMIC_LOAD_MIN_I16 : PPCCustomInserterPseudo<
2028    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_MIN_I16",
2029    [(set i32:$dst, (atomic_load_min_16 xoaddr:$ptr, i32:$incr))]>;
2030  def ATOMIC_LOAD_MAX_I16 : PPCCustomInserterPseudo<
2031    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_MAX_I16",
2032    [(set i32:$dst, (atomic_load_max_16 xoaddr:$ptr, i32:$incr))]>;
2033  def ATOMIC_LOAD_UMIN_I16 : PPCCustomInserterPseudo<
2034    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_UMIN_I16",
2035    [(set i32:$dst, (atomic_load_umin_16 xoaddr:$ptr, i32:$incr))]>;
2036  def ATOMIC_LOAD_UMAX_I16 : PPCCustomInserterPseudo<
2037    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_UMAX_I16",
2038    [(set i32:$dst, (atomic_load_umax_16 xoaddr:$ptr, i32:$incr))]>;
2039  def ATOMIC_LOAD_ADD_I32 : PPCCustomInserterPseudo<
2040    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_ADD_I32",
2041    [(set i32:$dst, (atomic_load_add_32 xoaddr:$ptr, i32:$incr))]>;
2042  def ATOMIC_LOAD_SUB_I32 : PPCCustomInserterPseudo<
2043    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_SUB_I32",
2044    [(set i32:$dst, (atomic_load_sub_32 xoaddr:$ptr, i32:$incr))]>;
2045  def ATOMIC_LOAD_AND_I32 : PPCCustomInserterPseudo<
2046    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_AND_I32",
2047    [(set i32:$dst, (atomic_load_and_32 xoaddr:$ptr, i32:$incr))]>;
2048  def ATOMIC_LOAD_OR_I32 : PPCCustomInserterPseudo<
2049    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_OR_I32",
2050    [(set i32:$dst, (atomic_load_or_32 xoaddr:$ptr, i32:$incr))]>;
2051  def ATOMIC_LOAD_XOR_I32 : PPCCustomInserterPseudo<
2052    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_XOR_I32",
2053    [(set i32:$dst, (atomic_load_xor_32 xoaddr:$ptr, i32:$incr))]>;
2054  def ATOMIC_LOAD_NAND_I32 : PPCCustomInserterPseudo<
2055    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_NAND_I32",
2056    [(set i32:$dst, (atomic_load_nand_32 xoaddr:$ptr, i32:$incr))]>;
2057  def ATOMIC_LOAD_MIN_I32 : PPCCustomInserterPseudo<
2058    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_MIN_I32",
2059    [(set i32:$dst, (atomic_load_min_32 xoaddr:$ptr, i32:$incr))]>;
2060  def ATOMIC_LOAD_MAX_I32 : PPCCustomInserterPseudo<
2061    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_MAX_I32",
2062    [(set i32:$dst, (atomic_load_max_32 xoaddr:$ptr, i32:$incr))]>;
2063  def ATOMIC_LOAD_UMIN_I32 : PPCCustomInserterPseudo<
2064    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_UMIN_I32",
2065    [(set i32:$dst, (atomic_load_umin_32 xoaddr:$ptr, i32:$incr))]>;
2066  def ATOMIC_LOAD_UMAX_I32 : PPCCustomInserterPseudo<
2067    (outs gprc:$dst), (ins memrr:$ptr, gprc:$incr), "#ATOMIC_LOAD_UMAX_I32",
2068    [(set i32:$dst, (atomic_load_umax_32 xoaddr:$ptr, i32:$incr))]>;
2069
2070  def ATOMIC_CMP_SWAP_I8 : PPCCustomInserterPseudo<
2071    (outs gprc:$dst), (ins memrr:$ptr, gprc:$old, gprc:$new), "#ATOMIC_CMP_SWAP_I8",
2072    [(set i32:$dst, (atomic_cmp_swap_8 xoaddr:$ptr, i32:$old, i32:$new))]>;
2073  def ATOMIC_CMP_SWAP_I16 : PPCCustomInserterPseudo<
2074    (outs gprc:$dst), (ins memrr:$ptr, gprc:$old, gprc:$new), "#ATOMIC_CMP_SWAP_I16 $dst $ptr $old $new",
2075    [(set i32:$dst, (atomic_cmp_swap_16 xoaddr:$ptr, i32:$old, i32:$new))]>;
2076  def ATOMIC_CMP_SWAP_I32 : PPCCustomInserterPseudo<
2077    (outs gprc:$dst), (ins memrr:$ptr, gprc:$old, gprc:$new), "#ATOMIC_CMP_SWAP_I32 $dst $ptr $old $new",
2078    [(set i32:$dst, (atomic_cmp_swap_32 xoaddr:$ptr, i32:$old, i32:$new))]>;
2079
2080  def ATOMIC_SWAP_I8 : PPCCustomInserterPseudo<
2081    (outs gprc:$dst), (ins memrr:$ptr, gprc:$new), "#ATOMIC_SWAP_i8",
2082    [(set i32:$dst, (atomic_swap_8 xoaddr:$ptr, i32:$new))]>;
2083  def ATOMIC_SWAP_I16 : PPCCustomInserterPseudo<
2084    (outs gprc:$dst), (ins memrr:$ptr, gprc:$new), "#ATOMIC_SWAP_I16",
2085    [(set i32:$dst, (atomic_swap_16 xoaddr:$ptr, i32:$new))]>;
2086  def ATOMIC_SWAP_I32 : PPCCustomInserterPseudo<
2087    (outs gprc:$dst), (ins memrr:$ptr, gprc:$new), "#ATOMIC_SWAP_I32",
2088    [(set i32:$dst, (atomic_swap_32 xoaddr:$ptr, i32:$new))]>;
2089}
2090
2091def : Pat<(PPCatomicCmpSwap_8 xoaddr:$ptr, i32:$old, i32:$new),
2092        (ATOMIC_CMP_SWAP_I8 xoaddr:$ptr, i32:$old, i32:$new)>;
2093def : Pat<(PPCatomicCmpSwap_16 xoaddr:$ptr, i32:$old, i32:$new),
2094        (ATOMIC_CMP_SWAP_I16 xoaddr:$ptr, i32:$old, i32:$new)>;
2095
2096// Instructions to support atomic operations
2097let mayLoad = 1, mayStore = 0, hasSideEffects = 0 in {
2098def LBARX : XForm_1_memOp<31,  52, (outs gprc:$rD), (ins memrr:$src),
2099                    "lbarx $rD, $src", IIC_LdStLWARX, []>,
2100                    Requires<[HasPartwordAtomics]>;
2101
2102def LHARX : XForm_1_memOp<31,  116, (outs gprc:$rD), (ins memrr:$src),
2103                    "lharx $rD, $src", IIC_LdStLWARX, []>,
2104                    Requires<[HasPartwordAtomics]>;
2105
2106def LWARX : XForm_1_memOp<31,  20, (outs gprc:$rD), (ins memrr:$src),
2107                    "lwarx $rD, $src", IIC_LdStLWARX, []>;
2108
2109// Instructions to support lock versions of atomics
2110// (EH=1 - see Power ISA 2.07 Book II 4.4.2)
2111def LBARXL : XForm_1_memOp<31,  52, (outs gprc:$rD), (ins memrr:$src),
2112                     "lbarx $rD, $src, 1", IIC_LdStLWARX, []>, isRecordForm,
2113                     Requires<[HasPartwordAtomics]>;
2114
2115def LHARXL : XForm_1_memOp<31,  116, (outs gprc:$rD), (ins memrr:$src),
2116                     "lharx $rD, $src, 1", IIC_LdStLWARX, []>, isRecordForm,
2117                     Requires<[HasPartwordAtomics]>;
2118
2119def LWARXL : XForm_1_memOp<31,  20, (outs gprc:$rD), (ins memrr:$src),
2120                     "lwarx $rD, $src, 1", IIC_LdStLWARX, []>, isRecordForm;
2121
2122// The atomic instructions use the destination register as well as the next one
2123// or two registers in order (modulo 31).
2124let hasExtraSrcRegAllocReq = 1 in
2125def LWAT : X_RD5_RS5_IM5<31, 582, (outs gprc:$rD), (ins gprc:$rA, u5imm:$FC),
2126                         "lwat $rD, $rA, $FC", IIC_LdStLoad>,
2127           Requires<[IsISA3_0]>;
2128}
2129
2130let Defs = [CR0], mayStore = 1, mayLoad = 0, hasSideEffects = 0 in {
2131def STBCX : XForm_1_memOp<31, 694, (outs), (ins gprc:$rS, memrr:$dst),
2132                    "stbcx. $rS, $dst", IIC_LdStSTWCX, []>,
2133                    isRecordForm, Requires<[HasPartwordAtomics]>;
2134
2135def STHCX : XForm_1_memOp<31, 726, (outs), (ins gprc:$rS, memrr:$dst),
2136                    "sthcx. $rS, $dst", IIC_LdStSTWCX, []>,
2137                    isRecordForm, Requires<[HasPartwordAtomics]>;
2138
2139def STWCX : XForm_1_memOp<31, 150, (outs), (ins gprc:$rS, memrr:$dst),
2140                    "stwcx. $rS, $dst", IIC_LdStSTWCX, []>, isRecordForm;
2141}
2142
2143let mayStore = 1, mayLoad = 0, hasSideEffects = 0 in
2144def STWAT : X_RD5_RS5_IM5<31, 710, (outs), (ins gprc:$rS, gprc:$rA, u5imm:$FC),
2145                          "stwat $rS, $rA, $FC", IIC_LdStStore>,
2146            Requires<[IsISA3_0]>;
2147
2148let isTerminator = 1, isBarrier = 1, hasCtrlDep = 1 in
2149def TRAP  : XForm_24<31, 4, (outs), (ins), "trap", IIC_LdStLoad, [(trap)]>;
2150
2151def TWI : DForm_base<3, (outs), (ins u5imm:$to, gprc:$rA, s16imm:$imm),
2152                     "twi $to, $rA, $imm", IIC_IntTrapW, []>;
2153def TW : XForm_1<31, 4, (outs), (ins u5imm:$to, gprc:$rA, gprc:$rB),
2154                 "tw $to, $rA, $rB", IIC_IntTrapW, []>;
2155def TDI : DForm_base<2, (outs), (ins u5imm:$to, g8rc:$rA, s16imm:$imm),
2156                     "tdi $to, $rA, $imm", IIC_IntTrapD, []>;
2157def TD : XForm_1<31, 68, (outs), (ins u5imm:$to, g8rc:$rA, g8rc:$rB),
2158                 "td $to, $rA, $rB", IIC_IntTrapD, []>;
2159
2160//===----------------------------------------------------------------------===//
2161// PPC32 Load Instructions.
2162//
2163
2164// Unindexed (r+i) Loads.
2165let PPC970_Unit = 2 in {
2166def LBZ : DForm_1<34, (outs gprc:$rD), (ins memri:$src),
2167                  "lbz $rD, $src", IIC_LdStLoad,
2168                  [(set i32:$rD, (zextloadi8 iaddr:$src))]>;
2169def LHA : DForm_1<42, (outs gprc:$rD), (ins memri:$src),
2170                  "lha $rD, $src", IIC_LdStLHA,
2171                  [(set i32:$rD, (sextloadi16 iaddr:$src))]>,
2172                  PPC970_DGroup_Cracked;
2173def LHZ : DForm_1<40, (outs gprc:$rD), (ins memri:$src),
2174                  "lhz $rD, $src", IIC_LdStLoad,
2175                  [(set i32:$rD, (zextloadi16 iaddr:$src))]>;
2176def LWZ : DForm_1<32, (outs gprc:$rD), (ins memri:$src),
2177                  "lwz $rD, $src", IIC_LdStLoad,
2178                  [(set i32:$rD, (load iaddr:$src))]>;
2179
2180let Predicates = [HasFPU] in {
2181def LFS : DForm_1<48, (outs f4rc:$rD), (ins memri:$src),
2182                  "lfs $rD, $src", IIC_LdStLFD,
2183                  [(set f32:$rD, (load iaddr:$src))]>;
2184def LFD : DForm_1<50, (outs f8rc:$rD), (ins memri:$src),
2185                  "lfd $rD, $src", IIC_LdStLFD,
2186                  [(set f64:$rD, (load iaddr:$src))]>;
2187}
2188
2189
2190// Unindexed (r+i) Loads with Update (preinc).
2191let mayLoad = 1, mayStore = 0, hasSideEffects = 0 in {
2192def LBZU : DForm_1<35, (outs gprc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr),
2193                   "lbzu $rD, $addr", IIC_LdStLoadUpd,
2194                   []>, RegConstraint<"$addr.reg = $ea_result">,
2195                   NoEncode<"$ea_result">;
2196
2197def LHAU : DForm_1<43, (outs gprc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr),
2198                   "lhau $rD, $addr", IIC_LdStLHAU,
2199                   []>, RegConstraint<"$addr.reg = $ea_result">,
2200                   NoEncode<"$ea_result">;
2201
2202def LHZU : DForm_1<41, (outs gprc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr),
2203                   "lhzu $rD, $addr", IIC_LdStLoadUpd,
2204                   []>, RegConstraint<"$addr.reg = $ea_result">,
2205                   NoEncode<"$ea_result">;
2206
2207def LWZU : DForm_1<33, (outs gprc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr),
2208                   "lwzu $rD, $addr", IIC_LdStLoadUpd,
2209                   []>, RegConstraint<"$addr.reg = $ea_result">,
2210                   NoEncode<"$ea_result">;
2211
2212let Predicates = [HasFPU] in {
2213def LFSU : DForm_1<49, (outs f4rc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr),
2214                  "lfsu $rD, $addr", IIC_LdStLFDU,
2215                  []>, RegConstraint<"$addr.reg = $ea_result">,
2216                   NoEncode<"$ea_result">;
2217
2218def LFDU : DForm_1<51, (outs f8rc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr),
2219                  "lfdu $rD, $addr", IIC_LdStLFDU,
2220                  []>, RegConstraint<"$addr.reg = $ea_result">,
2221                   NoEncode<"$ea_result">;
2222}
2223
2224
2225// Indexed (r+r) Loads with Update (preinc).
2226def LBZUX : XForm_1_memOp<31, 119, (outs gprc:$rD, ptr_rc_nor0:$ea_result),
2227                   (ins memrr:$addr),
2228                   "lbzux $rD, $addr", IIC_LdStLoadUpdX,
2229                   []>, RegConstraint<"$addr.ptrreg = $ea_result">,
2230                   NoEncode<"$ea_result">;
2231
2232def LHAUX : XForm_1_memOp<31, 375, (outs gprc:$rD, ptr_rc_nor0:$ea_result),
2233                   (ins memrr:$addr),
2234                   "lhaux $rD, $addr", IIC_LdStLHAUX,
2235                   []>, RegConstraint<"$addr.ptrreg = $ea_result">,
2236                   NoEncode<"$ea_result">;
2237
2238def LHZUX : XForm_1_memOp<31, 311, (outs gprc:$rD, ptr_rc_nor0:$ea_result),
2239                   (ins memrr:$addr),
2240                   "lhzux $rD, $addr", IIC_LdStLoadUpdX,
2241                   []>, RegConstraint<"$addr.ptrreg = $ea_result">,
2242                   NoEncode<"$ea_result">;
2243
2244def LWZUX : XForm_1_memOp<31, 55, (outs gprc:$rD, ptr_rc_nor0:$ea_result),
2245                   (ins memrr:$addr),
2246                   "lwzux $rD, $addr", IIC_LdStLoadUpdX,
2247                   []>, RegConstraint<"$addr.ptrreg = $ea_result">,
2248                   NoEncode<"$ea_result">;
2249
2250let Predicates = [HasFPU] in {
2251def LFSUX : XForm_1_memOp<31, 567, (outs f4rc:$rD, ptr_rc_nor0:$ea_result),
2252                   (ins memrr:$addr),
2253                   "lfsux $rD, $addr", IIC_LdStLFDUX,
2254                   []>, RegConstraint<"$addr.ptrreg = $ea_result">,
2255                   NoEncode<"$ea_result">;
2256
2257def LFDUX : XForm_1_memOp<31, 631, (outs f8rc:$rD, ptr_rc_nor0:$ea_result),
2258                   (ins memrr:$addr),
2259                   "lfdux $rD, $addr", IIC_LdStLFDUX,
2260                   []>, RegConstraint<"$addr.ptrreg = $ea_result">,
2261                   NoEncode<"$ea_result">;
2262}
2263}
2264}
2265
2266// Indexed (r+r) Loads.
2267//
2268let PPC970_Unit = 2, mayLoad = 1, mayStore = 0 in {
2269def LBZX : XForm_1_memOp<31,  87, (outs gprc:$rD), (ins memrr:$src),
2270                   "lbzx $rD, $src", IIC_LdStLoad,
2271                   [(set i32:$rD, (zextloadi8 xaddr:$src))]>;
2272def LHAX : XForm_1_memOp<31, 343, (outs gprc:$rD), (ins memrr:$src),
2273                   "lhax $rD, $src", IIC_LdStLHA,
2274                   [(set i32:$rD, (sextloadi16 xaddr:$src))]>,
2275                   PPC970_DGroup_Cracked;
2276def LHZX : XForm_1_memOp<31, 279, (outs gprc:$rD), (ins memrr:$src),
2277                   "lhzx $rD, $src", IIC_LdStLoad,
2278                   [(set i32:$rD, (zextloadi16 xaddr:$src))]>;
2279def LWZX : XForm_1_memOp<31,  23, (outs gprc:$rD), (ins memrr:$src),
2280                   "lwzx $rD, $src", IIC_LdStLoad,
2281                   [(set i32:$rD, (load xaddr:$src))]>;
2282def LHBRX : XForm_1_memOp<31, 790, (outs gprc:$rD), (ins memrr:$src),
2283                   "lhbrx $rD, $src", IIC_LdStLoad,
2284                   [(set i32:$rD, (PPClbrx xoaddr:$src, i16))]>;
2285def LWBRX : XForm_1_memOp<31,  534, (outs gprc:$rD), (ins memrr:$src),
2286                   "lwbrx $rD, $src", IIC_LdStLoad,
2287                   [(set i32:$rD, (PPClbrx xoaddr:$src, i32))]>;
2288
2289let Predicates = [HasFPU] in {
2290def LFSX   : XForm_25_memOp<31, 535, (outs f4rc:$frD), (ins memrr:$src),
2291                      "lfsx $frD, $src", IIC_LdStLFD,
2292                      [(set f32:$frD, (load xaddr:$src))]>;
2293def LFDX   : XForm_25_memOp<31, 599, (outs f8rc:$frD), (ins memrr:$src),
2294                      "lfdx $frD, $src", IIC_LdStLFD,
2295                      [(set f64:$frD, (load xaddr:$src))]>;
2296
2297def LFIWAX : XForm_25_memOp<31, 855, (outs f8rc:$frD), (ins memrr:$src),
2298                      "lfiwax $frD, $src", IIC_LdStLFD,
2299                      [(set f64:$frD, (PPClfiwax xoaddr:$src))]>;
2300def LFIWZX : XForm_25_memOp<31, 887, (outs f8rc:$frD), (ins memrr:$src),
2301                      "lfiwzx $frD, $src", IIC_LdStLFD,
2302                      [(set f64:$frD, (PPClfiwzx xoaddr:$src))]>;
2303}
2304}
2305
2306// Load Multiple
2307let mayLoad = 1, mayStore = 0, hasSideEffects = 0 in
2308def LMW : DForm_1<46, (outs gprc:$rD), (ins memri:$src),
2309                  "lmw $rD, $src", IIC_LdStLMW, []>;
2310
2311//===----------------------------------------------------------------------===//
2312// PPC32 Store Instructions.
2313//
2314
2315// Unindexed (r+i) Stores.
2316let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in {
2317def STB  : DForm_1<38, (outs), (ins gprc:$rS, memri:$dst),
2318                   "stb $rS, $dst", IIC_LdStStore,
2319                   [(truncstorei8 i32:$rS, iaddr:$dst)]>;
2320def STH  : DForm_1<44, (outs), (ins gprc:$rS, memri:$dst),
2321                   "sth $rS, $dst", IIC_LdStStore,
2322                   [(truncstorei16 i32:$rS, iaddr:$dst)]>;
2323def STW  : DForm_1<36, (outs), (ins gprc:$rS, memri:$dst),
2324                   "stw $rS, $dst", IIC_LdStStore,
2325                   [(store i32:$rS, iaddr:$dst)]>;
2326let Predicates = [HasFPU] in {
2327def STFS : DForm_1<52, (outs), (ins f4rc:$rS, memri:$dst),
2328                   "stfs $rS, $dst", IIC_LdStSTFD,
2329                   [(store f32:$rS, iaddr:$dst)]>;
2330def STFD : DForm_1<54, (outs), (ins f8rc:$rS, memri:$dst),
2331                   "stfd $rS, $dst", IIC_LdStSTFD,
2332                   [(store f64:$rS, iaddr:$dst)]>;
2333}
2334}
2335
2336// Unindexed (r+i) Stores with Update (preinc).
2337let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in {
2338def STBU  : DForm_1<39, (outs ptr_rc_nor0:$ea_res), (ins gprc:$rS, memri:$dst),
2339                    "stbu $rS, $dst", IIC_LdStSTU, []>,
2340                    RegConstraint<"$dst.reg = $ea_res">, NoEncode<"$ea_res">;
2341def STHU  : DForm_1<45, (outs ptr_rc_nor0:$ea_res), (ins gprc:$rS, memri:$dst),
2342                    "sthu $rS, $dst", IIC_LdStSTU, []>,
2343                    RegConstraint<"$dst.reg = $ea_res">, NoEncode<"$ea_res">;
2344def STWU  : DForm_1<37, (outs ptr_rc_nor0:$ea_res), (ins gprc:$rS, memri:$dst),
2345                    "stwu $rS, $dst", IIC_LdStSTU, []>,
2346                    RegConstraint<"$dst.reg = $ea_res">, NoEncode<"$ea_res">;
2347let Predicates = [HasFPU] in {
2348def STFSU : DForm_1<53, (outs ptr_rc_nor0:$ea_res), (ins f4rc:$rS, memri:$dst),
2349                    "stfsu $rS, $dst", IIC_LdStSTFDU, []>,
2350                    RegConstraint<"$dst.reg = $ea_res">, NoEncode<"$ea_res">;
2351def STFDU : DForm_1<55, (outs ptr_rc_nor0:$ea_res), (ins f8rc:$rS, memri:$dst),
2352                    "stfdu $rS, $dst", IIC_LdStSTFDU, []>,
2353                    RegConstraint<"$dst.reg = $ea_res">, NoEncode<"$ea_res">;
2354}
2355}
2356
2357// Patterns to match the pre-inc stores.  We can't put the patterns on
2358// the instruction definitions directly as ISel wants the address base
2359// and offset to be separate operands, not a single complex operand.
2360def : Pat<(pre_truncsti8 i32:$rS, iPTR:$ptrreg, iaddroff:$ptroff),
2361          (STBU $rS, iaddroff:$ptroff, $ptrreg)>;
2362def : Pat<(pre_truncsti16 i32:$rS, iPTR:$ptrreg, iaddroff:$ptroff),
2363          (STHU $rS, iaddroff:$ptroff, $ptrreg)>;
2364def : Pat<(pre_store i32:$rS, iPTR:$ptrreg, iaddroff:$ptroff),
2365          (STWU $rS, iaddroff:$ptroff, $ptrreg)>;
2366def : Pat<(pre_store f32:$rS, iPTR:$ptrreg, iaddroff:$ptroff),
2367          (STFSU $rS, iaddroff:$ptroff, $ptrreg)>;
2368def : Pat<(pre_store f64:$rS, iPTR:$ptrreg, iaddroff:$ptroff),
2369          (STFDU $rS, iaddroff:$ptroff, $ptrreg)>;
2370
2371// Indexed (r+r) Stores.
2372let PPC970_Unit = 2 in {
2373def STBX  : XForm_8_memOp<31, 215, (outs), (ins gprc:$rS, memrr:$dst),
2374                   "stbx $rS, $dst", IIC_LdStStore,
2375                   [(truncstorei8 i32:$rS, xaddr:$dst)]>,
2376                   PPC970_DGroup_Cracked;
2377def STHX  : XForm_8_memOp<31, 407, (outs), (ins gprc:$rS, memrr:$dst),
2378                   "sthx $rS, $dst", IIC_LdStStore,
2379                   [(truncstorei16 i32:$rS, xaddr:$dst)]>,
2380                   PPC970_DGroup_Cracked;
2381def STWX  : XForm_8_memOp<31, 151, (outs), (ins gprc:$rS, memrr:$dst),
2382                   "stwx $rS, $dst", IIC_LdStStore,
2383                   [(store i32:$rS, xaddr:$dst)]>,
2384                   PPC970_DGroup_Cracked;
2385
2386def STHBRX: XForm_8_memOp<31, 918, (outs), (ins gprc:$rS, memrr:$dst),
2387                   "sthbrx $rS, $dst", IIC_LdStStore,
2388                   [(PPCstbrx i32:$rS, xoaddr:$dst, i16)]>,
2389                   PPC970_DGroup_Cracked;
2390def STWBRX: XForm_8_memOp<31, 662, (outs), (ins gprc:$rS, memrr:$dst),
2391                   "stwbrx $rS, $dst", IIC_LdStStore,
2392                   [(PPCstbrx i32:$rS, xoaddr:$dst, i32)]>,
2393                   PPC970_DGroup_Cracked;
2394
2395let Predicates = [HasFPU] in {
2396def STFIWX: XForm_28_memOp<31, 983, (outs), (ins f8rc:$frS, memrr:$dst),
2397                     "stfiwx $frS, $dst", IIC_LdStSTFD,
2398                     [(PPCstfiwx f64:$frS, xoaddr:$dst)]>;
2399
2400def STFSX : XForm_28_memOp<31, 663, (outs), (ins f4rc:$frS, memrr:$dst),
2401                     "stfsx $frS, $dst", IIC_LdStSTFD,
2402                     [(store f32:$frS, xaddr:$dst)]>;
2403def STFDX : XForm_28_memOp<31, 727, (outs), (ins f8rc:$frS, memrr:$dst),
2404                     "stfdx $frS, $dst", IIC_LdStSTFD,
2405                     [(store f64:$frS, xaddr:$dst)]>;
2406}
2407}
2408
2409// Indexed (r+r) Stores with Update (preinc).
2410let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in {
2411def STBUX : XForm_8_memOp<31, 247, (outs ptr_rc_nor0:$ea_res),
2412                          (ins gprc:$rS, memrr:$dst),
2413                          "stbux $rS, $dst", IIC_LdStSTUX, []>,
2414                          RegConstraint<"$dst.ptrreg = $ea_res">,
2415                          NoEncode<"$ea_res">,
2416                          PPC970_DGroup_Cracked;
2417def STHUX : XForm_8_memOp<31, 439, (outs ptr_rc_nor0:$ea_res),
2418                          (ins gprc:$rS, memrr:$dst),
2419                          "sthux $rS, $dst", IIC_LdStSTUX, []>,
2420                          RegConstraint<"$dst.ptrreg = $ea_res">,
2421                          NoEncode<"$ea_res">,
2422                          PPC970_DGroup_Cracked;
2423def STWUX : XForm_8_memOp<31, 183, (outs ptr_rc_nor0:$ea_res),
2424                          (ins gprc:$rS, memrr:$dst),
2425                          "stwux $rS, $dst", IIC_LdStSTUX, []>,
2426                          RegConstraint<"$dst.ptrreg = $ea_res">,
2427                          NoEncode<"$ea_res">,
2428                          PPC970_DGroup_Cracked;
2429let Predicates = [HasFPU] in {
2430def STFSUX: XForm_8_memOp<31, 695, (outs ptr_rc_nor0:$ea_res),
2431                          (ins f4rc:$rS, memrr:$dst),
2432                          "stfsux $rS, $dst", IIC_LdStSTFDU, []>,
2433                          RegConstraint<"$dst.ptrreg = $ea_res">,
2434                          NoEncode<"$ea_res">,
2435                          PPC970_DGroup_Cracked;
2436def STFDUX: XForm_8_memOp<31, 759, (outs ptr_rc_nor0:$ea_res),
2437                          (ins f8rc:$rS, memrr:$dst),
2438                          "stfdux $rS, $dst", IIC_LdStSTFDU, []>,
2439                          RegConstraint<"$dst.ptrreg = $ea_res">,
2440                          NoEncode<"$ea_res">,
2441                          PPC970_DGroup_Cracked;
2442}
2443}
2444
2445// Patterns to match the pre-inc stores.  We can't put the patterns on
2446// the instruction definitions directly as ISel wants the address base
2447// and offset to be separate operands, not a single complex operand.
2448def : Pat<(pre_truncsti8 i32:$rS, iPTR:$ptrreg, iPTR:$ptroff),
2449          (STBUX $rS, $ptrreg, $ptroff)>;
2450def : Pat<(pre_truncsti16 i32:$rS, iPTR:$ptrreg, iPTR:$ptroff),
2451          (STHUX $rS, $ptrreg, $ptroff)>;
2452def : Pat<(pre_store i32:$rS, iPTR:$ptrreg, iPTR:$ptroff),
2453          (STWUX $rS, $ptrreg, $ptroff)>;
2454let Predicates = [HasFPU] in {
2455def : Pat<(pre_store f32:$rS, iPTR:$ptrreg, iPTR:$ptroff),
2456          (STFSUX $rS, $ptrreg, $ptroff)>;
2457def : Pat<(pre_store f64:$rS, iPTR:$ptrreg, iPTR:$ptroff),
2458          (STFDUX $rS, $ptrreg, $ptroff)>;
2459}
2460
2461// Store Multiple
2462let mayStore = 1, mayLoad = 0, hasSideEffects = 0 in
2463def STMW : DForm_1<47, (outs), (ins gprc:$rS, memri:$dst),
2464                   "stmw $rS, $dst", IIC_LdStLMW, []>;
2465
2466def SYNC : XForm_24_sync<31, 598, (outs), (ins u2imm:$L),
2467                        "sync $L", IIC_LdStSync, []>;
2468
2469let isCodeGenOnly = 1 in {
2470  def MSYNC : XForm_24_sync<31, 598, (outs), (ins),
2471                           "msync", IIC_LdStSync, []> {
2472    let L = 0;
2473  }
2474}
2475
2476// We used to have EIEIO as value but E[0-9A-Z] is a reserved name
2477def EnforceIEIO : XForm_24_eieio<31, 854, (outs), (ins),
2478                                 "eieio", IIC_LdStLoad, []>;
2479
2480def : Pat<(int_ppc_sync),   (SYNC 0)>, Requires<[HasSYNC]>;
2481def : Pat<(int_ppc_lwsync), (SYNC 1)>, Requires<[HasSYNC]>;
2482def : Pat<(int_ppc_sync),   (MSYNC)>, Requires<[HasOnlyMSYNC]>;
2483def : Pat<(int_ppc_lwsync), (MSYNC)>, Requires<[HasOnlyMSYNC]>;
2484def : Pat<(int_ppc_eieio),  (EnforceIEIO)>;
2485
2486//===----------------------------------------------------------------------===//
2487// PPC32 Arithmetic Instructions.
2488//
2489
2490let PPC970_Unit = 1 in {  // FXU Operations.
2491def ADDI   : DForm_2<14, (outs gprc:$rD), (ins gprc_nor0:$rA, s16imm:$imm),
2492                     "addi $rD, $rA, $imm", IIC_IntSimple,
2493                     [(set i32:$rD, (add i32:$rA, imm32SExt16:$imm))]>;
2494let BaseName = "addic" in {
2495let Defs = [CARRY] in
2496def ADDIC  : DForm_2<12, (outs gprc:$rD), (ins gprc:$rA, s16imm:$imm),
2497                     "addic $rD, $rA, $imm", IIC_IntGeneral,
2498                     [(set i32:$rD, (addc i32:$rA, imm32SExt16:$imm))]>,
2499                     RecFormRel, PPC970_DGroup_Cracked;
2500let Defs = [CARRY, CR0] in
2501def ADDIC_rec : DForm_2<13, (outs gprc:$rD), (ins gprc:$rA, s16imm:$imm),
2502                     "addic. $rD, $rA, $imm", IIC_IntGeneral,
2503                     []>, isRecordForm, RecFormRel;
2504}
2505def ADDIS  : DForm_2<15, (outs gprc:$rD), (ins gprc_nor0:$rA, s17imm:$imm),
2506                     "addis $rD, $rA, $imm", IIC_IntSimple,
2507                     [(set i32:$rD, (add i32:$rA, imm16ShiftedSExt:$imm))]>;
2508let isCodeGenOnly = 1 in
2509def LA     : DForm_2<14, (outs gprc:$rD), (ins gprc_nor0:$rA, s16imm:$sym),
2510                     "la $rD, $sym($rA)", IIC_IntGeneral,
2511                     [(set i32:$rD, (add i32:$rA,
2512                                          (PPClo tglobaladdr:$sym, 0)))]>;
2513def MULLI  : DForm_2< 7, (outs gprc:$rD), (ins gprc:$rA, s16imm:$imm),
2514                     "mulli $rD, $rA, $imm", IIC_IntMulLI,
2515                     [(set i32:$rD, (mul i32:$rA, imm32SExt16:$imm))]>;
2516let Defs = [CARRY] in
2517def SUBFIC : DForm_2< 8, (outs gprc:$rD), (ins gprc:$rA, s16imm:$imm),
2518                     "subfic $rD, $rA, $imm", IIC_IntGeneral,
2519                     [(set i32:$rD, (subc imm32SExt16:$imm, i32:$rA))]>;
2520
2521let isReMaterializable = 1, isAsCheapAsAMove = 1, isMoveImm = 1 in {
2522  def LI  : DForm_2_r0<14, (outs gprc:$rD), (ins s16imm:$imm),
2523                       "li $rD, $imm", IIC_IntSimple,
2524                       [(set i32:$rD, imm32SExt16:$imm)]>;
2525  def LIS : DForm_2_r0<15, (outs gprc:$rD), (ins s17imm:$imm),
2526                       "lis $rD, $imm", IIC_IntSimple,
2527                       [(set i32:$rD, imm16ShiftedSExt:$imm)]>;
2528}
2529}
2530
2531def : InstAlias<"li $rD, $imm", (ADDI gprc:$rD, ZERO, s16imm:$imm)>;
2532def : InstAlias<"lis $rD, $imm", (ADDIS gprc:$rD, ZERO, s17imm:$imm)>;
2533
2534let PPC970_Unit = 1 in {  // FXU Operations.
2535let Defs = [CR0] in {
2536def ANDI_rec : DForm_4<28, (outs gprc:$dst), (ins gprc:$src1, u16imm:$src2),
2537                    "andi. $dst, $src1, $src2", IIC_IntGeneral,
2538                    [(set i32:$dst, (and i32:$src1, immZExt16:$src2))]>,
2539                    isRecordForm;
2540def ANDIS_rec : DForm_4<29, (outs gprc:$dst), (ins gprc:$src1, u16imm:$src2),
2541                    "andis. $dst, $src1, $src2", IIC_IntGeneral,
2542                    [(set i32:$dst, (and i32:$src1, imm16ShiftedZExt:$src2))]>,
2543                    isRecordForm;
2544}
2545def ORI   : DForm_4<24, (outs gprc:$dst), (ins gprc:$src1, u16imm:$src2),
2546                    "ori $dst, $src1, $src2", IIC_IntSimple,
2547                    [(set i32:$dst, (or i32:$src1, immZExt16:$src2))]>;
2548def ORIS  : DForm_4<25, (outs gprc:$dst), (ins gprc:$src1, u16imm:$src2),
2549                    "oris $dst, $src1, $src2", IIC_IntSimple,
2550                    [(set i32:$dst, (or i32:$src1, imm16ShiftedZExt:$src2))]>;
2551def XORI  : DForm_4<26, (outs gprc:$dst), (ins gprc:$src1, u16imm:$src2),
2552                    "xori $dst, $src1, $src2", IIC_IntSimple,
2553                    [(set i32:$dst, (xor i32:$src1, immZExt16:$src2))]>;
2554def XORIS : DForm_4<27, (outs gprc:$dst), (ins gprc:$src1, u16imm:$src2),
2555                    "xoris $dst, $src1, $src2", IIC_IntSimple,
2556                    [(set i32:$dst, (xor i32:$src1, imm16ShiftedZExt:$src2))]>;
2557
2558def NOP   : DForm_4_zero<24, (outs), (ins), "nop", IIC_IntSimple,
2559                         []>;
2560let isCodeGenOnly = 1 in {
2561// The POWER6 and POWER7 have special group-terminating nops.
2562def NOP_GT_PWR6 : DForm_4_fixedreg_zero<24, 1, (outs), (ins),
2563                                        "ori 1, 1, 0", IIC_IntSimple, []>;
2564def NOP_GT_PWR7 : DForm_4_fixedreg_zero<24, 2, (outs), (ins),
2565                                        "ori 2, 2, 0", IIC_IntSimple, []>;
2566}
2567
2568let isCompare = 1, hasSideEffects = 0 in {
2569  def CMPWI : DForm_5_ext<11, (outs crrc:$crD), (ins gprc:$rA, s16imm:$imm),
2570                          "cmpwi $crD, $rA, $imm", IIC_IntCompare>;
2571  def CMPLWI : DForm_6_ext<10, (outs crrc:$dst), (ins gprc:$src1, u16imm:$src2),
2572                           "cmplwi $dst, $src1, $src2", IIC_IntCompare>;
2573  def CMPRB  : X_BF3_L1_RS5_RS5<31, 192, (outs crbitrc:$BF),
2574                                (ins u1imm:$L, g8rc:$rA, g8rc:$rB),
2575                                "cmprb $BF, $L, $rA, $rB", IIC_IntCompare, []>,
2576               Requires<[IsISA3_0]>;
2577}
2578}
2579
2580let PPC970_Unit = 1, hasSideEffects = 0 in {  // FXU Operations.
2581let isCommutable = 1 in {
2582defm NAND : XForm_6r<31, 476, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2583                     "nand", "$rA, $rS, $rB", IIC_IntSimple,
2584                     [(set i32:$rA, (not (and i32:$rS, i32:$rB)))]>;
2585defm AND  : XForm_6r<31,  28, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2586                     "and", "$rA, $rS, $rB", IIC_IntSimple,
2587                     [(set i32:$rA, (and i32:$rS, i32:$rB))]>;
2588} // isCommutable
2589defm ANDC : XForm_6r<31,  60, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2590                     "andc", "$rA, $rS, $rB", IIC_IntSimple,
2591                     [(set i32:$rA, (and i32:$rS, (not i32:$rB)))]>;
2592let isCommutable = 1 in {
2593defm OR   : XForm_6r<31, 444, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2594                     "or", "$rA, $rS, $rB", IIC_IntSimple,
2595                     [(set i32:$rA, (or i32:$rS, i32:$rB))]>;
2596defm NOR  : XForm_6r<31, 124, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2597                     "nor", "$rA, $rS, $rB", IIC_IntSimple,
2598                     [(set i32:$rA, (not (or i32:$rS, i32:$rB)))]>;
2599} // isCommutable
2600defm ORC  : XForm_6r<31, 412, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2601                     "orc", "$rA, $rS, $rB", IIC_IntSimple,
2602                     [(set i32:$rA, (or i32:$rS, (not i32:$rB)))]>;
2603let isCommutable = 1 in {
2604defm EQV  : XForm_6r<31, 284, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2605                     "eqv", "$rA, $rS, $rB", IIC_IntSimple,
2606                     [(set i32:$rA, (not (xor i32:$rS, i32:$rB)))]>;
2607defm XOR  : XForm_6r<31, 316, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2608                     "xor", "$rA, $rS, $rB", IIC_IntSimple,
2609                     [(set i32:$rA, (xor i32:$rS, i32:$rB))]>;
2610} // isCommutable
2611defm SLW  : XForm_6r<31,  24, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2612                     "slw", "$rA, $rS, $rB", IIC_IntGeneral,
2613                     [(set i32:$rA, (PPCshl i32:$rS, i32:$rB))]>;
2614defm SRW  : XForm_6r<31, 536, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2615                     "srw", "$rA, $rS, $rB", IIC_IntGeneral,
2616                     [(set i32:$rA, (PPCsrl i32:$rS, i32:$rB))]>;
2617defm SRAW : XForm_6rc<31, 792, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2618                      "sraw", "$rA, $rS, $rB", IIC_IntShift,
2619                      [(set i32:$rA, (PPCsra i32:$rS, i32:$rB))]>;
2620}
2621
2622def : InstAlias<"mr $rA, $rB", (OR gprc:$rA, gprc:$rB, gprc:$rB)>;
2623def : InstAlias<"mr. $rA, $rB", (OR_rec gprc:$rA, gprc:$rB, gprc:$rB)>;
2624
2625def : InstAlias<"not $rA, $rS", (NOR gprc:$rA, gprc:$rS, gprc:$rS)>;
2626def : InstAlias<"not. $rA, $rS", (NOR_rec gprc:$rA, gprc:$rS, gprc:$rS)>;
2627
2628def : InstAlias<"nop", (ORI R0, R0, 0)>;
2629
2630let PPC970_Unit = 1 in {  // FXU Operations.
2631let hasSideEffects = 0 in {
2632defm SRAWI : XForm_10rc<31, 824, (outs gprc:$rA), (ins gprc:$rS, u5imm:$SH),
2633                        "srawi", "$rA, $rS, $SH", IIC_IntShift,
2634                        [(set i32:$rA, (sra i32:$rS, (i32 imm:$SH)))]>;
2635defm CNTLZW : XForm_11r<31,  26, (outs gprc:$rA), (ins gprc:$rS),
2636                        "cntlzw", "$rA, $rS", IIC_IntGeneral,
2637                        [(set i32:$rA, (ctlz i32:$rS))]>;
2638defm CNTTZW : XForm_11r<31, 538, (outs gprc:$rA), (ins gprc:$rS),
2639                        "cnttzw", "$rA, $rS", IIC_IntGeneral,
2640                        [(set i32:$rA, (cttz i32:$rS))]>, Requires<[IsISA3_0]>;
2641defm EXTSB  : XForm_11r<31, 954, (outs gprc:$rA), (ins gprc:$rS),
2642                        "extsb", "$rA, $rS", IIC_IntSimple,
2643                        [(set i32:$rA, (sext_inreg i32:$rS, i8))]>;
2644defm EXTSH  : XForm_11r<31, 922, (outs gprc:$rA), (ins gprc:$rS),
2645                        "extsh", "$rA, $rS", IIC_IntSimple,
2646                        [(set i32:$rA, (sext_inreg i32:$rS, i16))]>;
2647
2648let isCommutable = 1 in
2649def CMPB : XForm_6<31, 508, (outs gprc:$rA), (ins gprc:$rS, gprc:$rB),
2650                   "cmpb $rA, $rS, $rB", IIC_IntGeneral,
2651                   [(set i32:$rA, (PPCcmpb i32:$rS, i32:$rB))]>;
2652}
2653let isCompare = 1, hasSideEffects = 0 in {
2654  def CMPW   : XForm_16_ext<31, 0, (outs crrc:$crD), (ins gprc:$rA, gprc:$rB),
2655                            "cmpw $crD, $rA, $rB", IIC_IntCompare>;
2656  def CMPLW  : XForm_16_ext<31, 32, (outs crrc:$crD), (ins gprc:$rA, gprc:$rB),
2657                            "cmplw $crD, $rA, $rB", IIC_IntCompare>;
2658}
2659}
2660let PPC970_Unit = 3, Predicates = [HasFPU] in {  // FPU Operations.
2661let isCompare = 1, mayRaiseFPException = 1, hasSideEffects = 0 in {
2662  def FCMPUS : XForm_17<63, 0, (outs crrc:$crD), (ins f4rc:$fA, f4rc:$fB),
2663                        "fcmpu $crD, $fA, $fB", IIC_FPCompare>;
2664  def FCMPOS : XForm_17<63, 32, (outs crrc:$crD), (ins f4rc:$fA, f4rc:$fB),
2665                        "fcmpo $crD, $fA, $fB", IIC_FPCompare>;
2666  let Interpretation64Bit = 1, isCodeGenOnly = 1 in {
2667    def FCMPUD : XForm_17<63, 0, (outs crrc:$crD), (ins f8rc:$fA, f8rc:$fB),
2668                          "fcmpu $crD, $fA, $fB", IIC_FPCompare>;
2669    def FCMPOD : XForm_17<63, 32, (outs crrc:$crD), (ins f8rc:$fA, f8rc:$fB),
2670                          "fcmpo $crD, $fA, $fB", IIC_FPCompare>;
2671  }
2672}
2673
2674def FTDIV: XForm_17<63, 128, (outs crrc:$crD), (ins f8rc:$fA, f8rc:$fB),
2675                      "ftdiv $crD, $fA, $fB", IIC_FPCompare>;
2676def FTSQRT: XForm_17a<63, 160, (outs crrc:$crD), (ins f8rc:$fB),
2677                      "ftsqrt $crD, $fB", IIC_FPCompare,
2678                      [(set i32:$crD, (PPCftsqrt f64:$fB))]>;
2679
2680let mayRaiseFPException = 1, hasSideEffects = 0 in {
2681  let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2682  defm FRIND  : XForm_26r<63, 392, (outs f8rc:$frD), (ins f8rc:$frB),
2683                          "frin", "$frD, $frB", IIC_FPGeneral,
2684                          [(set f64:$frD, (any_fround f64:$frB))]>;
2685  defm FRINS  : XForm_26r<63, 392, (outs f4rc:$frD), (ins f4rc:$frB),
2686                          "frin", "$frD, $frB", IIC_FPGeneral,
2687                          [(set f32:$frD, (any_fround f32:$frB))]>;
2688
2689  let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2690  defm FRIPD  : XForm_26r<63, 456, (outs f8rc:$frD), (ins f8rc:$frB),
2691                          "frip", "$frD, $frB", IIC_FPGeneral,
2692                          [(set f64:$frD, (any_fceil f64:$frB))]>;
2693  defm FRIPS  : XForm_26r<63, 456, (outs f4rc:$frD), (ins f4rc:$frB),
2694                          "frip", "$frD, $frB", IIC_FPGeneral,
2695                          [(set f32:$frD, (any_fceil f32:$frB))]>;
2696  let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2697  defm FRIZD  : XForm_26r<63, 424, (outs f8rc:$frD), (ins f8rc:$frB),
2698                          "friz", "$frD, $frB", IIC_FPGeneral,
2699                          [(set f64:$frD, (any_ftrunc f64:$frB))]>;
2700  defm FRIZS  : XForm_26r<63, 424, (outs f4rc:$frD), (ins f4rc:$frB),
2701                          "friz", "$frD, $frB", IIC_FPGeneral,
2702                          [(set f32:$frD, (any_ftrunc f32:$frB))]>;
2703  let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2704  defm FRIMD  : XForm_26r<63, 488, (outs f8rc:$frD), (ins f8rc:$frB),
2705                          "frim", "$frD, $frB", IIC_FPGeneral,
2706                          [(set f64:$frD, (any_ffloor f64:$frB))]>;
2707  defm FRIMS  : XForm_26r<63, 488, (outs f4rc:$frD), (ins f4rc:$frB),
2708                          "frim", "$frD, $frB", IIC_FPGeneral,
2709                          [(set f32:$frD, (any_ffloor f32:$frB))]>;
2710}
2711
2712let Uses = [RM], mayRaiseFPException = 1, hasSideEffects = 0 in {
2713  defm FCTIW  : XForm_26r<63, 14, (outs f8rc:$frD), (ins f8rc:$frB),
2714                          "fctiw", "$frD, $frB", IIC_FPGeneral,
2715                          []>;
2716  defm FCTIWU  : XForm_26r<63, 142, (outs f8rc:$frD), (ins f8rc:$frB),
2717                          "fctiwu", "$frD, $frB", IIC_FPGeneral,
2718                          []>;
2719  defm FCTIWZ : XForm_26r<63, 15, (outs f8rc:$frD), (ins f8rc:$frB),
2720                          "fctiwz", "$frD, $frB", IIC_FPGeneral,
2721                          [(set f64:$frD, (PPCany_fctiwz f64:$frB))]>;
2722
2723  defm FRSP   : XForm_26r<63, 12, (outs f4rc:$frD), (ins f8rc:$frB),
2724                          "frsp", "$frD, $frB", IIC_FPGeneral,
2725                          [(set f32:$frD, (any_fpround f64:$frB))]>;
2726
2727  defm FSQRT  : XForm_26r<63, 22, (outs f8rc:$frD), (ins f8rc:$frB),
2728                          "fsqrt", "$frD, $frB", IIC_FPSqrtD,
2729                          [(set f64:$frD, (any_fsqrt f64:$frB))]>;
2730  defm FSQRTS : XForm_26r<59, 22, (outs f4rc:$frD), (ins f4rc:$frB),
2731                          "fsqrts", "$frD, $frB", IIC_FPSqrtS,
2732                          [(set f32:$frD, (any_fsqrt f32:$frB))]>;
2733}
2734}
2735
2736def : Pat<(PPCfsqrt f64:$frA), (FSQRT $frA)>;
2737
2738/// Note that FMR is defined as pseudo-ops on the PPC970 because they are
2739/// often coalesced away and we don't want the dispatch group builder to think
2740/// that they will fill slots (which could cause the load of a LSU reject to
2741/// sneak into a d-group with a store).
2742let hasSideEffects = 0, Predicates = [HasFPU] in
2743defm FMR   : XForm_26r<63, 72, (outs f4rc:$frD), (ins f4rc:$frB),
2744                       "fmr", "$frD, $frB", IIC_FPGeneral,
2745                       []>,  // (set f32:$frD, f32:$frB)
2746                       PPC970_Unit_Pseudo;
2747
2748let PPC970_Unit = 3, hasSideEffects = 0, Predicates = [HasFPU] in {  // FPU Operations.
2749// These are artificially split into two different forms, for 4/8 byte FP.
2750defm FABSS  : XForm_26r<63, 264, (outs f4rc:$frD), (ins f4rc:$frB),
2751                        "fabs", "$frD, $frB", IIC_FPGeneral,
2752                        [(set f32:$frD, (fabs f32:$frB))]>;
2753let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2754defm FABSD  : XForm_26r<63, 264, (outs f8rc:$frD), (ins f8rc:$frB),
2755                        "fabs", "$frD, $frB", IIC_FPGeneral,
2756                        [(set f64:$frD, (fabs f64:$frB))]>;
2757defm FNABSS : XForm_26r<63, 136, (outs f4rc:$frD), (ins f4rc:$frB),
2758                        "fnabs", "$frD, $frB", IIC_FPGeneral,
2759                        [(set f32:$frD, (fneg (fabs f32:$frB)))]>;
2760let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2761defm FNABSD : XForm_26r<63, 136, (outs f8rc:$frD), (ins f8rc:$frB),
2762                        "fnabs", "$frD, $frB", IIC_FPGeneral,
2763                        [(set f64:$frD, (fneg (fabs f64:$frB)))]>;
2764defm FNEGS  : XForm_26r<63, 40, (outs f4rc:$frD), (ins f4rc:$frB),
2765                        "fneg", "$frD, $frB", IIC_FPGeneral,
2766                        [(set f32:$frD, (fneg f32:$frB))]>;
2767let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2768defm FNEGD  : XForm_26r<63, 40, (outs f8rc:$frD), (ins f8rc:$frB),
2769                        "fneg", "$frD, $frB", IIC_FPGeneral,
2770                        [(set f64:$frD, (fneg f64:$frB))]>;
2771
2772defm FCPSGNS : XForm_28r<63, 8, (outs f4rc:$frD), (ins f4rc:$frA, f4rc:$frB),
2773                        "fcpsgn", "$frD, $frA, $frB", IIC_FPGeneral,
2774                        [(set f32:$frD, (fcopysign f32:$frB, f32:$frA))]>;
2775let Interpretation64Bit = 1, isCodeGenOnly = 1 in
2776defm FCPSGND : XForm_28r<63, 8, (outs f8rc:$frD), (ins f8rc:$frA, f8rc:$frB),
2777                        "fcpsgn", "$frD, $frA, $frB", IIC_FPGeneral,
2778                        [(set f64:$frD, (fcopysign f64:$frB, f64:$frA))]>;
2779
2780// Reciprocal estimates.
2781let mayRaiseFPException = 1 in {
2782defm FRE      : XForm_26r<63, 24, (outs f8rc:$frD), (ins f8rc:$frB),
2783                          "fre", "$frD, $frB", IIC_FPGeneral,
2784                          [(set f64:$frD, (PPCfre f64:$frB))]>;
2785defm FRES     : XForm_26r<59, 24, (outs f4rc:$frD), (ins f4rc:$frB),
2786                          "fres", "$frD, $frB", IIC_FPGeneral,
2787                          [(set f32:$frD, (PPCfre f32:$frB))]>;
2788defm FRSQRTE  : XForm_26r<63, 26, (outs f8rc:$frD), (ins f8rc:$frB),
2789                          "frsqrte", "$frD, $frB", IIC_FPGeneral,
2790                          [(set f64:$frD, (PPCfrsqrte f64:$frB))]>;
2791defm FRSQRTES : XForm_26r<59, 26, (outs f4rc:$frD), (ins f4rc:$frB),
2792                          "frsqrtes", "$frD, $frB", IIC_FPGeneral,
2793                          [(set f32:$frD, (PPCfrsqrte f32:$frB))]>;
2794}
2795}
2796
2797// XL-Form instructions.  condition register logical ops.
2798//
2799let hasSideEffects = 0 in
2800def MCRF   : XLForm_3<19, 0, (outs crrc:$BF), (ins crrc:$BFA),
2801                      "mcrf $BF, $BFA", IIC_BrMCR>,
2802             PPC970_DGroup_First, PPC970_Unit_CRU;
2803
2804// FIXME: According to the ISA (section 2.5.1 of version 2.06), the
2805// condition-register logical instructions have preferred forms. Specifically,
2806// it is preferred that the bit specified by the BT field be in the same
2807// condition register as that specified by the bit BB. We might want to account
2808// for this via hinting the register allocator and anti-dep breakers, or we
2809// could constrain the register class to force this constraint and then loosen
2810// it during register allocation via convertToThreeAddress or some similar
2811// mechanism.
2812
2813let isCommutable = 1 in {
2814def CRAND  : XLForm_1<19, 257, (outs crbitrc:$CRD),
2815                               (ins crbitrc:$CRA, crbitrc:$CRB),
2816                      "crand $CRD, $CRA, $CRB", IIC_BrCR,
2817                      [(set i1:$CRD, (and i1:$CRA, i1:$CRB))]>;
2818
2819def CRNAND : XLForm_1<19, 225, (outs crbitrc:$CRD),
2820                               (ins crbitrc:$CRA, crbitrc:$CRB),
2821                      "crnand $CRD, $CRA, $CRB", IIC_BrCR,
2822                      [(set i1:$CRD, (not (and i1:$CRA, i1:$CRB)))]>;
2823
2824def CROR   : XLForm_1<19, 449, (outs crbitrc:$CRD),
2825                               (ins crbitrc:$CRA, crbitrc:$CRB),
2826                      "cror $CRD, $CRA, $CRB", IIC_BrCR,
2827                      [(set i1:$CRD, (or i1:$CRA, i1:$CRB))]>;
2828
2829def CRXOR  : XLForm_1<19, 193, (outs crbitrc:$CRD),
2830                               (ins crbitrc:$CRA, crbitrc:$CRB),
2831                      "crxor $CRD, $CRA, $CRB", IIC_BrCR,
2832                      [(set i1:$CRD, (xor i1:$CRA, i1:$CRB))]>;
2833
2834def CRNOR  : XLForm_1<19, 33, (outs crbitrc:$CRD),
2835                              (ins crbitrc:$CRA, crbitrc:$CRB),
2836                      "crnor $CRD, $CRA, $CRB", IIC_BrCR,
2837                      [(set i1:$CRD, (not (or i1:$CRA, i1:$CRB)))]>;
2838
2839def CREQV  : XLForm_1<19, 289, (outs crbitrc:$CRD),
2840                               (ins crbitrc:$CRA, crbitrc:$CRB),
2841                      "creqv $CRD, $CRA, $CRB", IIC_BrCR,
2842                      [(set i1:$CRD, (not (xor i1:$CRA, i1:$CRB)))]>;
2843} // isCommutable
2844
2845def CRANDC : XLForm_1<19, 129, (outs crbitrc:$CRD),
2846                               (ins crbitrc:$CRA, crbitrc:$CRB),
2847                      "crandc $CRD, $CRA, $CRB", IIC_BrCR,
2848                      [(set i1:$CRD, (and i1:$CRA, (not i1:$CRB)))]>;
2849
2850def CRORC  : XLForm_1<19, 417, (outs crbitrc:$CRD),
2851                               (ins crbitrc:$CRA, crbitrc:$CRB),
2852                      "crorc $CRD, $CRA, $CRB", IIC_BrCR,
2853                      [(set i1:$CRD, (or i1:$CRA, (not i1:$CRB)))]>;
2854
2855let isCodeGenOnly = 1 in {
2856let isReMaterializable = 1, isAsCheapAsAMove = 1 in {
2857def CRSET  : XLForm_1_ext<19, 289, (outs crbitrc:$dst), (ins),
2858              "creqv $dst, $dst, $dst", IIC_BrCR,
2859              [(set i1:$dst, 1)]>;
2860
2861def CRUNSET: XLForm_1_ext<19, 193, (outs crbitrc:$dst), (ins),
2862              "crxor $dst, $dst, $dst", IIC_BrCR,
2863              [(set i1:$dst, 0)]>;
2864}
2865
2866let Defs = [CR1EQ], CRD = 6 in {
2867def CR6SET  : XLForm_1_ext<19, 289, (outs), (ins),
2868              "creqv 6, 6, 6", IIC_BrCR,
2869              [(PPCcr6set)]>;
2870
2871def CR6UNSET: XLForm_1_ext<19, 193, (outs), (ins),
2872              "crxor 6, 6, 6", IIC_BrCR,
2873              [(PPCcr6unset)]>;
2874}
2875}
2876
2877// XFX-Form instructions.  Instructions that deal with SPRs.
2878//
2879
2880def MFSPR : XFXForm_1<31, 339, (outs gprc:$RT), (ins i32imm:$SPR),
2881                      "mfspr $RT, $SPR", IIC_SprMFSPR>;
2882def MTSPR : XFXForm_1<31, 467, (outs), (ins i32imm:$SPR, gprc:$RT),
2883                      "mtspr $SPR, $RT", IIC_SprMTSPR>;
2884
2885def MFTB : XFXForm_1<31, 371, (outs gprc:$RT), (ins i32imm:$SPR),
2886                     "mftb $RT, $SPR", IIC_SprMFTB>;
2887
2888def MFPMR : XFXForm_1<31, 334, (outs gprc:$RT), (ins i32imm:$SPR),
2889                     "mfpmr $RT, $SPR", IIC_SprMFPMR>;
2890
2891def MTPMR : XFXForm_1<31, 462, (outs), (ins i32imm:$SPR, gprc:$RT),
2892                     "mtpmr $SPR, $RT", IIC_SprMTPMR>;
2893
2894
2895// A pseudo-instruction used to implement the read of the 64-bit cycle counter
2896// on a 32-bit target.
2897let hasSideEffects = 1 in
2898def ReadTB : PPCCustomInserterPseudo<(outs gprc:$lo, gprc:$hi), (ins),
2899                    "#ReadTB", []>;
2900
2901let Uses = [CTR] in {
2902def MFCTR : XFXForm_1_ext<31, 339, 9, (outs gprc:$rT), (ins),
2903                          "mfctr $rT", IIC_SprMFSPR>,
2904            PPC970_DGroup_First, PPC970_Unit_FXU;
2905}
2906let Defs = [CTR], Pattern = [(PPCmtctr i32:$rS)] in {
2907def MTCTR : XFXForm_7_ext<31, 467, 9, (outs), (ins gprc:$rS),
2908                          "mtctr $rS", IIC_SprMTSPR>,
2909            PPC970_DGroup_First, PPC970_Unit_FXU;
2910}
2911let hasSideEffects = 1, isCodeGenOnly = 1, Defs = [CTR] in {
2912let Pattern = [(int_set_loop_iterations i32:$rS)] in
2913def MTCTRloop : XFXForm_7_ext<31, 467, 9, (outs), (ins gprc:$rS),
2914                              "mtctr $rS", IIC_SprMTSPR>,
2915                PPC970_DGroup_First, PPC970_Unit_FXU;
2916}
2917
2918let hasSideEffects = 0 in {
2919let Defs = [LR] in {
2920def MTLR  : XFXForm_7_ext<31, 467, 8, (outs), (ins gprc:$rS),
2921                          "mtlr $rS", IIC_SprMTSPR>,
2922            PPC970_DGroup_First, PPC970_Unit_FXU;
2923}
2924let Uses = [LR] in {
2925def MFLR  : XFXForm_1_ext<31, 339, 8, (outs gprc:$rT), (ins),
2926                          "mflr $rT", IIC_SprMFSPR>,
2927            PPC970_DGroup_First, PPC970_Unit_FXU;
2928}
2929}
2930
2931let isCodeGenOnly = 1 in {
2932  // Move to/from VRSAVE: despite being a SPR, the VRSAVE register is renamed
2933  // like a GPR on the PPC970.  As such, copies in and out have the same
2934  // performance characteristics as an OR instruction.
2935  def MTVRSAVE : XFXForm_7_ext<31, 467, 256, (outs), (ins gprc:$rS),
2936                               "mtspr 256, $rS", IIC_IntGeneral>,
2937                 PPC970_DGroup_Single, PPC970_Unit_FXU;
2938  def MFVRSAVE : XFXForm_1_ext<31, 339, 256, (outs gprc:$rT), (ins),
2939                               "mfspr $rT, 256", IIC_IntGeneral>,
2940                 PPC970_DGroup_First, PPC970_Unit_FXU;
2941
2942  def MTVRSAVEv : XFXForm_7_ext<31, 467, 256,
2943                                (outs VRSAVERC:$reg), (ins gprc:$rS),
2944                                "mtspr 256, $rS", IIC_IntGeneral>,
2945                  PPC970_DGroup_Single, PPC970_Unit_FXU;
2946  def MFVRSAVEv : XFXForm_1_ext<31, 339, 256, (outs gprc:$rT),
2947                                (ins VRSAVERC:$reg),
2948                                "mfspr $rT, 256", IIC_IntGeneral>,
2949                  PPC970_DGroup_First, PPC970_Unit_FXU;
2950}
2951
2952// Aliases for mtvrsave/mfvrsave to mfspr/mtspr.
2953def : InstAlias<"mtvrsave $rS", (MTVRSAVE gprc:$rS)>;
2954def : InstAlias<"mfvrsave $rS", (MFVRSAVE gprc:$rS)>;
2955
2956let hasSideEffects = 0 in {
2957// mtocrf's input needs to be prepared by shifting by an amount dependent
2958// on the cr register selected. Thus, post-ra anti-dep breaking must not
2959// later change that register assignment.
2960let hasExtraDefRegAllocReq = 1 in {
2961def MTOCRF: XFXForm_5a<31, 144, (outs crbitm:$FXM), (ins gprc:$ST),
2962                       "mtocrf $FXM, $ST", IIC_BrMCRX>,
2963            PPC970_DGroup_First, PPC970_Unit_CRU;
2964
2965// Similarly to mtocrf, the mask for mtcrf must be prepared in a way that
2966// is dependent on the cr fields being set.
2967def MTCRF : XFXForm_5<31, 144, (outs), (ins i32imm:$FXM, gprc:$rS),
2968                      "mtcrf $FXM, $rS", IIC_BrMCRX>,
2969            PPC970_MicroCode, PPC970_Unit_CRU;
2970} // hasExtraDefRegAllocReq = 1
2971
2972// mfocrf's input needs to be prepared by shifting by an amount dependent
2973// on the cr register selected. Thus, post-ra anti-dep breaking must not
2974// later change that register assignment.
2975let hasExtraSrcRegAllocReq = 1 in {
2976def MFOCRF: XFXForm_5a<31, 19, (outs gprc:$rT), (ins crbitm:$FXM),
2977                       "mfocrf $rT, $FXM", IIC_SprMFCRF>,
2978            PPC970_DGroup_First, PPC970_Unit_CRU;
2979
2980// Similarly to mfocrf, the mask for mfcrf must be prepared in a way that
2981// is dependent on the cr fields being copied.
2982def MFCR : XFXForm_3<31, 19, (outs gprc:$rT), (ins),
2983                     "mfcr $rT", IIC_SprMFCR>,
2984                     PPC970_MicroCode, PPC970_Unit_CRU;
2985} // hasExtraSrcRegAllocReq = 1
2986
2987def MCRXRX : X_BF3<31, 576, (outs crrc:$BF), (ins),
2988                   "mcrxrx $BF", IIC_BrMCRX>, Requires<[IsISA3_0]>;
2989} // hasSideEffects = 0
2990
2991def : InstAlias<"mtcr $rA", (MTCRF 255, gprc:$rA)>;
2992
2993let Predicates = [HasFPU] in {
2994// Custom inserter instruction to perform FADD in round-to-zero mode.
2995let Uses = [RM], mayRaiseFPException = 1 in {
2996  def FADDrtz: PPCCustomInserterPseudo<(outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRB), "",
2997                      [(set f64:$FRT, (PPCany_faddrtz f64:$FRA, f64:$FRB))]>;
2998}
2999
3000// The above pseudo gets expanded to make use of the following instructions
3001// to manipulate FPSCR.  Note that FPSCR is not modeled at the DAG level.
3002
3003// When FM is 30/31, we are setting the 62/63 bit of FPSCR, the implicit-def
3004// RM should be set.
3005def MTFSB0 : XForm_43<63, 70, (outs), (ins u5imm:$FM),
3006                      "mtfsb0 $FM", IIC_IntMTFSB0, []>,
3007             PPC970_DGroup_Single, PPC970_Unit_FPU;
3008def MTFSB1 : XForm_43<63, 38, (outs), (ins u5imm:$FM),
3009                      "mtfsb1 $FM", IIC_IntMTFSB0, []>,
3010             PPC970_DGroup_Single, PPC970_Unit_FPU;
3011
3012let Defs = [RM] in {
3013  let isCodeGenOnly = 1 in
3014  def MTFSFb  : XFLForm<63, 711, (outs), (ins i32imm:$FM, f8rc:$rT),
3015                        "mtfsf $FM, $rT", IIC_IntMTFSB0, []>,
3016                PPC970_DGroup_Single, PPC970_Unit_FPU;
3017}
3018let Uses = [RM] in {
3019  def MFFS   : XForm_42<63, 583, (outs f8rc:$rT), (ins),
3020                         "mffs $rT", IIC_IntMFFS,
3021                         [(set f64:$rT, (PPCmffs))]>,
3022               PPC970_DGroup_Single, PPC970_Unit_FPU;
3023
3024  let Defs = [CR1] in
3025  def MFFS_rec : XForm_42<63, 583, (outs f8rc:$rT), (ins),
3026                      "mffs. $rT", IIC_IntMFFS, []>, isRecordForm;
3027
3028  def MFFSCE : X_FRT5_XO2_XO3_XO10<63, 0, 1, 583, (outs f8rc:$rT), (ins),
3029                                  "mffsce $rT", IIC_IntMFFS, []>,
3030               PPC970_DGroup_Single, PPC970_Unit_FPU;
3031
3032  def MFFSCDRN : X_FRT5_XO2_XO3_FRB5_XO10<63, 2, 4, 583, (outs f8rc:$rT),
3033                                         (ins f8rc:$FRB), "mffscdrn $rT, $FRB",
3034                                         IIC_IntMFFS, []>,
3035                 PPC970_DGroup_Single, PPC970_Unit_FPU;
3036
3037  def MFFSCDRNI : X_FRT5_XO2_XO3_DRM3_XO10<63, 2, 5, 583, (outs f8rc:$rT),
3038                                          (ins u3imm:$DRM),
3039                                          "mffscdrni $rT, $DRM",
3040                                          IIC_IntMFFS, []>,
3041                  PPC970_DGroup_Single, PPC970_Unit_FPU;
3042
3043  def MFFSCRN : X_FRT5_XO2_XO3_FRB5_XO10<63, 2, 6, 583, (outs f8rc:$rT),
3044                                        (ins f8rc:$FRB), "mffscrn $rT, $FRB",
3045                                        IIC_IntMFFS, []>,
3046                PPC970_DGroup_Single, PPC970_Unit_FPU;
3047
3048  def MFFSCRNI : X_FRT5_XO2_XO3_RM2_X10<63, 2, 7, 583, (outs f8rc:$rT),
3049                                       (ins u2imm:$RM), "mffscrni $rT, $RM",
3050                                       IIC_IntMFFS, []>,
3051                 PPC970_DGroup_Single, PPC970_Unit_FPU;
3052
3053  def MFFSL  : X_FRT5_XO2_XO3_XO10<63, 3, 0, 583, (outs f8rc:$rT), (ins),
3054                                  "mffsl $rT", IIC_IntMFFS, []>,
3055               PPC970_DGroup_Single, PPC970_Unit_FPU;
3056}
3057}
3058
3059let Predicates = [IsISA3_0] in {
3060def MODSW : XForm_8<31, 779, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3061                        "modsw $rT, $rA, $rB", IIC_IntDivW,
3062                        [(set i32:$rT, (srem i32:$rA, i32:$rB))]>;
3063def MODUW : XForm_8<31, 267, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3064                        "moduw $rT, $rA, $rB", IIC_IntDivW,
3065                        [(set i32:$rT, (urem i32:$rA, i32:$rB))]>;
3066}
3067
3068let PPC970_Unit = 1, hasSideEffects = 0 in {  // FXU Operations.
3069// XO-Form instructions.  Arithmetic instructions that can set overflow bit
3070let isCommutable = 1 in
3071defm ADD4  : XOForm_1rx<31, 266, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3072                        "add", "$rT, $rA, $rB", IIC_IntSimple,
3073                        [(set i32:$rT, (add i32:$rA, i32:$rB))]>;
3074let isCodeGenOnly = 1 in
3075def ADD4TLS  : XOForm_1<31, 266, 0, (outs gprc:$rT), (ins gprc:$rA, tlsreg32:$rB),
3076                       "add $rT, $rA, $rB", IIC_IntSimple,
3077                       [(set i32:$rT, (add i32:$rA, tglobaltlsaddr:$rB))]>;
3078let isCommutable = 1 in
3079defm ADDC  : XOForm_1rc<31, 10, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3080                        "addc", "$rT, $rA, $rB", IIC_IntGeneral,
3081                        [(set i32:$rT, (addc i32:$rA, i32:$rB))]>,
3082                        PPC970_DGroup_Cracked;
3083
3084defm DIVW  : XOForm_1rcr<31, 491, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3085                          "divw", "$rT, $rA, $rB", IIC_IntDivW,
3086                          [(set i32:$rT, (sdiv i32:$rA, i32:$rB))]>;
3087defm DIVWU : XOForm_1rcr<31, 459, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3088                          "divwu", "$rT, $rA, $rB", IIC_IntDivW,
3089                          [(set i32:$rT, (udiv i32:$rA, i32:$rB))]>;
3090defm DIVWE : XOForm_1rcr<31, 427, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3091                         "divwe", "$rT, $rA, $rB", IIC_IntDivW,
3092                         [(set i32:$rT, (int_ppc_divwe gprc:$rA, gprc:$rB))]>,
3093                         Requires<[HasExtDiv]>;
3094defm DIVWEU : XOForm_1rcr<31, 395, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3095                          "divweu", "$rT, $rA, $rB", IIC_IntDivW,
3096                          [(set i32:$rT, (int_ppc_divweu gprc:$rA, gprc:$rB))]>,
3097                          Requires<[HasExtDiv]>;
3098let isCommutable = 1 in {
3099defm MULHW : XOForm_1r<31, 75, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3100                       "mulhw", "$rT, $rA, $rB", IIC_IntMulHW,
3101                       [(set i32:$rT, (mulhs i32:$rA, i32:$rB))]>;
3102defm MULHWU : XOForm_1r<31, 11, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3103                       "mulhwu", "$rT, $rA, $rB", IIC_IntMulHWU,
3104                       [(set i32:$rT, (mulhu i32:$rA, i32:$rB))]>;
3105defm MULLW : XOForm_1rx<31, 235, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3106                        "mullw", "$rT, $rA, $rB", IIC_IntMulHW,
3107                        [(set i32:$rT, (mul i32:$rA, i32:$rB))]>;
3108} // isCommutable
3109defm SUBF  : XOForm_1rx<31, 40, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3110                        "subf", "$rT, $rA, $rB", IIC_IntGeneral,
3111                        [(set i32:$rT, (sub i32:$rB, i32:$rA))]>;
3112defm SUBFC : XOForm_1rc<31, 8, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3113                        "subfc", "$rT, $rA, $rB", IIC_IntGeneral,
3114                        [(set i32:$rT, (subc i32:$rB, i32:$rA))]>,
3115                        PPC970_DGroup_Cracked;
3116defm NEG    : XOForm_3r<31, 104, 0, (outs gprc:$rT), (ins gprc:$rA),
3117                        "neg", "$rT, $rA", IIC_IntSimple,
3118                        [(set i32:$rT, (ineg i32:$rA))]>;
3119let Uses = [CARRY] in {
3120let isCommutable = 1 in
3121defm ADDE  : XOForm_1rc<31, 138, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3122                        "adde", "$rT, $rA, $rB", IIC_IntGeneral,
3123                        [(set i32:$rT, (adde i32:$rA, i32:$rB))]>;
3124defm ADDME  : XOForm_3rc<31, 234, 0, (outs gprc:$rT), (ins gprc:$rA),
3125                         "addme", "$rT, $rA", IIC_IntGeneral,
3126                         [(set i32:$rT, (adde i32:$rA, -1))]>;
3127defm ADDZE  : XOForm_3rc<31, 202, 0, (outs gprc:$rT), (ins gprc:$rA),
3128                         "addze", "$rT, $rA", IIC_IntGeneral,
3129                         [(set i32:$rT, (adde i32:$rA, 0))]>;
3130defm SUBFE : XOForm_1rc<31, 136, 0, (outs gprc:$rT), (ins gprc:$rA, gprc:$rB),
3131                        "subfe", "$rT, $rA, $rB", IIC_IntGeneral,
3132                        [(set i32:$rT, (sube i32:$rB, i32:$rA))]>;
3133defm SUBFME : XOForm_3rc<31, 232, 0, (outs gprc:$rT), (ins gprc:$rA),
3134                         "subfme", "$rT, $rA", IIC_IntGeneral,
3135                         [(set i32:$rT, (sube -1, i32:$rA))]>;
3136defm SUBFZE : XOForm_3rc<31, 200, 0, (outs gprc:$rT), (ins gprc:$rA),
3137                         "subfze", "$rT, $rA", IIC_IntGeneral,
3138                         [(set i32:$rT, (sube 0, i32:$rA))]>;
3139}
3140}
3141
3142def : InstAlias<"sub $rA, $rB, $rC", (SUBF gprc:$rA, gprc:$rC, gprc:$rB)>;
3143def : InstAlias<"sub. $rA, $rB, $rC", (SUBF_rec gprc:$rA, gprc:$rC, gprc:$rB)>;
3144def : InstAlias<"subc $rA, $rB, $rC", (SUBFC gprc:$rA, gprc:$rC, gprc:$rB)>;
3145def : InstAlias<"subc. $rA, $rB, $rC", (SUBFC_rec gprc:$rA, gprc:$rC, gprc:$rB)>;
3146
3147// A-Form instructions.  Most of the instructions executed in the FPU are of
3148// this type.
3149//
3150let PPC970_Unit = 3, hasSideEffects = 0, Predicates = [HasFPU] in {  // FPU Operations.
3151let mayRaiseFPException = 1, Uses = [RM] in {
3152let isCommutable = 1 in {
3153  defm FMADD : AForm_1r<63, 29,
3154                      (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRC, f8rc:$FRB),
3155                      "fmadd", "$FRT, $FRA, $FRC, $FRB", IIC_FPFused,
3156                      [(set f64:$FRT, (any_fma f64:$FRA, f64:$FRC, f64:$FRB))]>;
3157  defm FMADDS : AForm_1r<59, 29,
3158                      (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRC, f4rc:$FRB),
3159                      "fmadds", "$FRT, $FRA, $FRC, $FRB", IIC_FPGeneral,
3160                      [(set f32:$FRT, (any_fma f32:$FRA, f32:$FRC, f32:$FRB))]>;
3161  defm FMSUB : AForm_1r<63, 28,
3162                      (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRC, f8rc:$FRB),
3163                      "fmsub", "$FRT, $FRA, $FRC, $FRB", IIC_FPFused,
3164                      [(set f64:$FRT,
3165                            (any_fma f64:$FRA, f64:$FRC, (fneg f64:$FRB)))]>;
3166  defm FMSUBS : AForm_1r<59, 28,
3167                      (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRC, f4rc:$FRB),
3168                      "fmsubs", "$FRT, $FRA, $FRC, $FRB", IIC_FPGeneral,
3169                      [(set f32:$FRT,
3170                            (any_fma f32:$FRA, f32:$FRC, (fneg f32:$FRB)))]>;
3171  defm FNMADD : AForm_1r<63, 31,
3172                      (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRC, f8rc:$FRB),
3173                      "fnmadd", "$FRT, $FRA, $FRC, $FRB", IIC_FPFused,
3174                      [(set f64:$FRT,
3175                            (fneg (any_fma f64:$FRA, f64:$FRC, f64:$FRB)))]>;
3176  defm FNMADDS : AForm_1r<59, 31,
3177                      (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRC, f4rc:$FRB),
3178                      "fnmadds", "$FRT, $FRA, $FRC, $FRB", IIC_FPGeneral,
3179                      [(set f32:$FRT,
3180                            (fneg (any_fma f32:$FRA, f32:$FRC, f32:$FRB)))]>;
3181  defm FNMSUB : AForm_1r<63, 30,
3182                      (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRC, f8rc:$FRB),
3183                      "fnmsub", "$FRT, $FRA, $FRC, $FRB", IIC_FPFused,
3184                      [(set f64:$FRT, (fneg (any_fma f64:$FRA, f64:$FRC,
3185                                                 (fneg f64:$FRB))))]>;
3186  defm FNMSUBS : AForm_1r<59, 30,
3187                      (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRC, f4rc:$FRB),
3188                      "fnmsubs", "$FRT, $FRA, $FRC, $FRB", IIC_FPGeneral,
3189                      [(set f32:$FRT, (fneg (any_fma f32:$FRA, f32:$FRC,
3190                                                 (fneg f32:$FRB))))]>;
3191} // isCommutable
3192}
3193// FSEL is artificially split into 4 and 8-byte forms for the result.  To avoid
3194// having 4 of these, force the comparison to always be an 8-byte double (code
3195// should use an FMRSD if the input comparison value really wants to be a float)
3196// and 4/8 byte forms for the result and operand type..
3197let Interpretation64Bit = 1, isCodeGenOnly = 1 in
3198defm FSELD : AForm_1r<63, 23,
3199                      (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRC, f8rc:$FRB),
3200                      "fsel", "$FRT, $FRA, $FRC, $FRB", IIC_FPGeneral,
3201                      [(set f64:$FRT, (PPCfsel f64:$FRA, f64:$FRC, f64:$FRB))]>;
3202defm FSELS : AForm_1r<63, 23,
3203                      (outs f4rc:$FRT), (ins f8rc:$FRA, f4rc:$FRC, f4rc:$FRB),
3204                      "fsel", "$FRT, $FRA, $FRC, $FRB", IIC_FPGeneral,
3205                      [(set f32:$FRT, (PPCfsel f64:$FRA, f32:$FRC, f32:$FRB))]>;
3206let Uses = [RM], mayRaiseFPException = 1 in {
3207  let isCommutable = 1 in {
3208  defm FADD  : AForm_2r<63, 21,
3209                        (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRB),
3210                        "fadd", "$FRT, $FRA, $FRB", IIC_FPAddSub,
3211                        [(set f64:$FRT, (any_fadd f64:$FRA, f64:$FRB))]>;
3212  defm FADDS : AForm_2r<59, 21,
3213                        (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRB),
3214                        "fadds", "$FRT, $FRA, $FRB", IIC_FPGeneral,
3215                        [(set f32:$FRT, (any_fadd f32:$FRA, f32:$FRB))]>;
3216  } // isCommutable
3217  defm FDIV  : AForm_2r<63, 18,
3218                        (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRB),
3219                        "fdiv", "$FRT, $FRA, $FRB", IIC_FPDivD,
3220                        [(set f64:$FRT, (any_fdiv f64:$FRA, f64:$FRB))]>;
3221  defm FDIVS : AForm_2r<59, 18,
3222                        (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRB),
3223                        "fdivs", "$FRT, $FRA, $FRB", IIC_FPDivS,
3224                        [(set f32:$FRT, (any_fdiv f32:$FRA, f32:$FRB))]>;
3225  let isCommutable = 1 in {
3226  defm FMUL  : AForm_3r<63, 25,
3227                        (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRC),
3228                        "fmul", "$FRT, $FRA, $FRC", IIC_FPFused,
3229                        [(set f64:$FRT, (any_fmul f64:$FRA, f64:$FRC))]>;
3230  defm FMULS : AForm_3r<59, 25,
3231                        (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRC),
3232                        "fmuls", "$FRT, $FRA, $FRC", IIC_FPGeneral,
3233                        [(set f32:$FRT, (any_fmul f32:$FRA, f32:$FRC))]>;
3234  } // isCommutable
3235  defm FSUB  : AForm_2r<63, 20,
3236                        (outs f8rc:$FRT), (ins f8rc:$FRA, f8rc:$FRB),
3237                        "fsub", "$FRT, $FRA, $FRB", IIC_FPAddSub,
3238                        [(set f64:$FRT, (any_fsub f64:$FRA, f64:$FRB))]>;
3239  defm FSUBS : AForm_2r<59, 20,
3240                        (outs f4rc:$FRT), (ins f4rc:$FRA, f4rc:$FRB),
3241                        "fsubs", "$FRT, $FRA, $FRB", IIC_FPGeneral,
3242                        [(set f32:$FRT, (any_fsub f32:$FRA, f32:$FRB))]>;
3243  }
3244}
3245
3246let hasSideEffects = 0 in {
3247let PPC970_Unit = 1 in {  // FXU Operations.
3248  let isSelect = 1 in
3249  def ISEL  : AForm_4<31, 15,
3250                     (outs gprc:$rT), (ins gprc_nor0:$rA, gprc:$rB, crbitrc:$cond),
3251                     "isel $rT, $rA, $rB, $cond", IIC_IntISEL,
3252                     []>;
3253}
3254
3255let PPC970_Unit = 1 in {  // FXU Operations.
3256// M-Form instructions.  rotate and mask instructions.
3257//
3258let isCommutable = 1 in {
3259// RLWIMI can be commuted if the rotate amount is zero.
3260defm RLWIMI : MForm_2r<20, (outs gprc:$rA),
3261                       (ins gprc:$rSi, gprc:$rS, u5imm:$SH, u5imm:$MB,
3262                       u5imm:$ME), "rlwimi", "$rA, $rS, $SH, $MB, $ME",
3263                       IIC_IntRotate, []>, PPC970_DGroup_Cracked,
3264                       RegConstraint<"$rSi = $rA">, NoEncode<"$rSi">;
3265}
3266let BaseName = "rlwinm" in {
3267def RLWINM : MForm_2<21,
3268                     (outs gprc:$rA), (ins gprc:$rS, u5imm:$SH, u5imm:$MB, u5imm:$ME),
3269                     "rlwinm $rA, $rS, $SH, $MB, $ME", IIC_IntGeneral,
3270                     []>, RecFormRel;
3271let Defs = [CR0] in
3272def RLWINM_rec : MForm_2<21,
3273                      (outs gprc:$rA), (ins gprc:$rS, u5imm:$SH, u5imm:$MB, u5imm:$ME),
3274                      "rlwinm. $rA, $rS, $SH, $MB, $ME", IIC_IntGeneral,
3275                      []>, isRecordForm, RecFormRel, PPC970_DGroup_Cracked;
3276}
3277defm RLWNM  : MForm_2r<23, (outs gprc:$rA),
3278                       (ins gprc:$rS, gprc:$rB, u5imm:$MB, u5imm:$ME),
3279                       "rlwnm", "$rA, $rS, $rB, $MB, $ME", IIC_IntGeneral,
3280                       []>;
3281}
3282} // hasSideEffects = 0
3283
3284//===----------------------------------------------------------------------===//
3285// PowerPC Instruction Patterns
3286//
3287
3288// Arbitrary immediate support.  Implement in terms of LIS/ORI.
3289def : Pat<(i32 imm:$imm),
3290          (ORI (LIS (HI16 imm:$imm)), (LO16 imm:$imm))>;
3291
3292// Implement the 'not' operation with the NOR instruction.
3293def i32not : OutPatFrag<(ops node:$in),
3294                        (NOR $in, $in)>;
3295def        : Pat<(not i32:$in),
3296                 (i32not $in)>;
3297
3298// ADD an arbitrary immediate.
3299def : Pat<(add i32:$in, imm:$imm),
3300          (ADDIS (ADDI $in, (LO16 imm:$imm)), (HA16 imm:$imm))>;
3301// OR an arbitrary immediate.
3302def : Pat<(or i32:$in, imm:$imm),
3303          (ORIS (ORI $in, (LO16 imm:$imm)), (HI16 imm:$imm))>;
3304// XOR an arbitrary immediate.
3305def : Pat<(xor i32:$in, imm:$imm),
3306          (XORIS (XORI $in, (LO16 imm:$imm)), (HI16 imm:$imm))>;
3307// SUBFIC
3308def : Pat<(sub imm32SExt16:$imm, i32:$in),
3309          (SUBFIC $in, imm:$imm)>;
3310
3311// SHL/SRL
3312def : Pat<(shl i32:$in, (i32 imm:$imm)),
3313          (RLWINM $in, imm:$imm, 0, (SHL32 imm:$imm))>;
3314def : Pat<(srl i32:$in, (i32 imm:$imm)),
3315          (RLWINM $in, (SRL32 imm:$imm), imm:$imm, 31)>;
3316
3317// ROTL
3318def : Pat<(rotl i32:$in, i32:$sh),
3319          (RLWNM $in, $sh, 0, 31)>;
3320def : Pat<(rotl i32:$in, (i32 imm:$imm)),
3321          (RLWINM $in, imm:$imm, 0, 31)>;
3322
3323// RLWNM
3324def : Pat<(and (rotl i32:$in, i32:$sh), maskimm32:$imm),
3325          (RLWNM $in, $sh, (MB maskimm32:$imm), (ME maskimm32:$imm))>;
3326
3327// Calls
3328def : Pat<(PPCcall (i32 tglobaladdr:$dst)),
3329          (BL tglobaladdr:$dst)>;
3330
3331def : Pat<(PPCcall (i32 texternalsym:$dst)),
3332          (BL texternalsym:$dst)>;
3333
3334// Calls for AIX only
3335def : Pat<(PPCcall (i32 mcsym:$dst)),
3336          (BL mcsym:$dst)>;
3337
3338def : Pat<(PPCcall_nop (i32 mcsym:$dst)),
3339          (BL_NOP mcsym:$dst)>;
3340
3341def : Pat<(PPCcall_nop (i32 texternalsym:$dst)),
3342          (BL_NOP texternalsym:$dst)>;
3343
3344def : Pat<(PPCtc_return (i32 tglobaladdr:$dst),  imm:$imm),
3345          (TCRETURNdi tglobaladdr:$dst, imm:$imm)>;
3346
3347def : Pat<(PPCtc_return (i32 texternalsym:$dst), imm:$imm),
3348          (TCRETURNdi texternalsym:$dst, imm:$imm)>;
3349
3350def : Pat<(PPCtc_return CTRRC:$dst, imm:$imm),
3351          (TCRETURNri CTRRC:$dst, imm:$imm)>;
3352
3353def : Pat<(int_ppc_readflm), (MFFS)>;
3354
3355// Hi and Lo for Darwin Global Addresses.
3356def : Pat<(PPChi tglobaladdr:$in, 0), (LIS tglobaladdr:$in)>;
3357def : Pat<(PPClo tglobaladdr:$in, 0), (LI tglobaladdr:$in)>;
3358def : Pat<(PPChi tconstpool:$in, 0), (LIS tconstpool:$in)>;
3359def : Pat<(PPClo tconstpool:$in, 0), (LI tconstpool:$in)>;
3360def : Pat<(PPChi tjumptable:$in, 0), (LIS tjumptable:$in)>;
3361def : Pat<(PPClo tjumptable:$in, 0), (LI tjumptable:$in)>;
3362def : Pat<(PPChi tblockaddress:$in, 0), (LIS tblockaddress:$in)>;
3363def : Pat<(PPClo tblockaddress:$in, 0), (LI tblockaddress:$in)>;
3364def : Pat<(PPChi tglobaltlsaddr:$g, i32:$in),
3365          (ADDIS $in, tglobaltlsaddr:$g)>;
3366def : Pat<(PPClo tglobaltlsaddr:$g, i32:$in),
3367          (ADDI $in, tglobaltlsaddr:$g)>;
3368def : Pat<(add i32:$in, (PPChi tglobaladdr:$g, 0)),
3369          (ADDIS $in, tglobaladdr:$g)>;
3370def : Pat<(add i32:$in, (PPChi tconstpool:$g, 0)),
3371          (ADDIS $in, tconstpool:$g)>;
3372def : Pat<(add i32:$in, (PPChi tjumptable:$g, 0)),
3373          (ADDIS $in, tjumptable:$g)>;
3374def : Pat<(add i32:$in, (PPChi tblockaddress:$g, 0)),
3375          (ADDIS $in, tblockaddress:$g)>;
3376
3377// Support for thread-local storage.
3378def PPC32GOT: PPCEmitTimePseudo<(outs gprc:$rD), (ins), "#PPC32GOT",
3379                [(set i32:$rD, (PPCppc32GOT))]>;
3380
3381// Get the _GLOBAL_OFFSET_TABLE_ in PIC mode.
3382// This uses two output registers, the first as the real output, the second as a
3383// temporary register, used internally in code generation.
3384def PPC32PICGOT: PPCEmitTimePseudo<(outs gprc:$rD, gprc:$rT), (ins), "#PPC32PICGOT",
3385                []>, NoEncode<"$rT">;
3386
3387def LDgotTprelL32: PPCEmitTimePseudo<(outs gprc_nor0:$rD), (ins s16imm:$disp, gprc_nor0:$reg),
3388                           "#LDgotTprelL32",
3389                           [(set i32:$rD,
3390                             (PPCldGotTprelL tglobaltlsaddr:$disp, i32:$reg))]>;
3391def : Pat<(PPCaddTls i32:$in, tglobaltlsaddr:$g),
3392          (ADD4TLS $in, tglobaltlsaddr:$g)>;
3393
3394def ADDItlsgdL32 : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc_nor0:$reg, s16imm:$disp),
3395                         "#ADDItlsgdL32",
3396                         [(set i32:$rD,
3397                           (PPCaddiTlsgdL i32:$reg, tglobaltlsaddr:$disp))]>;
3398// LR is a true define, while the rest of the Defs are clobbers.  R3 is
3399// explicitly defined when this op is created, so not mentioned here.
3400let hasExtraSrcRegAllocReq = 1, hasExtraDefRegAllocReq = 1,
3401    Defs = [R0,R4,R5,R6,R7,R8,R9,R10,R11,R12,LR,CTR,CR0,CR1,CR5,CR6,CR7] in
3402def GETtlsADDR32 : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc:$reg, tlsgd32:$sym),
3403                          "GETtlsADDR32",
3404                          [(set i32:$rD,
3405                            (PPCgetTlsAddr i32:$reg, tglobaltlsaddr:$sym))]>;
3406// Combined op for ADDItlsgdL32 and GETtlsADDR32, late expanded.  R3 and LR
3407// are true defines while the rest of the Defs are clobbers.
3408let hasExtraSrcRegAllocReq = 1, hasExtraDefRegAllocReq = 1,
3409    Defs = [R0,R3,R4,R5,R6,R7,R8,R9,R10,R11,R12,LR,CTR,CR0,CR1,CR5,CR6,CR7] in
3410def ADDItlsgdLADDR32 : PPCEmitTimePseudo<(outs gprc:$rD),
3411                              (ins gprc_nor0:$reg, s16imm:$disp, tlsgd32:$sym),
3412                              "#ADDItlsgdLADDR32",
3413                              [(set i32:$rD,
3414                                (PPCaddiTlsgdLAddr i32:$reg,
3415                                                   tglobaltlsaddr:$disp,
3416                                                   tglobaltlsaddr:$sym))]>;
3417def ADDItlsldL32 : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc_nor0:$reg, s16imm:$disp),
3418                          "#ADDItlsldL32",
3419                          [(set i32:$rD,
3420                            (PPCaddiTlsldL i32:$reg, tglobaltlsaddr:$disp))]>;
3421// LR is a true define, while the rest of the Defs are clobbers.  R3 is
3422// explicitly defined when this op is created, so not mentioned here.
3423let hasExtraSrcRegAllocReq = 1, hasExtraDefRegAllocReq = 1,
3424    Defs = [R0,R4,R5,R6,R7,R8,R9,R10,R11,R12,LR,CTR,CR0,CR1,CR5,CR6,CR7] in
3425def GETtlsldADDR32 : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc:$reg, tlsgd32:$sym),
3426                            "GETtlsldADDR32",
3427                            [(set i32:$rD,
3428                              (PPCgetTlsldAddr i32:$reg,
3429                                               tglobaltlsaddr:$sym))]>;
3430// Combined op for ADDItlsldL32 and GETtlsADDR32, late expanded.  R3 and LR
3431// are true defines while the rest of the Defs are clobbers.
3432let hasExtraSrcRegAllocReq = 1, hasExtraDefRegAllocReq = 1,
3433    Defs = [R0,R3,R4,R5,R6,R7,R8,R9,R10,R11,R12,LR,CTR,CR0,CR1,CR5,CR6,CR7] in
3434def ADDItlsldLADDR32 : PPCEmitTimePseudo<(outs gprc:$rD),
3435                              (ins gprc_nor0:$reg, s16imm:$disp, tlsgd32:$sym),
3436                              "#ADDItlsldLADDR32",
3437                              [(set i32:$rD,
3438                                (PPCaddiTlsldLAddr i32:$reg,
3439                                                   tglobaltlsaddr:$disp,
3440                                                   tglobaltlsaddr:$sym))]>;
3441def ADDIdtprelL32 : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc_nor0:$reg, s16imm:$disp),
3442                           "#ADDIdtprelL32",
3443                           [(set i32:$rD,
3444                             (PPCaddiDtprelL i32:$reg, tglobaltlsaddr:$disp))]>;
3445def ADDISdtprelHA32 : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc_nor0:$reg, s16imm:$disp),
3446                            "#ADDISdtprelHA32",
3447                            [(set i32:$rD,
3448                              (PPCaddisDtprelHA i32:$reg,
3449                                                tglobaltlsaddr:$disp))]>;
3450
3451// Support for Position-independent code
3452def LWZtoc : PPCEmitTimePseudo<(outs gprc:$rD), (ins tocentry32:$disp, gprc:$reg),
3453                   "#LWZtoc",
3454                   [(set i32:$rD,
3455                     (PPCtoc_entry tglobaladdr:$disp, i32:$reg))]>;
3456def LWZtocL : PPCEmitTimePseudo<(outs gprc:$rD), (ins tocentry32:$disp, gprc_nor0:$reg),
3457                    "#LWZtocL",
3458                    [(set i32:$rD,
3459                      (PPCtoc_entry tglobaladdr:$disp, i32:$reg))]>;
3460def ADDIStocHA : PPCEmitTimePseudo<(outs gprc:$rD), (ins gprc_nor0:$reg, tocentry32:$disp),
3461                       "#ADDIStocHA",
3462                       [(set i32:$rD,
3463                         (PPCtoc_entry i32:$reg, tglobaladdr:$disp))]>;
3464
3465// Get Global (GOT) Base Register offset, from the word immediately preceding
3466// the function label.
3467def UpdateGBR : PPCEmitTimePseudo<(outs gprc:$rD, gprc:$rT), (ins gprc:$rI), "#UpdateGBR", []>;
3468
3469// Pseudo-instruction marked for deletion. When deleting the instruction would
3470// cause iterator invalidation in MIR transformation passes, this pseudo can be
3471// used instead. It will be removed unconditionally at pre-emit time (prior to
3472// branch selection).
3473def UNENCODED_NOP: PPCEmitTimePseudo<(outs), (ins), "#UNENCODED_NOP", []>;
3474
3475// Standard shifts.  These are represented separately from the real shifts above
3476// so that we can distinguish between shifts that allow 5-bit and 6-bit shift
3477// amounts.
3478def : Pat<(sra i32:$rS, i32:$rB),
3479          (SRAW $rS, $rB)>;
3480def : Pat<(srl i32:$rS, i32:$rB),
3481          (SRW $rS, $rB)>;
3482def : Pat<(shl i32:$rS, i32:$rB),
3483          (SLW $rS, $rB)>;
3484
3485def : Pat<(i32 (zextloadi1 iaddr:$src)),
3486          (LBZ iaddr:$src)>;
3487def : Pat<(i32 (zextloadi1 xaddr:$src)),
3488          (LBZX xaddr:$src)>;
3489def : Pat<(i32 (extloadi1 iaddr:$src)),
3490          (LBZ iaddr:$src)>;
3491def : Pat<(i32 (extloadi1 xaddr:$src)),
3492          (LBZX xaddr:$src)>;
3493def : Pat<(i32 (extloadi8 iaddr:$src)),
3494          (LBZ iaddr:$src)>;
3495def : Pat<(i32 (extloadi8 xaddr:$src)),
3496          (LBZX xaddr:$src)>;
3497def : Pat<(i32 (extloadi16 iaddr:$src)),
3498          (LHZ iaddr:$src)>;
3499def : Pat<(i32 (extloadi16 xaddr:$src)),
3500          (LHZX xaddr:$src)>;
3501let Predicates = [HasFPU] in {
3502def : Pat<(f64 (extloadf32 iaddr:$src)),
3503          (COPY_TO_REGCLASS (LFS iaddr:$src), F8RC)>;
3504def : Pat<(f64 (extloadf32 xaddr:$src)),
3505          (COPY_TO_REGCLASS (LFSX xaddr:$src), F8RC)>;
3506
3507def : Pat<(f64 (any_fpextend f32:$src)),
3508          (COPY_TO_REGCLASS $src, F8RC)>;
3509}
3510
3511// Only seq_cst fences require the heavyweight sync (SYNC 0).
3512// All others can use the lightweight sync (SYNC 1).
3513// source: http://www.cl.cam.ac.uk/~pes20/cpp/cpp0xmappings.html
3514// The rule for seq_cst is duplicated to work with both 64 bits and 32 bits
3515// versions of Power.
3516def : Pat<(atomic_fence (i64 7), (timm)), (SYNC 0)>, Requires<[HasSYNC]>;
3517def : Pat<(atomic_fence (i32 7), (timm)), (SYNC 0)>, Requires<[HasSYNC]>;
3518def : Pat<(atomic_fence (timm), (timm)), (SYNC 1)>, Requires<[HasSYNC]>;
3519def : Pat<(atomic_fence (timm), (timm)), (MSYNC)>, Requires<[HasOnlyMSYNC]>;
3520
3521let Predicates = [HasFPU] in {
3522// Additional fnmsub patterns for custom node
3523def : Pat<(PPCfnmsub f64:$A, f64:$B, f64:$C),
3524          (FNMSUB $A, $B, $C)>;
3525def : Pat<(PPCfnmsub f32:$A, f32:$B, f32:$C),
3526          (FNMSUBS $A, $B, $C)>;
3527def : Pat<(fneg (PPCfnmsub f64:$A, f64:$B, f64:$C)),
3528          (FMSUB $A, $B, $C)>;
3529def : Pat<(fneg (PPCfnmsub f32:$A, f32:$B, f32:$C)),
3530          (FMSUBS $A, $B, $C)>;
3531def : Pat<(PPCfnmsub f64:$A, f64:$B, (fneg f64:$C)),
3532          (FNMADD $A, $B, $C)>;
3533def : Pat<(PPCfnmsub f32:$A, f32:$B, (fneg f32:$C)),
3534          (FNMADDS $A, $B, $C)>;
3535
3536// FCOPYSIGN's operand types need not agree.
3537def : Pat<(fcopysign f64:$frB, f32:$frA),
3538          (FCPSGND (COPY_TO_REGCLASS $frA, F8RC), $frB)>;
3539def : Pat<(fcopysign f32:$frB, f64:$frA),
3540          (FCPSGNS (COPY_TO_REGCLASS $frA, F4RC), $frB)>;
3541}
3542
3543include "PPCInstrAltivec.td"
3544include "PPCInstrSPE.td"
3545include "PPCInstr64Bit.td"
3546include "PPCInstrVSX.td"
3547include "PPCInstrHTM.td"
3548
3549def crnot : OutPatFrag<(ops node:$in),
3550                       (CRNOR $in, $in)>;
3551def       : Pat<(not i1:$in),
3552                (crnot $in)>;
3553
3554// Prefixed instructions may require access to the above defs at a later
3555// time so we include this after the def.
3556include "PPCInstrPrefix.td"
3557
3558// Patterns for arithmetic i1 operations.
3559def : Pat<(add i1:$a, i1:$b),
3560          (CRXOR $a, $b)>;
3561def : Pat<(sub i1:$a, i1:$b),
3562          (CRXOR $a, $b)>;
3563def : Pat<(mul i1:$a, i1:$b),
3564          (CRAND $a, $b)>;
3565
3566// We're sometimes asked to materialize i1 -1, which is just 1 in this case
3567// (-1 is used to mean all bits set).
3568def : Pat<(i1 -1), (CRSET)>;
3569
3570// i1 extensions, implemented in terms of isel.
3571def : Pat<(i32 (zext i1:$in)),
3572          (SELECT_I4 $in, (LI 1), (LI 0))>;
3573def : Pat<(i32 (sext i1:$in)),
3574          (SELECT_I4 $in, (LI -1), (LI 0))>;
3575
3576def : Pat<(i64 (zext i1:$in)),
3577          (SELECT_I8 $in, (LI8 1), (LI8 0))>;
3578def : Pat<(i64 (sext i1:$in)),
3579          (SELECT_I8 $in, (LI8 -1), (LI8 0))>;
3580
3581// FIXME: We should choose either a zext or a sext based on other constants
3582// already around.
3583def : Pat<(i32 (anyext i1:$in)),
3584          (SELECT_I4 $in, (LI 1), (LI 0))>;
3585def : Pat<(i64 (anyext i1:$in)),
3586          (SELECT_I8 $in, (LI8 1), (LI8 0))>;
3587
3588// match setcc on i1 variables.
3589// CRANDC is:
3590//   1 1 : F
3591//   1 0 : T
3592//   0 1 : F
3593//   0 0 : F
3594//
3595// LT is:
3596//  -1 -1  : F
3597//  -1  0  : T
3598//   0 -1  : F
3599//   0  0  : F
3600//
3601// ULT is:
3602//   1 1 : F
3603//   1 0 : F
3604//   0 1 : T
3605//   0 0 : F
3606def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETLT)),
3607          (CRANDC $s1, $s2)>;
3608def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETULT)),
3609          (CRANDC $s2, $s1)>;
3610// CRORC is:
3611//   1 1 : T
3612//   1 0 : T
3613//   0 1 : F
3614//   0 0 : T
3615//
3616// LE is:
3617//  -1 -1 : T
3618//  -1  0 : T
3619//   0 -1 : F
3620//   0  0 : T
3621//
3622// ULE is:
3623//   1 1 : T
3624//   1 0 : F
3625//   0 1 : T
3626//   0 0 : T
3627def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETLE)),
3628          (CRORC $s1, $s2)>;
3629def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETULE)),
3630          (CRORC $s2, $s1)>;
3631
3632def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETEQ)),
3633          (CREQV $s1, $s2)>;
3634
3635// GE is:
3636//  -1 -1 : T
3637//  -1  0 : F
3638//   0 -1 : T
3639//   0  0 : T
3640//
3641// UGE is:
3642//   1 1 : T
3643//   1 0 : T
3644//   0 1 : F
3645//   0 0 : T
3646def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETGE)),
3647          (CRORC $s2, $s1)>;
3648def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETUGE)),
3649          (CRORC $s1, $s2)>;
3650
3651// GT is:
3652//  -1 -1 : F
3653//  -1  0 : F
3654//   0 -1 : T
3655//   0  0 : F
3656//
3657// UGT is:
3658//  1 1 : F
3659//  1 0 : T
3660//  0 1 : F
3661//  0 0 : F
3662def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETGT)),
3663          (CRANDC $s2, $s1)>;
3664def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETUGT)),
3665          (CRANDC $s1, $s2)>;
3666
3667def : Pat<(i1 (setcc i1:$s1, i1:$s2, SETNE)),
3668          (CRXOR $s1, $s2)>;
3669
3670// match setcc on non-i1 (non-vector) variables. Note that SETUEQ, SETOGE,
3671// SETOLE, SETONE, SETULT and SETUGT should be expanded by legalize for
3672// floating-point types.
3673
3674multiclass CRNotPat<dag pattern, dag result> {
3675  def : Pat<pattern, (crnot result)>;
3676  def : Pat<(not pattern), result>;
3677
3678  // We can also fold the crnot into an extension:
3679  def : Pat<(i32 (zext pattern)),
3680            (SELECT_I4 result, (LI 0), (LI 1))>;
3681  def : Pat<(i32 (sext pattern)),
3682            (SELECT_I4 result, (LI 0), (LI -1))>;
3683
3684  // We can also fold the crnot into an extension:
3685  def : Pat<(i64 (zext pattern)),
3686            (SELECT_I8 result, (LI8 0), (LI8 1))>;
3687  def : Pat<(i64 (sext pattern)),
3688            (SELECT_I8 result, (LI8 0), (LI8 -1))>;
3689
3690  // FIXME: We should choose either a zext or a sext based on other constants
3691  // already around.
3692  def : Pat<(i32 (anyext pattern)),
3693            (SELECT_I4 result, (LI 0), (LI 1))>;
3694
3695  def : Pat<(i64 (anyext pattern)),
3696            (SELECT_I8 result, (LI8 0), (LI8 1))>;
3697}
3698
3699// FIXME: Because of what seems like a bug in TableGen's type-inference code,
3700// we need to write imm:$imm in the output patterns below, not just $imm, or
3701// else the resulting matcher will not correctly add the immediate operand
3702// (making it a register operand instead).
3703
3704// extended SETCC.
3705multiclass ExtSetCCPat<CondCode cc, PatFrag pfrag,
3706                       OutPatFrag rfrag, OutPatFrag rfrag8> {
3707  def : Pat<(i32 (zext (i1 (pfrag i32:$s1, cc)))),
3708            (rfrag $s1)>;
3709  def : Pat<(i64 (zext (i1 (pfrag i64:$s1, cc)))),
3710            (rfrag8 $s1)>;
3711  def : Pat<(i64 (zext (i1 (pfrag i32:$s1, cc)))),
3712            (INSERT_SUBREG (i64 (IMPLICIT_DEF)), (rfrag $s1), sub_32)>;
3713  def : Pat<(i32 (zext (i1 (pfrag i64:$s1, cc)))),
3714            (EXTRACT_SUBREG (rfrag8 $s1), sub_32)>;
3715
3716  def : Pat<(i32 (anyext (i1 (pfrag i32:$s1, cc)))),
3717            (rfrag $s1)>;
3718  def : Pat<(i64 (anyext (i1 (pfrag i64:$s1, cc)))),
3719            (rfrag8 $s1)>;
3720  def : Pat<(i64 (anyext (i1 (pfrag i32:$s1, cc)))),
3721            (INSERT_SUBREG (i64 (IMPLICIT_DEF)), (rfrag $s1), sub_32)>;
3722  def : Pat<(i32 (anyext (i1 (pfrag i64:$s1, cc)))),
3723            (EXTRACT_SUBREG (rfrag8 $s1), sub_32)>;
3724}
3725
3726// Note that we do all inversions below with i(32|64)not, instead of using
3727// (xori x, 1) because on the A2 nor has single-cycle latency while xori
3728// has 2-cycle latency.
3729
3730defm : ExtSetCCPat<SETEQ,
3731                   PatFrag<(ops node:$in, node:$cc),
3732                           (setcc $in, 0, $cc)>,
3733                   OutPatFrag<(ops node:$in),
3734                              (RLWINM (CNTLZW $in), 27, 31, 31)>,
3735                   OutPatFrag<(ops node:$in),
3736                              (RLDICL (CNTLZD $in), 58, 63)> >;
3737
3738defm : ExtSetCCPat<SETNE,
3739                   PatFrag<(ops node:$in, node:$cc),
3740                           (setcc $in, 0, $cc)>,
3741                   OutPatFrag<(ops node:$in),
3742                              (RLWINM (i32not (CNTLZW $in)), 27, 31, 31)>,
3743                   OutPatFrag<(ops node:$in),
3744                              (RLDICL (i64not (CNTLZD $in)), 58, 63)> >;
3745
3746defm : ExtSetCCPat<SETLT,
3747                   PatFrag<(ops node:$in, node:$cc),
3748                           (setcc $in, 0, $cc)>,
3749                   OutPatFrag<(ops node:$in),
3750                              (RLWINM $in, 1, 31, 31)>,
3751                   OutPatFrag<(ops node:$in),
3752                              (RLDICL $in, 1, 63)> >;
3753
3754defm : ExtSetCCPat<SETGE,
3755                   PatFrag<(ops node:$in, node:$cc),
3756                           (setcc $in, 0, $cc)>,
3757                   OutPatFrag<(ops node:$in),
3758                              (RLWINM (i32not $in), 1, 31, 31)>,
3759                   OutPatFrag<(ops node:$in),
3760                              (RLDICL (i64not $in), 1, 63)> >;
3761
3762defm : ExtSetCCPat<SETGT,
3763                   PatFrag<(ops node:$in, node:$cc),
3764                           (setcc $in, 0, $cc)>,
3765                   OutPatFrag<(ops node:$in),
3766                              (RLWINM (ANDC (NEG $in), $in), 1, 31, 31)>,
3767                   OutPatFrag<(ops node:$in),
3768                              (RLDICL (ANDC8 (NEG8 $in), $in), 1, 63)> >;
3769
3770defm : ExtSetCCPat<SETLE,
3771                   PatFrag<(ops node:$in, node:$cc),
3772                           (setcc $in, 0, $cc)>,
3773                   OutPatFrag<(ops node:$in),
3774                              (RLWINM (ORC $in, (NEG $in)), 1, 31, 31)>,
3775                   OutPatFrag<(ops node:$in),
3776                              (RLDICL (ORC8 $in, (NEG8 $in)), 1, 63)> >;
3777
3778defm : ExtSetCCPat<SETLT,
3779                   PatFrag<(ops node:$in, node:$cc),
3780                           (setcc $in, -1, $cc)>,
3781                   OutPatFrag<(ops node:$in),
3782                              (RLWINM (AND $in, (ADDI $in, 1)), 1, 31, 31)>,
3783                   OutPatFrag<(ops node:$in),
3784                              (RLDICL (AND8 $in, (ADDI8 $in, 1)), 1, 63)> >;
3785
3786defm : ExtSetCCPat<SETGE,
3787                   PatFrag<(ops node:$in, node:$cc),
3788                           (setcc $in, -1, $cc)>,
3789                   OutPatFrag<(ops node:$in),
3790                              (RLWINM (NAND $in, (ADDI $in, 1)), 1, 31, 31)>,
3791                   OutPatFrag<(ops node:$in),
3792                              (RLDICL (NAND8 $in, (ADDI8 $in, 1)), 1, 63)> >;
3793
3794defm : ExtSetCCPat<SETGT,
3795                   PatFrag<(ops node:$in, node:$cc),
3796                           (setcc $in, -1, $cc)>,
3797                   OutPatFrag<(ops node:$in),
3798                              (RLWINM (i32not $in), 1, 31, 31)>,
3799                   OutPatFrag<(ops node:$in),
3800                              (RLDICL (i64not $in), 1, 63)> >;
3801
3802defm : ExtSetCCPat<SETLE,
3803                   PatFrag<(ops node:$in, node:$cc),
3804                           (setcc $in, -1, $cc)>,
3805                   OutPatFrag<(ops node:$in),
3806                              (RLWINM $in, 1, 31, 31)>,
3807                   OutPatFrag<(ops node:$in),
3808                              (RLDICL $in, 1, 63)> >;
3809
3810// An extended SETCC with shift amount.
3811multiclass ExtSetCCShiftPat<CondCode cc, PatFrag pfrag,
3812                            OutPatFrag rfrag, OutPatFrag rfrag8> {
3813  def : Pat<(i32 (zext (i1 (pfrag i32:$s1, i32:$sa, cc)))),
3814            (rfrag $s1, $sa)>;
3815  def : Pat<(i64 (zext (i1 (pfrag i64:$s1, i32:$sa, cc)))),
3816            (rfrag8 $s1, $sa)>;
3817  def : Pat<(i64 (zext (i1 (pfrag i32:$s1, i32:$sa, cc)))),
3818            (INSERT_SUBREG (i64 (IMPLICIT_DEF)), (rfrag $s1, $sa), sub_32)>;
3819  def : Pat<(i32 (zext (i1 (pfrag i64:$s1, i32:$sa, cc)))),
3820            (EXTRACT_SUBREG (rfrag8 $s1, $sa), sub_32)>;
3821
3822  def : Pat<(i32 (anyext (i1 (pfrag i32:$s1, i32:$sa, cc)))),
3823            (rfrag $s1, $sa)>;
3824  def : Pat<(i64 (anyext (i1 (pfrag i64:$s1, i32:$sa, cc)))),
3825            (rfrag8 $s1, $sa)>;
3826  def : Pat<(i64 (anyext (i1 (pfrag i32:$s1, i32:$sa, cc)))),
3827            (INSERT_SUBREG (i64 (IMPLICIT_DEF)), (rfrag $s1, $sa), sub_32)>;
3828  def : Pat<(i32 (anyext (i1 (pfrag i64:$s1, i32:$sa, cc)))),
3829            (EXTRACT_SUBREG (rfrag8 $s1, $sa), sub_32)>;
3830}
3831
3832defm : ExtSetCCShiftPat<SETNE,
3833                        PatFrag<(ops node:$in, node:$sa, node:$cc),
3834                                (setcc (and $in, (shl 1, $sa)), 0, $cc)>,
3835                        OutPatFrag<(ops node:$in, node:$sa),
3836                                   (RLWNM $in, (SUBFIC $sa, 32), 31, 31)>,
3837                        OutPatFrag<(ops node:$in, node:$sa),
3838                                   (RLDCL $in, (SUBFIC $sa, 64), 63)> >;
3839
3840defm : ExtSetCCShiftPat<SETEQ,
3841                        PatFrag<(ops node:$in, node:$sa, node:$cc),
3842                                (setcc (and $in, (shl 1, $sa)), 0, $cc)>,
3843                        OutPatFrag<(ops node:$in, node:$sa),
3844                                   (RLWNM (i32not $in),
3845                                          (SUBFIC $sa, 32), 31, 31)>,
3846                        OutPatFrag<(ops node:$in, node:$sa),
3847                                   (RLDCL (i64not $in),
3848                                          (SUBFIC $sa, 64), 63)> >;
3849
3850// SETCC for i32.
3851def : Pat<(i1 (setcc i32:$s1, immZExt16:$imm, SETULT)),
3852          (EXTRACT_SUBREG (CMPLWI $s1, imm:$imm), sub_lt)>;
3853def : Pat<(i1 (setcc i32:$s1, imm32SExt16:$imm, SETLT)),
3854          (EXTRACT_SUBREG (CMPWI $s1, imm:$imm), sub_lt)>;
3855def : Pat<(i1 (setcc i32:$s1, immZExt16:$imm, SETUGT)),
3856          (EXTRACT_SUBREG (CMPLWI $s1, imm:$imm), sub_gt)>;
3857def : Pat<(i1 (setcc i32:$s1, imm32SExt16:$imm, SETGT)),
3858          (EXTRACT_SUBREG (CMPWI $s1, imm:$imm), sub_gt)>;
3859def : Pat<(i1 (setcc i32:$s1, imm32SExt16:$imm, SETEQ)),
3860          (EXTRACT_SUBREG (CMPWI $s1, imm:$imm), sub_eq)>;
3861def : Pat<(i1 (setcc i32:$s1, immZExt16:$imm, SETEQ)),
3862          (EXTRACT_SUBREG (CMPLWI $s1, imm:$imm), sub_eq)>;
3863
3864// For non-equality comparisons, the default code would materialize the
3865// constant, then compare against it, like this:
3866//   lis r2, 4660
3867//   ori r2, r2, 22136
3868//   cmpw cr0, r3, r2
3869//   beq cr0,L6
3870// Since we are just comparing for equality, we can emit this instead:
3871//   xoris r0,r3,0x1234
3872//   cmplwi cr0,r0,0x5678
3873//   beq cr0,L6
3874
3875def : Pat<(i1 (setcc i32:$s1, imm:$imm, SETEQ)),
3876          (EXTRACT_SUBREG (CMPLWI (XORIS $s1, (HI16 imm:$imm)),
3877                                  (LO16 imm:$imm)), sub_eq)>;
3878
3879def : Pat<(i1 (setcc i32:$s1, i32:$s2, SETULT)),
3880          (EXTRACT_SUBREG (CMPLW $s1, $s2), sub_lt)>;
3881def : Pat<(i1 (setcc i32:$s1, i32:$s2, SETLT)),
3882          (EXTRACT_SUBREG (CMPW $s1, $s2), sub_lt)>;
3883def : Pat<(i1 (setcc i32:$s1, i32:$s2, SETUGT)),
3884          (EXTRACT_SUBREG (CMPLW $s1, $s2), sub_gt)>;
3885def : Pat<(i1 (setcc i32:$s1, i32:$s2, SETGT)),
3886          (EXTRACT_SUBREG (CMPW $s1, $s2), sub_gt)>;
3887def : Pat<(i1 (setcc i32:$s1, i32:$s2, SETEQ)),
3888          (EXTRACT_SUBREG (CMPW $s1, $s2), sub_eq)>;
3889
3890// SETCC for i64.
3891def : Pat<(i1 (setcc i64:$s1, immZExt16:$imm, SETULT)),
3892          (EXTRACT_SUBREG (CMPLDI $s1, imm:$imm), sub_lt)>;
3893def : Pat<(i1 (setcc i64:$s1, imm64SExt16:$imm, SETLT)),
3894          (EXTRACT_SUBREG (CMPDI $s1, imm:$imm), sub_lt)>;
3895def : Pat<(i1 (setcc i64:$s1, immZExt16:$imm, SETUGT)),
3896          (EXTRACT_SUBREG (CMPLDI $s1, imm:$imm), sub_gt)>;
3897def : Pat<(i1 (setcc i64:$s1, imm64SExt16:$imm, SETGT)),
3898          (EXTRACT_SUBREG (CMPDI $s1, imm:$imm), sub_gt)>;
3899def : Pat<(i1 (setcc i64:$s1, imm64SExt16:$imm, SETEQ)),
3900          (EXTRACT_SUBREG (CMPDI $s1, imm:$imm), sub_eq)>;
3901def : Pat<(i1 (setcc i64:$s1, immZExt16:$imm, SETEQ)),
3902          (EXTRACT_SUBREG (CMPLDI $s1, imm:$imm), sub_eq)>;
3903
3904// For non-equality comparisons, the default code would materialize the
3905// constant, then compare against it, like this:
3906//   lis r2, 4660
3907//   ori r2, r2, 22136
3908//   cmpd cr0, r3, r2
3909//   beq cr0,L6
3910// Since we are just comparing for equality, we can emit this instead:
3911//   xoris r0,r3,0x1234
3912//   cmpldi cr0,r0,0x5678
3913//   beq cr0,L6
3914
3915def : Pat<(i1 (setcc i64:$s1, imm64ZExt32:$imm, SETEQ)),
3916          (EXTRACT_SUBREG (CMPLDI (XORIS8 $s1, (HI16 imm:$imm)),
3917                                  (LO16 imm:$imm)), sub_eq)>;
3918
3919def : Pat<(i1 (setcc i64:$s1, i64:$s2, SETULT)),
3920          (EXTRACT_SUBREG (CMPLD $s1, $s2), sub_lt)>;
3921def : Pat<(i1 (setcc i64:$s1, i64:$s2, SETLT)),
3922          (EXTRACT_SUBREG (CMPD $s1, $s2), sub_lt)>;
3923def : Pat<(i1 (setcc i64:$s1, i64:$s2, SETUGT)),
3924          (EXTRACT_SUBREG (CMPLD $s1, $s2), sub_gt)>;
3925def : Pat<(i1 (setcc i64:$s1, i64:$s2, SETGT)),
3926          (EXTRACT_SUBREG (CMPD $s1, $s2), sub_gt)>;
3927def : Pat<(i1 (setcc i64:$s1, i64:$s2, SETEQ)),
3928          (EXTRACT_SUBREG (CMPD $s1, $s2), sub_eq)>;
3929
3930let Predicates = [IsNotISA3_1] in {
3931// Instantiations of CRNotPat for i32.
3932defm : CRNotPat<(i1 (setcc i32:$s1, immZExt16:$imm, SETUGE)),
3933                (EXTRACT_SUBREG (CMPLWI $s1, imm:$imm), sub_lt)>;
3934defm : CRNotPat<(i1 (setcc i32:$s1, imm32SExt16:$imm, SETGE)),
3935                (EXTRACT_SUBREG (CMPWI $s1, imm:$imm), sub_lt)>;
3936defm : CRNotPat<(i1 (setcc i32:$s1, immZExt16:$imm, SETULE)),
3937                (EXTRACT_SUBREG (CMPLWI $s1, imm:$imm), sub_gt)>;
3938defm : CRNotPat<(i1 (setcc i32:$s1, imm32SExt16:$imm, SETLE)),
3939                (EXTRACT_SUBREG (CMPWI $s1, imm:$imm), sub_gt)>;
3940defm : CRNotPat<(i1 (setcc i32:$s1, imm32SExt16:$imm, SETNE)),
3941                (EXTRACT_SUBREG (CMPWI $s1, imm:$imm), sub_eq)>;
3942defm : CRNotPat<(i1 (setcc i32:$s1, immZExt16:$imm, SETNE)),
3943                (EXTRACT_SUBREG (CMPLWI $s1, imm:$imm), sub_eq)>;
3944
3945defm : CRNotPat<(i1 (setcc i32:$s1, imm:$imm, SETNE)),
3946                (EXTRACT_SUBREG (CMPLWI (XORIS $s1, (HI16 imm:$imm)),
3947                                        (LO16 imm:$imm)), sub_eq)>;
3948
3949defm : CRNotPat<(i1 (setcc i32:$s1, i32:$s2, SETUGE)),
3950                (EXTRACT_SUBREG (CMPLW $s1, $s2), sub_lt)>;
3951defm : CRNotPat<(i1 (setcc i32:$s1, i32:$s2, SETGE)),
3952                (EXTRACT_SUBREG (CMPW $s1, $s2), sub_lt)>;
3953defm : CRNotPat<(i1 (setcc i32:$s1, i32:$s2, SETULE)),
3954                (EXTRACT_SUBREG (CMPLW $s1, $s2), sub_gt)>;
3955defm : CRNotPat<(i1 (setcc i32:$s1, i32:$s2, SETLE)),
3956                (EXTRACT_SUBREG (CMPW $s1, $s2), sub_gt)>;
3957defm : CRNotPat<(i1 (setcc i32:$s1, i32:$s2, SETNE)),
3958                (EXTRACT_SUBREG (CMPW $s1, $s2), sub_eq)>;
3959
3960// Instantiations of CRNotPat for i64.
3961defm : CRNotPat<(i1 (setcc i64:$s1, immZExt16:$imm, SETUGE)),
3962                (EXTRACT_SUBREG (CMPLDI $s1, imm:$imm), sub_lt)>;
3963defm : CRNotPat<(i1 (setcc i64:$s1, imm64SExt16:$imm, SETGE)),
3964                (EXTRACT_SUBREG (CMPDI $s1, imm:$imm), sub_lt)>;
3965defm : CRNotPat<(i1 (setcc i64:$s1, immZExt16:$imm, SETULE)),
3966                (EXTRACT_SUBREG (CMPLDI $s1, imm:$imm), sub_gt)>;
3967defm : CRNotPat<(i1 (setcc i64:$s1, imm64SExt16:$imm, SETLE)),
3968                (EXTRACT_SUBREG (CMPDI $s1, imm:$imm), sub_gt)>;
3969defm : CRNotPat<(i1 (setcc i64:$s1, imm64SExt16:$imm, SETNE)),
3970                (EXTRACT_SUBREG (CMPDI $s1, imm:$imm), sub_eq)>;
3971defm : CRNotPat<(i1 (setcc i64:$s1, immZExt16:$imm, SETNE)),
3972                (EXTRACT_SUBREG (CMPLDI $s1, imm:$imm), sub_eq)>;
3973
3974defm : CRNotPat<(i1 (setcc i64:$s1, imm64ZExt32:$imm, SETNE)),
3975                (EXTRACT_SUBREG (CMPLDI (XORIS8 $s1, (HI16 imm:$imm)),
3976                                        (LO16 imm:$imm)), sub_eq)>;
3977
3978defm : CRNotPat<(i1 (setcc i64:$s1, i64:$s2, SETUGE)),
3979                (EXTRACT_SUBREG (CMPLD $s1, $s2), sub_lt)>;
3980defm : CRNotPat<(i1 (setcc i64:$s1, i64:$s2, SETGE)),
3981                (EXTRACT_SUBREG (CMPD $s1, $s2), sub_lt)>;
3982defm : CRNotPat<(i1 (setcc i64:$s1, i64:$s2, SETULE)),
3983                (EXTRACT_SUBREG (CMPLD $s1, $s2), sub_gt)>;
3984defm : CRNotPat<(i1 (setcc i64:$s1, i64:$s2, SETLE)),
3985                (EXTRACT_SUBREG (CMPD $s1, $s2), sub_gt)>;
3986defm : CRNotPat<(i1 (setcc i64:$s1, i64:$s2, SETNE)),
3987                (EXTRACT_SUBREG (CMPD $s1, $s2), sub_eq)>;
3988}
3989
3990multiclass FSetCCPat<SDNode SetCC, ValueType Ty, PatLeaf FCmp> {
3991  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETUGE)),
3992                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_lt)>;
3993  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETGE)),
3994                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_lt)>;
3995  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETULE)),
3996                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_gt)>;
3997  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETLE)),
3998                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_gt)>;
3999  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETUNE)),
4000                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_eq)>;
4001  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETNE)),
4002                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_eq)>;
4003  defm : CRNotPat<(i1 (SetCC Ty:$s1, Ty:$s2, SETO)),
4004                  (EXTRACT_SUBREG (FCmp $s1, $s2), sub_un)>;
4005
4006  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETOLT)),
4007            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_lt)>;
4008  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETLT)),
4009            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_lt)>;
4010  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETOGT)),
4011            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_gt)>;
4012  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETGT)),
4013            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_gt)>;
4014  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETOEQ)),
4015            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_eq)>;
4016  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETEQ)),
4017            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_eq)>;
4018  def : Pat<(i1 (SetCC Ty:$s1, Ty:$s2, SETUO)),
4019            (EXTRACT_SUBREG (FCmp $s1, $s2), sub_un)>;
4020}
4021
4022let Predicates = [HasFPU] in {
4023// FCMPU: If either of the operands is a Signaling NaN, then VXSNAN is set.
4024// SETCC for f32.
4025defm : FSetCCPat<any_fsetcc, f32, FCMPUS>;
4026
4027// SETCC for f64.
4028defm : FSetCCPat<any_fsetcc, f64, FCMPUD>;
4029
4030// SETCC for f128.
4031defm : FSetCCPat<any_fsetcc, f128, XSCMPUQP>;
4032
4033// FCMPO: If either of the operands is a Signaling NaN, then VXSNAN is set and,
4034// if neither operand is a Signaling NaN but at least one operand is a Quiet NaN,
4035// then VXVC is set.
4036// SETCCS for f32.
4037defm : FSetCCPat<strict_fsetccs, f32, FCMPOS>;
4038
4039// SETCCS for f64.
4040defm : FSetCCPat<strict_fsetccs, f64, FCMPOD>;
4041
4042// SETCCS for f128.
4043defm : FSetCCPat<strict_fsetccs, f128, XSCMPOQP>;
4044}
4045
4046// This must be in this file because it relies on patterns defined in this file
4047// after the inclusion of the instruction sets.
4048let Predicates = [HasSPE] in {
4049// SETCC for f32.
4050def : Pat<(i1 (setcc f32:$s1, f32:$s2, SETOLT)),
4051          (EXTRACT_SUBREG (EFSCMPLT $s1, $s2), sub_gt)>;
4052def : Pat<(i1 (setcc f32:$s1, f32:$s2, SETLT)),
4053          (EXTRACT_SUBREG (EFSCMPLT $s1, $s2), sub_gt)>;
4054def : Pat<(i1 (setcc f32:$s1, f32:$s2, SETOGT)),
4055          (EXTRACT_SUBREG (EFSCMPGT $s1, $s2), sub_gt)>;
4056def : Pat<(i1 (setcc f32:$s1, f32:$s2, SETGT)),
4057          (EXTRACT_SUBREG (EFSCMPGT $s1, $s2), sub_gt)>;
4058def : Pat<(i1 (setcc f32:$s1, f32:$s2, SETOEQ)),
4059          (EXTRACT_SUBREG (EFSCMPEQ $s1, $s2), sub_gt)>;
4060def : Pat<(i1 (setcc f32:$s1, f32:$s2, SETEQ)),
4061          (EXTRACT_SUBREG (EFSCMPEQ $s1, $s2), sub_gt)>;
4062
4063defm : CRNotPat<(i1 (setcc f32:$s1, f32:$s2, SETUGE)),
4064                (EXTRACT_SUBREG (EFSCMPLT $s1, $s2), sub_gt)>;
4065defm : CRNotPat<(i1 (setcc f32:$s1, f32:$s2, SETGE)),
4066                (EXTRACT_SUBREG (EFSCMPLT $s1, $s2), sub_gt)>;
4067defm : CRNotPat<(i1 (setcc f32:$s1, f32:$s2, SETULE)),
4068                (EXTRACT_SUBREG (EFSCMPGT $s1, $s2), sub_gt)>;
4069defm : CRNotPat<(i1 (setcc f32:$s1, f32:$s2, SETLE)),
4070                (EXTRACT_SUBREG (EFSCMPGT $s1, $s2), sub_gt)>;
4071defm : CRNotPat<(i1 (setcc f32:$s1, f32:$s2, SETUNE)),
4072                (EXTRACT_SUBREG (EFSCMPEQ $s1, $s2), sub_gt)>;
4073defm : CRNotPat<(i1 (setcc f32:$s1, f32:$s2, SETNE)),
4074                (EXTRACT_SUBREG (EFSCMPEQ $s1, $s2), sub_gt)>;
4075
4076// SETCC for f64.
4077def : Pat<(i1 (setcc f64:$s1, f64:$s2, SETOLT)),
4078          (EXTRACT_SUBREG (EFDCMPLT $s1, $s2), sub_gt)>;
4079def : Pat<(i1 (setcc f64:$s1, f64:$s2, SETLT)),
4080          (EXTRACT_SUBREG (EFDCMPLT $s1, $s2), sub_gt)>;
4081def : Pat<(i1 (setcc f64:$s1, f64:$s2, SETOGT)),
4082          (EXTRACT_SUBREG (EFDCMPGT $s1, $s2), sub_gt)>;
4083def : Pat<(i1 (setcc f64:$s1, f64:$s2, SETGT)),
4084          (EXTRACT_SUBREG (EFDCMPGT $s1, $s2), sub_gt)>;
4085def : Pat<(i1 (setcc f64:$s1, f64:$s2, SETOEQ)),
4086          (EXTRACT_SUBREG (EFDCMPEQ $s1, $s2), sub_gt)>;
4087def : Pat<(i1 (setcc f64:$s1, f64:$s2, SETEQ)),
4088          (EXTRACT_SUBREG (EFDCMPEQ $s1, $s2), sub_gt)>;
4089
4090defm : CRNotPat<(i1 (setcc f64:$s1, f64:$s2, SETUGE)),
4091                (EXTRACT_SUBREG (EFDCMPLT $s1, $s2), sub_gt)>;
4092defm : CRNotPat<(i1 (setcc f64:$s1, f64:$s2, SETGE)),
4093                (EXTRACT_SUBREG (EFDCMPLT $s1, $s2), sub_gt)>;
4094defm : CRNotPat<(i1 (setcc f64:$s1, f64:$s2, SETULE)),
4095                (EXTRACT_SUBREG (EFDCMPGT $s1, $s2), sub_gt)>;
4096defm : CRNotPat<(i1 (setcc f64:$s1, f64:$s2, SETLE)),
4097                (EXTRACT_SUBREG (EFDCMPGT $s1, $s2), sub_gt)>;
4098defm : CRNotPat<(i1 (setcc f64:$s1, f64:$s2, SETUNE)),
4099                (EXTRACT_SUBREG (EFDCMPEQ $s1, $s2), sub_gt)>;
4100defm : CRNotPat<(i1 (setcc f64:$s1, f64:$s2, SETNE)),
4101                (EXTRACT_SUBREG (EFDCMPEQ $s1, $s2), sub_gt)>;
4102}
4103// match select on i1 variables:
4104def : Pat<(i1 (select i1:$cond, i1:$tval, i1:$fval)),
4105          (CROR (CRAND        $cond , $tval),
4106                (CRAND (crnot $cond), $fval))>;
4107
4108// match selectcc on i1 variables:
4109//   select (lhs == rhs), tval, fval is:
4110//   ((lhs == rhs) & tval) | (!(lhs == rhs) & fval)
4111def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETLT)),
4112           (CROR (CRAND (CRANDC $lhs, $rhs), $tval),
4113                 (CRAND (CRORC  $rhs, $lhs), $fval))>;
4114def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETULT)),
4115           (CROR (CRAND (CRANDC $rhs, $lhs), $tval),
4116                 (CRAND (CRORC  $lhs, $rhs), $fval))>;
4117def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETLE)),
4118           (CROR (CRAND (CRORC  $lhs, $rhs), $tval),
4119                 (CRAND (CRANDC $rhs, $lhs), $fval))>;
4120def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETULE)),
4121           (CROR (CRAND (CRORC  $rhs, $lhs), $tval),
4122                 (CRAND (CRANDC $lhs, $rhs), $fval))>;
4123def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETEQ)),
4124           (CROR (CRAND (CREQV $lhs, $rhs), $tval),
4125                 (CRAND (CRXOR $lhs, $rhs), $fval))>;
4126def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETGE)),
4127           (CROR (CRAND (CRORC  $rhs, $lhs), $tval),
4128                 (CRAND (CRANDC $lhs, $rhs), $fval))>;
4129def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETUGE)),
4130           (CROR (CRAND (CRORC  $lhs, $rhs), $tval),
4131                 (CRAND (CRANDC $rhs, $lhs), $fval))>;
4132def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETGT)),
4133           (CROR (CRAND (CRANDC $rhs, $lhs), $tval),
4134                 (CRAND (CRORC  $lhs, $rhs), $fval))>;
4135def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETUGT)),
4136           (CROR (CRAND (CRANDC $lhs, $rhs), $tval),
4137                 (CRAND (CRORC  $rhs, $lhs), $fval))>;
4138def : Pat <(i1 (selectcc i1:$lhs, i1:$rhs, i1:$tval, i1:$fval, SETNE)),
4139           (CROR (CRAND (CREQV $lhs, $rhs), $fval),
4140                 (CRAND (CRXOR $lhs, $rhs), $tval))>;
4141
4142// match selectcc on i1 variables with non-i1 output.
4143def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETLT)),
4144          (SELECT_I4 (CRANDC $lhs, $rhs), $tval, $fval)>;
4145def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETULT)),
4146          (SELECT_I4 (CRANDC $rhs, $lhs), $tval, $fval)>;
4147def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETLE)),
4148          (SELECT_I4 (CRORC  $lhs, $rhs), $tval, $fval)>;
4149def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETULE)),
4150          (SELECT_I4 (CRORC  $rhs, $lhs), $tval, $fval)>;
4151def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETEQ)),
4152          (SELECT_I4 (CREQV $lhs, $rhs), $tval, $fval)>;
4153def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETGE)),
4154          (SELECT_I4 (CRORC  $rhs, $lhs), $tval, $fval)>;
4155def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETUGE)),
4156          (SELECT_I4 (CRORC  $lhs, $rhs), $tval, $fval)>;
4157def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETGT)),
4158          (SELECT_I4 (CRANDC $rhs, $lhs), $tval, $fval)>;
4159def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETUGT)),
4160          (SELECT_I4 (CRANDC $lhs, $rhs), $tval, $fval)>;
4161def : Pat<(i32 (selectcc i1:$lhs, i1:$rhs, i32:$tval, i32:$fval, SETNE)),
4162          (SELECT_I4 (CRXOR $lhs, $rhs), $tval, $fval)>;
4163
4164def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETLT)),
4165          (SELECT_I8 (CRANDC $lhs, $rhs), $tval, $fval)>;
4166def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETULT)),
4167          (SELECT_I8 (CRANDC $rhs, $lhs), $tval, $fval)>;
4168def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETLE)),
4169          (SELECT_I8 (CRORC  $lhs, $rhs), $tval, $fval)>;
4170def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETULE)),
4171          (SELECT_I8 (CRORC  $rhs, $lhs), $tval, $fval)>;
4172def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETEQ)),
4173          (SELECT_I8 (CREQV $lhs, $rhs), $tval, $fval)>;
4174def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETGE)),
4175          (SELECT_I8 (CRORC  $rhs, $lhs), $tval, $fval)>;
4176def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETUGE)),
4177          (SELECT_I8 (CRORC  $lhs, $rhs), $tval, $fval)>;
4178def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETGT)),
4179          (SELECT_I8 (CRANDC $rhs, $lhs), $tval, $fval)>;
4180def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETUGT)),
4181          (SELECT_I8 (CRANDC $lhs, $rhs), $tval, $fval)>;
4182def : Pat<(i64 (selectcc i1:$lhs, i1:$rhs, i64:$tval, i64:$fval, SETNE)),
4183          (SELECT_I8 (CRXOR $lhs, $rhs), $tval, $fval)>;
4184
4185let Predicates = [HasFPU] in {
4186def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETLT)),
4187          (SELECT_F4 (CRANDC $lhs, $rhs), $tval, $fval)>;
4188def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETULT)),
4189          (SELECT_F4 (CRANDC $rhs, $lhs), $tval, $fval)>;
4190def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETLE)),
4191          (SELECT_F4 (CRORC  $lhs, $rhs), $tval, $fval)>;
4192def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETULE)),
4193          (SELECT_F4 (CRORC  $rhs, $lhs), $tval, $fval)>;
4194def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETEQ)),
4195          (SELECT_F4 (CREQV $lhs, $rhs), $tval, $fval)>;
4196def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETGE)),
4197          (SELECT_F4 (CRORC  $rhs, $lhs), $tval, $fval)>;
4198def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETUGE)),
4199          (SELECT_F4 (CRORC  $lhs, $rhs), $tval, $fval)>;
4200def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETGT)),
4201          (SELECT_F4 (CRANDC $rhs, $lhs), $tval, $fval)>;
4202def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETUGT)),
4203          (SELECT_F4 (CRANDC $lhs, $rhs), $tval, $fval)>;
4204def : Pat<(f32 (selectcc i1:$lhs, i1:$rhs, f32:$tval, f32:$fval, SETNE)),
4205          (SELECT_F4 (CRXOR $lhs, $rhs), $tval, $fval)>;
4206
4207def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETLT)),
4208          (SELECT_F8 (CRANDC $lhs, $rhs), $tval, $fval)>;
4209def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETULT)),
4210          (SELECT_F8 (CRANDC $rhs, $lhs), $tval, $fval)>;
4211def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETLE)),
4212          (SELECT_F8 (CRORC  $lhs, $rhs), $tval, $fval)>;
4213def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETULE)),
4214          (SELECT_F8 (CRORC  $rhs, $lhs), $tval, $fval)>;
4215def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETEQ)),
4216          (SELECT_F8 (CREQV $lhs, $rhs), $tval, $fval)>;
4217def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETGE)),
4218          (SELECT_F8 (CRORC  $rhs, $lhs), $tval, $fval)>;
4219def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETUGE)),
4220          (SELECT_F8 (CRORC  $lhs, $rhs), $tval, $fval)>;
4221def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETGT)),
4222          (SELECT_F8 (CRANDC $rhs, $lhs), $tval, $fval)>;
4223def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETUGT)),
4224          (SELECT_F8 (CRANDC $lhs, $rhs), $tval, $fval)>;
4225def : Pat<(f64 (selectcc i1:$lhs, i1:$rhs, f64:$tval, f64:$fval, SETNE)),
4226          (SELECT_F8 (CRXOR $lhs, $rhs), $tval, $fval)>;
4227}
4228
4229def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETLT)),
4230          (SELECT_F16 (CRANDC $lhs, $rhs), $tval, $fval)>;
4231def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETULT)),
4232          (SELECT_F16 (CRANDC $rhs, $lhs), $tval, $fval)>;
4233def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETLE)),
4234          (SELECT_F16 (CRORC  $lhs, $rhs), $tval, $fval)>;
4235def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETULE)),
4236          (SELECT_F16 (CRORC  $rhs, $lhs), $tval, $fval)>;
4237def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETEQ)),
4238          (SELECT_F16 (CREQV $lhs, $rhs), $tval, $fval)>;
4239def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETGE)),
4240         (SELECT_F16 (CRORC  $rhs, $lhs), $tval, $fval)>;
4241def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETUGE)),
4242          (SELECT_F16 (CRORC  $lhs, $rhs), $tval, $fval)>;
4243def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETGT)),
4244          (SELECT_F16 (CRANDC $rhs, $lhs), $tval, $fval)>;
4245def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETUGT)),
4246          (SELECT_F16 (CRANDC $lhs, $rhs), $tval, $fval)>;
4247def : Pat<(f128 (selectcc i1:$lhs, i1:$rhs, f128:$tval, f128:$fval, SETNE)),
4248          (SELECT_F16 (CRXOR $lhs, $rhs), $tval, $fval)>;
4249
4250def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETLT)),
4251          (SELECT_VRRC (CRANDC $lhs, $rhs), $tval, $fval)>;
4252def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETULT)),
4253          (SELECT_VRRC (CRANDC $rhs, $lhs), $tval, $fval)>;
4254def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETLE)),
4255          (SELECT_VRRC (CRORC  $lhs, $rhs), $tval, $fval)>;
4256def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETULE)),
4257          (SELECT_VRRC (CRORC  $rhs, $lhs), $tval, $fval)>;
4258def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETEQ)),
4259          (SELECT_VRRC (CREQV $lhs, $rhs), $tval, $fval)>;
4260def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETGE)),
4261          (SELECT_VRRC (CRORC  $rhs, $lhs), $tval, $fval)>;
4262def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETUGE)),
4263          (SELECT_VRRC (CRORC  $lhs, $rhs), $tval, $fval)>;
4264def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETGT)),
4265          (SELECT_VRRC (CRANDC $rhs, $lhs), $tval, $fval)>;
4266def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETUGT)),
4267          (SELECT_VRRC (CRANDC $lhs, $rhs), $tval, $fval)>;
4268def : Pat<(v4i32 (selectcc i1:$lhs, i1:$rhs, v4i32:$tval, v4i32:$fval, SETNE)),
4269          (SELECT_VRRC (CRXOR $lhs, $rhs), $tval, $fval)>;
4270
4271def ANDI_rec_1_EQ_BIT : PPCCustomInserterPseudo<(outs crbitrc:$dst), (ins gprc:$in),
4272                             "#ANDI_rec_1_EQ_BIT",
4273                             [(set i1:$dst, (trunc (not i32:$in)))]>;
4274def ANDI_rec_1_GT_BIT : PPCCustomInserterPseudo<(outs crbitrc:$dst), (ins gprc:$in),
4275                             "#ANDI_rec_1_GT_BIT",
4276                             [(set i1:$dst, (trunc i32:$in))]>;
4277
4278def ANDI_rec_1_EQ_BIT8 : PPCCustomInserterPseudo<(outs crbitrc:$dst), (ins g8rc:$in),
4279                              "#ANDI_rec_1_EQ_BIT8",
4280                              [(set i1:$dst, (trunc (not i64:$in)))]>;
4281def ANDI_rec_1_GT_BIT8 : PPCCustomInserterPseudo<(outs crbitrc:$dst), (ins g8rc:$in),
4282                              "#ANDI_rec_1_GT_BIT8",
4283                              [(set i1:$dst, (trunc i64:$in))]>;
4284
4285def : Pat<(i1 (not (trunc i32:$in))),
4286           (ANDI_rec_1_EQ_BIT $in)>;
4287def : Pat<(i1 (not (trunc i64:$in))),
4288           (ANDI_rec_1_EQ_BIT8 $in)>;
4289
4290//===----------------------------------------------------------------------===//
4291// PowerPC Instructions used for assembler/disassembler only
4292//
4293
4294// FIXME: For B=0 or B > 8, the registers following RT are used.
4295// WARNING: Do not add patterns for this instruction without fixing this.
4296def LSWI  : XForm_base_r3xo_memOp<31, 597, (outs gprc:$RT),
4297                                  (ins gprc:$A, u5imm:$B),
4298                                  "lswi $RT, $A, $B", IIC_LdStLoad, []>;
4299
4300// FIXME: For B=0 or B > 8, the registers following RT are used.
4301// WARNING: Do not add patterns for this instruction without fixing this.
4302def STSWI : XForm_base_r3xo_memOp<31, 725, (outs),
4303                                  (ins gprc:$RT, gprc:$A, u5imm:$B),
4304                                  "stswi $RT, $A, $B", IIC_LdStLoad, []>;
4305
4306def ISYNC : XLForm_2_ext<19, 150, 0, 0, 0, (outs), (ins),
4307                         "isync", IIC_SprISYNC, []>;
4308
4309def ICBI : XForm_1a<31, 982, (outs), (ins memrr:$src),
4310                    "icbi $src", IIC_LdStICBI, []>;
4311
4312def WAIT : XForm_24_sync<31, 30, (outs), (ins u2imm:$L),
4313                         "wait $L", IIC_LdStLoad, []>;
4314
4315def MBAR : XForm_mbar<31, 854, (outs), (ins u5imm:$MO),
4316                         "mbar $MO", IIC_LdStLoad>, Requires<[IsBookE]>;
4317
4318def MTSR: XForm_sr<31, 210, (outs), (ins gprc:$RS, u4imm:$SR),
4319            "mtsr $SR, $RS", IIC_SprMTSR>;
4320
4321def MFSR: XForm_sr<31, 595, (outs gprc:$RS), (ins u4imm:$SR),
4322            "mfsr $RS, $SR", IIC_SprMFSR>;
4323
4324def MTSRIN: XForm_srin<31, 242, (outs), (ins gprc:$RS, gprc:$RB),
4325            "mtsrin $RS, $RB", IIC_SprMTSR>;
4326
4327def MFSRIN: XForm_srin<31, 659, (outs gprc:$RS), (ins gprc:$RB),
4328            "mfsrin $RS, $RB", IIC_SprMFSR>;
4329
4330def MTMSR: XForm_mtmsr<31, 146, (outs), (ins gprc:$RS, u1imm:$L),
4331                    "mtmsr $RS, $L", IIC_SprMTMSR>;
4332
4333def WRTEE: XForm_mtmsr<31, 131, (outs), (ins gprc:$RS),
4334                    "wrtee $RS", IIC_SprMTMSR>, Requires<[IsBookE]> {
4335  let L = 0;
4336}
4337
4338def WRTEEI: I<31, (outs), (ins i1imm:$E), "wrteei $E", IIC_SprMTMSR>,
4339              Requires<[IsBookE]> {
4340  bits<1> E;
4341
4342  let Inst{16} = E;
4343  let Inst{21-30} = 163;
4344}
4345
4346def DCCCI : XForm_tlb<454, (outs), (ins gprc:$A, gprc:$B),
4347               "dccci $A, $B", IIC_LdStLoad>, Requires<[IsPPC4xx]>;
4348def ICCCI : XForm_tlb<966, (outs), (ins gprc:$A, gprc:$B),
4349               "iccci $A, $B", IIC_LdStLoad>, Requires<[IsPPC4xx]>;
4350
4351def : InstAlias<"dci 0", (DCCCI R0, R0)>, Requires<[IsPPC4xx]>;
4352def : InstAlias<"dccci", (DCCCI R0, R0)>, Requires<[IsPPC4xx]>;
4353def : InstAlias<"ici 0", (ICCCI R0, R0)>, Requires<[IsPPC4xx]>;
4354def : InstAlias<"iccci", (ICCCI R0, R0)>, Requires<[IsPPC4xx]>;
4355
4356def MFMSR : XForm_rs<31, 83, (outs gprc:$RT), (ins),
4357                  "mfmsr $RT", IIC_SprMFMSR, []>;
4358
4359def MTMSRD : XForm_mtmsr<31, 178, (outs), (ins gprc:$RS, u1imm:$L),
4360                    "mtmsrd $RS, $L", IIC_SprMTMSRD>;
4361
4362def MCRFS : XLForm_3<63, 64, (outs crrc:$BF), (ins crrc:$BFA),
4363                     "mcrfs $BF, $BFA", IIC_BrMCR>;
4364
4365// If W is 0 and BF is 7, the 60:63 bits will be set, we should set the
4366// implicit-def RM.
4367def MTFSFI : XLForm_4<63, 134, (outs crrc:$BF), (ins i32imm:$U, i32imm:$W),
4368                      "mtfsfi $BF, $U, $W", IIC_IntMFFS>;
4369let Defs = [CR1] in
4370def MTFSFI_rec : XLForm_4<63, 134, (outs crrc:$BF), (ins i32imm:$U, i32imm:$W),
4371                       "mtfsfi. $BF, $U, $W", IIC_IntMFFS>, isRecordForm;
4372
4373def : InstAlias<"mtfsfi $BF, $U", (MTFSFI crrc:$BF, i32imm:$U, 0)>;
4374def : InstAlias<"mtfsfi. $BF, $U", (MTFSFI_rec crrc:$BF, i32imm:$U, 0)>;
4375
4376let Predicates = [HasFPU] in {
4377let Defs = [RM] in {
4378def MTFSF : XFLForm_1<63, 711, (outs),
4379                      (ins i32imm:$FLM, f8rc:$FRB, u1imm:$L, i32imm:$W),
4380                      "mtfsf $FLM, $FRB, $L, $W", IIC_IntMFFS, []>;
4381let Defs = [CR1] in
4382def MTFSF_rec : XFLForm_1<63, 711, (outs),
4383                       (ins i32imm:$FLM, f8rc:$FRB, u1imm:$L, i32imm:$W),
4384                       "mtfsf. $FLM, $FRB, $L, $W", IIC_IntMFFS, []>, isRecordForm;
4385}
4386
4387def : InstAlias<"mtfsf $FLM, $FRB", (MTFSF i32imm:$FLM, f8rc:$FRB, 0, 0)>;
4388def : InstAlias<"mtfsf. $FLM, $FRB", (MTFSF_rec i32imm:$FLM, f8rc:$FRB, 0, 0)>;
4389}
4390
4391def SLBIE : XForm_16b<31, 434, (outs), (ins gprc:$RB),
4392                        "slbie $RB", IIC_SprSLBIE, []>;
4393
4394def SLBMTE : XForm_26<31, 402, (outs), (ins gprc:$RS, gprc:$RB),
4395                    "slbmte $RS, $RB", IIC_SprSLBMTE, []>;
4396
4397def SLBMFEE : XForm_26<31, 915, (outs gprc:$RT), (ins gprc:$RB),
4398                       "slbmfee $RT, $RB", IIC_SprSLBMFEE, []>;
4399
4400def SLBMFEV : XLForm_1_gen<31, 851, (outs gprc:$RT), (ins gprc:$RB),
4401                       "slbmfev $RT, $RB", IIC_SprSLBMFEV, []>;
4402
4403def SLBIA : XForm_0<31, 498, (outs), (ins), "slbia", IIC_SprSLBIA, []>;
4404
4405let Defs = [CR0] in
4406def SLBFEE_rec : XForm_26<31, 979, (outs gprc:$RT), (ins gprc:$RB),
4407                         "slbfee. $RT, $RB", IIC_SprSLBFEE, []>, isRecordForm;
4408
4409def TLBIA : XForm_0<31, 370, (outs), (ins),
4410                        "tlbia", IIC_SprTLBIA, []>;
4411
4412def TLBSYNC : XForm_0<31, 566, (outs), (ins),
4413                        "tlbsync", IIC_SprTLBSYNC, []>;
4414
4415def TLBIEL : XForm_16b<31, 274, (outs), (ins gprc:$RB),
4416                          "tlbiel $RB", IIC_SprTLBIEL, []>;
4417
4418def TLBLD : XForm_16b<31, 978, (outs), (ins gprc:$RB),
4419                          "tlbld $RB", IIC_LdStLoad, []>, Requires<[IsPPC6xx]>;
4420def TLBLI : XForm_16b<31, 1010, (outs), (ins gprc:$RB),
4421                          "tlbli $RB", IIC_LdStLoad, []>, Requires<[IsPPC6xx]>;
4422
4423def TLBIE : XForm_26<31, 306, (outs), (ins gprc:$RS, gprc:$RB),
4424                          "tlbie $RB,$RS", IIC_SprTLBIE, []>;
4425
4426def TLBSX : XForm_tlb<914, (outs), (ins gprc:$A, gprc:$B), "tlbsx $A, $B",
4427                IIC_LdStLoad>, Requires<[IsBookE]>;
4428
4429def TLBIVAX : XForm_tlb<786, (outs), (ins gprc:$A, gprc:$B), "tlbivax $A, $B",
4430                IIC_LdStLoad>, Requires<[IsBookE]>;
4431
4432def TLBRE : XForm_24_eieio<31, 946, (outs), (ins),
4433                           "tlbre", IIC_LdStLoad, []>, Requires<[IsBookE]>;
4434
4435def TLBWE : XForm_24_eieio<31, 978, (outs), (ins),
4436                           "tlbwe", IIC_LdStLoad, []>, Requires<[IsBookE]>;
4437
4438def TLBRE2 : XForm_tlbws<31, 946, (outs gprc:$RS), (ins gprc:$A, i1imm:$WS),
4439               "tlbre $RS, $A, $WS", IIC_LdStLoad, []>, Requires<[IsPPC4xx]>;
4440
4441def TLBWE2 : XForm_tlbws<31, 978, (outs), (ins gprc:$RS, gprc:$A, i1imm:$WS),
4442               "tlbwe $RS, $A, $WS", IIC_LdStLoad, []>, Requires<[IsPPC4xx]>;
4443
4444def TLBSX2 : XForm_base_r3xo<31, 914, (outs), (ins gprc:$RST, gprc:$A, gprc:$B),
4445                             "tlbsx $RST, $A, $B", IIC_LdStLoad, []>,
4446                             Requires<[IsPPC4xx]>;
4447def TLBSX2D : XForm_base_r3xo<31, 914, (outs),
4448                              (ins gprc:$RST, gprc:$A, gprc:$B),
4449                              "tlbsx. $RST, $A, $B", IIC_LdStLoad, []>,
4450                              Requires<[IsPPC4xx]>, isRecordForm;
4451
4452def RFID : XForm_0<19, 18, (outs), (ins), "rfid", IIC_IntRFID, []>;
4453
4454def RFI : XForm_0<19, 50, (outs), (ins), "rfi", IIC_SprRFI, []>,
4455                  Requires<[IsBookE]>;
4456def RFCI : XForm_0<19, 51, (outs), (ins), "rfci", IIC_BrB, []>,
4457                   Requires<[IsBookE]>;
4458
4459def RFDI : XForm_0<19, 39, (outs), (ins), "rfdi", IIC_BrB, []>,
4460                   Requires<[IsE500]>;
4461def RFMCI : XForm_0<19, 38, (outs), (ins), "rfmci", IIC_BrB, []>,
4462                    Requires<[IsE500]>;
4463
4464def MFDCR : XFXForm_1<31, 323, (outs gprc:$RT), (ins i32imm:$SPR),
4465                      "mfdcr $RT, $SPR", IIC_SprMFSPR>, Requires<[IsPPC4xx]>;
4466def MTDCR : XFXForm_1<31, 451, (outs), (ins gprc:$RT, i32imm:$SPR),
4467                      "mtdcr $SPR, $RT", IIC_SprMTSPR>, Requires<[IsPPC4xx]>;
4468
4469def HRFID : XLForm_1_np<19, 274, (outs), (ins), "hrfid", IIC_BrB, []>;
4470def NAP   : XLForm_1_np<19, 434, (outs), (ins), "nap", IIC_BrB, []>;
4471
4472def ATTN : XForm_attn<0, 256, (outs), (ins), "attn", IIC_BrB>;
4473
4474def LBZCIX : XForm_base_r3xo_memOp<31, 853, (outs gprc:$RST),
4475                                  (ins gprc:$A, gprc:$B),
4476                                  "lbzcix $RST, $A, $B", IIC_LdStLoad, []>;
4477def LHZCIX : XForm_base_r3xo_memOp<31, 821, (outs gprc:$RST),
4478                                  (ins gprc:$A, gprc:$B),
4479                                  "lhzcix $RST, $A, $B", IIC_LdStLoad, []>;
4480def LWZCIX : XForm_base_r3xo_memOp<31, 789, (outs gprc:$RST),
4481                                  (ins gprc:$A, gprc:$B),
4482                                  "lwzcix $RST, $A, $B", IIC_LdStLoad, []>;
4483def LDCIX :  XForm_base_r3xo_memOp<31, 885, (outs gprc:$RST),
4484                                  (ins gprc:$A, gprc:$B),
4485                                  "ldcix $RST, $A, $B", IIC_LdStLoad, []>;
4486
4487def STBCIX : XForm_base_r3xo_memOp<31, 981, (outs),
4488                                  (ins gprc:$RST, gprc:$A, gprc:$B),
4489                                  "stbcix $RST, $A, $B", IIC_LdStLoad, []>;
4490def STHCIX : XForm_base_r3xo_memOp<31, 949, (outs),
4491                                  (ins gprc:$RST, gprc:$A, gprc:$B),
4492                                  "sthcix $RST, $A, $B", IIC_LdStLoad, []>;
4493def STWCIX : XForm_base_r3xo_memOp<31, 917, (outs),
4494                                  (ins gprc:$RST, gprc:$A, gprc:$B),
4495                                  "stwcix $RST, $A, $B", IIC_LdStLoad, []>;
4496def STDCIX : XForm_base_r3xo_memOp<31, 1013, (outs),
4497                                  (ins gprc:$RST, gprc:$A, gprc:$B),
4498                                  "stdcix $RST, $A, $B", IIC_LdStLoad, []>;
4499
4500// External PID Load Store Instructions
4501
4502def LBEPX   : XForm_1<31, 95, (outs gprc:$rD), (ins memrr:$src),
4503                      "lbepx $rD, $src", IIC_LdStLoad, []>,
4504                      Requires<[IsE500]>;
4505
4506def LFDEPX  : XForm_25<31, 607, (outs f8rc:$frD), (ins memrr:$src),
4507                      "lfdepx $frD, $src", IIC_LdStLFD, []>,
4508                      Requires<[IsE500]>;
4509
4510def LHEPX   : XForm_1<31, 287, (outs gprc:$rD), (ins memrr:$src),
4511                      "lhepx $rD, $src", IIC_LdStLoad, []>,
4512                      Requires<[IsE500]>;
4513
4514def LWEPX   : XForm_1<31, 31, (outs gprc:$rD), (ins memrr:$src),
4515                      "lwepx $rD, $src", IIC_LdStLoad, []>,
4516                      Requires<[IsE500]>;
4517
4518def STBEPX  : XForm_8<31, 223, (outs), (ins gprc:$rS, memrr:$dst),
4519                      "stbepx $rS, $dst", IIC_LdStStore, []>,
4520                      Requires<[IsE500]>;
4521
4522def STFDEPX : XForm_28_memOp<31, 735, (outs), (ins f8rc:$frS, memrr:$dst),
4523                      "stfdepx $frS, $dst", IIC_LdStSTFD, []>,
4524                      Requires<[IsE500]>;
4525
4526def STHEPX  : XForm_8<31, 415, (outs), (ins gprc:$rS, memrr:$dst),
4527                      "sthepx $rS, $dst", IIC_LdStStore, []>,
4528                      Requires<[IsE500]>;
4529
4530def STWEPX  : XForm_8<31, 159, (outs), (ins gprc:$rS, memrr:$dst),
4531                      "stwepx $rS, $dst", IIC_LdStStore, []>,
4532                      Requires<[IsE500]>;
4533
4534def DCBFEP  : DCB_Form<127, 0, (outs), (ins memrr:$dst), "dcbfep $dst",
4535                      IIC_LdStDCBF, []>, Requires<[IsE500]>;
4536
4537def DCBSTEP : DCB_Form<63, 0, (outs), (ins memrr:$dst), "dcbstep $dst",
4538                      IIC_LdStDCBF, []>, Requires<[IsE500]>;
4539
4540def DCBTEP  : DCB_Form_hint<319, (outs), (ins memrr:$dst, u5imm:$TH),
4541                      "dcbtep $TH, $dst", IIC_LdStDCBF, []>,
4542                      Requires<[IsE500]>;
4543
4544def DCBTSTEP : DCB_Form_hint<255, (outs), (ins memrr:$dst, u5imm:$TH),
4545                      "dcbtstep $TH, $dst", IIC_LdStDCBF, []>,
4546                      Requires<[IsE500]>;
4547
4548def DCBZEP  : DCB_Form<1023, 0, (outs), (ins memrr:$dst), "dcbzep $dst",
4549                      IIC_LdStDCBF, []>, Requires<[IsE500]>;
4550
4551def DCBZLEP : DCB_Form<1023, 1, (outs), (ins memrr:$dst), "dcbzlep $dst",
4552                      IIC_LdStDCBF, []>, Requires<[IsE500]>;
4553
4554def ICBIEP  : XForm_1a<31, 991, (outs), (ins memrr:$src), "icbiep $src",
4555                      IIC_LdStICBI, []>, Requires<[IsE500]>;
4556
4557//===----------------------------------------------------------------------===//
4558// PowerPC Assembler Instruction Aliases
4559//
4560
4561// Pseudo-instructions for alternate assembly syntax (never used by codegen).
4562// These are aliases that require C++ handling to convert to the target
4563// instruction, while InstAliases can be handled directly by tblgen.
4564class PPCAsmPseudo<string asm, dag iops>
4565  : Instruction {
4566  let Namespace = "PPC";
4567  bit PPC64 = 0;  // Default value, override with isPPC64
4568
4569  let OutOperandList = (outs);
4570  let InOperandList = iops;
4571  let Pattern = [];
4572  let AsmString = asm;
4573  let isAsmParserOnly = 1;
4574  let isPseudo = 1;
4575  let hasNoSchedulingInfo = 1;
4576}
4577
4578def : InstAlias<"sc", (SC 0)>;
4579
4580def : InstAlias<"sync", (SYNC 0)>, Requires<[HasSYNC]>;
4581def : InstAlias<"msync", (SYNC 0), 0>, Requires<[HasSYNC]>;
4582def : InstAlias<"lwsync", (SYNC 1)>, Requires<[HasSYNC]>;
4583def : InstAlias<"ptesync", (SYNC 2)>, Requires<[HasSYNC]>;
4584
4585def : InstAlias<"wait", (WAIT 0)>;
4586def : InstAlias<"waitrsv", (WAIT 1)>;
4587def : InstAlias<"waitimpl", (WAIT 2)>;
4588
4589def : InstAlias<"mbar", (MBAR 0)>, Requires<[IsBookE]>;
4590
4591def DCBTx   : PPCAsmPseudo<"dcbt $dst", (ins memrr:$dst)>;
4592def DCBTSTx : PPCAsmPseudo<"dcbtst $dst", (ins memrr:$dst)>;
4593
4594def DCBTCT : PPCAsmPseudo<"dcbtct $dst, $TH", (ins memrr:$dst, u5imm:$TH)>;
4595def DCBTDS : PPCAsmPseudo<"dcbtds $dst, $TH", (ins memrr:$dst, u5imm:$TH)>;
4596def DCBTT  : PPCAsmPseudo<"dcbtt $dst", (ins memrr:$dst)>;
4597
4598def DCBTSTCT : PPCAsmPseudo<"dcbtstct $dst, $TH", (ins memrr:$dst, u5imm:$TH)>;
4599def DCBTSTDS : PPCAsmPseudo<"dcbtstds $dst, $TH", (ins memrr:$dst, u5imm:$TH)>;
4600def DCBTSTT  : PPCAsmPseudo<"dcbtstt $dst", (ins memrr:$dst)>;
4601
4602def DCBFx  : PPCAsmPseudo<"dcbf $dst", (ins memrr:$dst)>;
4603def DCBFL  : PPCAsmPseudo<"dcbfl $dst", (ins memrr:$dst)>;
4604def DCBFLP : PPCAsmPseudo<"dcbflp $dst", (ins memrr:$dst)>;
4605
4606def : Pat<(int_ppc_isync),  (ISYNC)>;
4607def : Pat<(int_ppc_dcbfl xoaddr:$dst),
4608          (DCBF 1, xoaddr:$dst)>;
4609def : Pat<(int_ppc_dcbflp xoaddr:$dst),
4610          (DCBF 3, xoaddr:$dst)>;
4611
4612let Predicates = [IsISA3_1] in {
4613  def DCBFPS  : PPCAsmPseudo<"dcbfps $dst", (ins memrr:$dst)>;
4614  def DCBSTPS : PPCAsmPseudo<"dcbstps $dst", (ins memrr:$dst)>;
4615
4616  def : Pat<(int_ppc_dcbfps xoaddr:$dst),
4617            (DCBF 4, xoaddr:$dst)>;
4618  def : Pat<(int_ppc_dcbstps xoaddr:$dst),
4619            (DCBF 6, xoaddr:$dst)>;
4620}
4621
4622def : InstAlias<"crset $bx", (CREQV crbitrc:$bx, crbitrc:$bx, crbitrc:$bx)>;
4623def : InstAlias<"crclr $bx", (CRXOR crbitrc:$bx, crbitrc:$bx, crbitrc:$bx)>;
4624def : InstAlias<"crmove $bx, $by", (CROR crbitrc:$bx, crbitrc:$by, crbitrc:$by)>;
4625def : InstAlias<"crnot $bx, $by", (CRNOR crbitrc:$bx, crbitrc:$by, crbitrc:$by)>;
4626
4627def : InstAlias<"mftb $Rx", (MFTB gprc:$Rx, 268)>;
4628def : InstAlias<"mftbl $Rx", (MFTB gprc:$Rx, 268)>;
4629def : InstAlias<"mftbu $Rx", (MFTB gprc:$Rx, 269)>;
4630
4631def : InstAlias<"xnop", (XORI R0, R0, 0)>;
4632
4633foreach BR = 0-7 in {
4634    def : InstAlias<"mfbr"#BR#" $Rx",
4635                    (MFDCR gprc:$Rx, !add(BR, 0x80))>,
4636                    Requires<[IsPPC4xx]>;
4637    def : InstAlias<"mtbr"#BR#" $Rx",
4638                    (MTDCR gprc:$Rx, !add(BR, 0x80))>,
4639                    Requires<[IsPPC4xx]>;
4640}
4641
4642def : InstAlias<"mtmsrd $RS", (MTMSRD gprc:$RS, 0)>;
4643def : InstAlias<"mtmsr $RS", (MTMSR gprc:$RS, 0)>;
4644
4645def : InstAlias<"mtxer $Rx", (MTSPR 1, gprc:$Rx)>;
4646def : InstAlias<"mfxer $Rx", (MFSPR gprc:$Rx, 1)>;
4647
4648def : InstAlias<"mtudscr $Rx", (MTSPR 3, gprc:$Rx)>;
4649def : InstAlias<"mfudscr $Rx", (MFSPR gprc:$Rx, 3)>;
4650
4651def : InstAlias<"mfrtcu $Rx", (MFSPR gprc:$Rx, 4)>;
4652def : InstAlias<"mfrtcl $Rx", (MFSPR gprc:$Rx, 5)>;
4653
4654def : InstAlias<"mtlr $Rx", (MTSPR 8, gprc:$Rx)>;
4655def : InstAlias<"mflr $Rx", (MFSPR gprc:$Rx, 8)>;
4656
4657def : InstAlias<"mtctr $Rx", (MTSPR 9, gprc:$Rx)>;
4658def : InstAlias<"mfctr $Rx", (MFSPR gprc:$Rx, 9)>;
4659
4660def : InstAlias<"mtuamr $Rx", (MTSPR 13, gprc:$Rx)>;
4661def : InstAlias<"mfuamr $Rx", (MFSPR gprc:$Rx, 13)>;
4662
4663def : InstAlias<"mtdscr $Rx", (MTSPR 17, gprc:$Rx)>;
4664def : InstAlias<"mfdscr $Rx", (MFSPR gprc:$Rx, 17)>;
4665
4666def : InstAlias<"mtdsisr $Rx", (MTSPR 18, gprc:$Rx)>;
4667def : InstAlias<"mfdsisr $Rx", (MFSPR gprc:$Rx, 18)>;
4668
4669def : InstAlias<"mtdar $Rx", (MTSPR 19, gprc:$Rx)>;
4670def : InstAlias<"mfdar $Rx", (MFSPR gprc:$Rx, 19)>;
4671
4672def : InstAlias<"mtdec $Rx", (MTSPR 22, gprc:$Rx)>;
4673def : InstAlias<"mfdec $Rx", (MFSPR gprc:$Rx, 22)>;
4674
4675def : InstAlias<"mtsdr1 $Rx", (MTSPR 25, gprc:$Rx)>;
4676def : InstAlias<"mfsdr1 $Rx", (MFSPR gprc:$Rx, 25)>;
4677
4678def : InstAlias<"mtsrr0 $Rx", (MTSPR 26, gprc:$Rx)>;
4679def : InstAlias<"mfsrr0 $Rx", (MFSPR gprc:$Rx, 26)>;
4680
4681def : InstAlias<"mtsrr1 $Rx", (MTSPR 27, gprc:$Rx)>;
4682def : InstAlias<"mfsrr1 $Rx", (MFSPR gprc:$Rx, 27)>;
4683
4684def : InstAlias<"mtcfar $Rx", (MTSPR 28, gprc:$Rx)>;
4685def : InstAlias<"mfcfar $Rx", (MFSPR gprc:$Rx, 28)>;
4686
4687def : InstAlias<"mtamr $Rx", (MTSPR 29, gprc:$Rx)>;
4688def : InstAlias<"mfamr $Rx", (MFSPR gprc:$Rx, 29)>;
4689
4690def : InstAlias<"mtpid $Rx", (MTSPR 48, gprc:$Rx)>, Requires<[IsBookE]>;
4691def : InstAlias<"mfpid $Rx", (MFSPR gprc:$Rx, 48)>, Requires<[IsBookE]>;
4692
4693foreach SPRG = 4-7 in {
4694  def : InstAlias<"mfsprg $RT, "#SPRG, (MFSPR gprc:$RT, !add(SPRG, 256))>,
4695                  Requires<[IsBookE]>;
4696  def : InstAlias<"mfsprg"#SPRG#" $RT", (MFSPR gprc:$RT, !add(SPRG, 256))>,
4697                  Requires<[IsBookE]>;
4698  def : InstAlias<"mtsprg "#SPRG#", $RT", (MTSPR !add(SPRG, 256), gprc:$RT)>,
4699                  Requires<[IsBookE]>;
4700  def : InstAlias<"mtsprg"#SPRG#" $RT", (MTSPR !add(SPRG, 256), gprc:$RT)>,
4701                  Requires<[IsBookE]>;
4702}
4703
4704foreach SPRG = 0-3 in {
4705  def : InstAlias<"mfsprg $RT, "#SPRG, (MFSPR gprc:$RT, !add(SPRG, 272))>;
4706  def : InstAlias<"mfsprg"#SPRG#" $RT", (MFSPR gprc:$RT, !add(SPRG, 272))>;
4707  def : InstAlias<"mtsprg "#SPRG#", $RT", (MTSPR !add(SPRG, 272), gprc:$RT)>;
4708  def : InstAlias<"mtsprg"#SPRG#" $RT", (MTSPR !add(SPRG, 272), gprc:$RT)>;
4709}
4710
4711def : InstAlias<"mfasr $RT", (MFSPR gprc:$RT, 280)>;
4712def : InstAlias<"mtasr $RT", (MTSPR 280, gprc:$RT)>;
4713
4714def : InstAlias<"mttbl $Rx", (MTSPR 284, gprc:$Rx)>;
4715def : InstAlias<"mttbu $Rx", (MTSPR 285, gprc:$Rx)>;
4716
4717def : InstAlias<"mfpvr $RT", (MFSPR gprc:$RT, 287)>;
4718
4719def : InstAlias<"mfspefscr $Rx", (MFSPR gprc:$Rx, 512)>;
4720def : InstAlias<"mtspefscr $Rx", (MTSPR 512, gprc:$Rx)>;
4721
4722foreach BATR = 0-3 in {
4723    def : InstAlias<"mtdbatu "#BATR#", $Rx",
4724                    (MTSPR !add(BATR, !add(BATR, 536)), gprc:$Rx)>,
4725                    Requires<[IsPPC6xx]>;
4726    def : InstAlias<"mfdbatu $Rx, "#BATR,
4727                    (MFSPR gprc:$Rx, !add(BATR, !add(BATR, 536)))>,
4728                    Requires<[IsPPC6xx]>;
4729    def : InstAlias<"mtdbatl "#BATR#", $Rx",
4730                    (MTSPR !add(BATR, !add(BATR, 537)), gprc:$Rx)>,
4731                    Requires<[IsPPC6xx]>;
4732    def : InstAlias<"mfdbatl $Rx, "#BATR,
4733                    (MFSPR gprc:$Rx, !add(BATR, !add(BATR, 537)))>,
4734                    Requires<[IsPPC6xx]>;
4735    def : InstAlias<"mtibatu "#BATR#", $Rx",
4736                    (MTSPR !add(BATR, !add(BATR, 528)), gprc:$Rx)>,
4737                    Requires<[IsPPC6xx]>;
4738    def : InstAlias<"mfibatu $Rx, "#BATR,
4739                    (MFSPR gprc:$Rx, !add(BATR, !add(BATR, 528)))>,
4740                    Requires<[IsPPC6xx]>;
4741    def : InstAlias<"mtibatl "#BATR#", $Rx",
4742                    (MTSPR !add(BATR, !add(BATR, 529)), gprc:$Rx)>,
4743                    Requires<[IsPPC6xx]>;
4744    def : InstAlias<"mfibatl $Rx, "#BATR,
4745                    (MFSPR gprc:$Rx, !add(BATR, !add(BATR, 529)))>,
4746                    Requires<[IsPPC6xx]>;
4747}
4748
4749def : InstAlias<"mtppr $RT", (MTSPR 896, gprc:$RT)>;
4750def : InstAlias<"mfppr $RT", (MFSPR gprc:$RT, 896)>;
4751
4752def : InstAlias<"mtesr $Rx", (MTSPR 980, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4753def : InstAlias<"mfesr $Rx", (MFSPR gprc:$Rx, 980)>, Requires<[IsPPC4xx]>;
4754
4755def : InstAlias<"mtdear $Rx", (MTSPR 981, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4756def : InstAlias<"mfdear $Rx", (MFSPR gprc:$Rx, 981)>, Requires<[IsPPC4xx]>;
4757
4758def : InstAlias<"mttcr $Rx", (MTSPR 986, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4759def : InstAlias<"mftcr $Rx", (MFSPR gprc:$Rx, 986)>, Requires<[IsPPC4xx]>;
4760
4761def : InstAlias<"mftbhi $Rx", (MFSPR gprc:$Rx, 988)>, Requires<[IsPPC4xx]>;
4762def : InstAlias<"mttbhi $Rx", (MTSPR 988, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4763
4764def : InstAlias<"mftblo $Rx", (MFSPR gprc:$Rx, 989)>, Requires<[IsPPC4xx]>;
4765def : InstAlias<"mttblo $Rx", (MTSPR 989, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4766
4767def : InstAlias<"mtsrr2 $Rx", (MTSPR 990, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4768def : InstAlias<"mfsrr2 $Rx", (MFSPR gprc:$Rx, 990)>, Requires<[IsPPC4xx]>;
4769
4770def : InstAlias<"mtsrr3 $Rx", (MTSPR 991, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4771def : InstAlias<"mfsrr3 $Rx", (MFSPR gprc:$Rx, 991)>, Requires<[IsPPC4xx]>;
4772
4773def : InstAlias<"mtdccr $Rx", (MTSPR 1018, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4774def : InstAlias<"mfdccr $Rx", (MFSPR gprc:$Rx, 1018)>, Requires<[IsPPC4xx]>;
4775
4776def : InstAlias<"mticcr $Rx", (MTSPR 1019, gprc:$Rx)>, Requires<[IsPPC4xx]>;
4777def : InstAlias<"mficcr $Rx", (MFSPR gprc:$Rx, 1019)>, Requires<[IsPPC4xx]>;
4778
4779
4780def : InstAlias<"tlbie $RB", (TLBIE R0, gprc:$RB)>;
4781
4782def : InstAlias<"tlbrehi $RS, $A", (TLBRE2 gprc:$RS, gprc:$A, 0)>,
4783                Requires<[IsPPC4xx]>;
4784def : InstAlias<"tlbrelo $RS, $A", (TLBRE2 gprc:$RS, gprc:$A, 1)>,
4785                Requires<[IsPPC4xx]>;
4786def : InstAlias<"tlbwehi $RS, $A", (TLBWE2 gprc:$RS, gprc:$A, 0)>,
4787                Requires<[IsPPC4xx]>;
4788def : InstAlias<"tlbwelo $RS, $A", (TLBWE2 gprc:$RS, gprc:$A, 1)>,
4789                Requires<[IsPPC4xx]>;
4790
4791def LAx : PPCAsmPseudo<"la $rA, $addr", (ins gprc:$rA, memri:$addr)>;
4792
4793def SUBI : PPCAsmPseudo<"subi $rA, $rB, $imm",
4794                        (ins gprc:$rA, gprc:$rB, s16imm:$imm)>;
4795def SUBIS : PPCAsmPseudo<"subis $rA, $rB, $imm",
4796                         (ins gprc:$rA, gprc:$rB, s16imm:$imm)>;
4797def SUBIC : PPCAsmPseudo<"subic $rA, $rB, $imm",
4798                         (ins gprc:$rA, gprc:$rB, s16imm:$imm)>;
4799def SUBIC_rec : PPCAsmPseudo<"subic. $rA, $rB, $imm",
4800                          (ins gprc:$rA, gprc:$rB, s16imm:$imm)>;
4801
4802def EXTLWI : PPCAsmPseudo<"extlwi $rA, $rS, $n, $b",
4803                          (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4804def EXTLWI_rec : PPCAsmPseudo<"extlwi. $rA, $rS, $n, $b",
4805                           (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4806def EXTRWI : PPCAsmPseudo<"extrwi $rA, $rS, $n, $b",
4807                          (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4808def EXTRWI_rec : PPCAsmPseudo<"extrwi. $rA, $rS, $n, $b",
4809                           (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4810def INSLWI : PPCAsmPseudo<"inslwi $rA, $rS, $n, $b",
4811                          (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4812def INSLWI_rec : PPCAsmPseudo<"inslwi. $rA, $rS, $n, $b",
4813                           (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4814def INSRWI : PPCAsmPseudo<"insrwi $rA, $rS, $n, $b",
4815                          (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4816def INSRWI_rec : PPCAsmPseudo<"insrwi. $rA, $rS, $n, $b",
4817                           (ins gprc:$rA, gprc:$rS, u5imm:$n, u5imm:$b)>;
4818def ROTRWI : PPCAsmPseudo<"rotrwi $rA, $rS, $n",
4819                          (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4820def ROTRWI_rec : PPCAsmPseudo<"rotrwi. $rA, $rS, $n",
4821                           (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4822def SLWI : PPCAsmPseudo<"slwi $rA, $rS, $n",
4823                        (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4824def SLWI_rec : PPCAsmPseudo<"slwi. $rA, $rS, $n",
4825                         (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4826def SRWI : PPCAsmPseudo<"srwi $rA, $rS, $n",
4827                        (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4828def SRWI_rec : PPCAsmPseudo<"srwi. $rA, $rS, $n",
4829                         (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4830def CLRRWI : PPCAsmPseudo<"clrrwi $rA, $rS, $n",
4831                          (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4832def CLRRWI_rec : PPCAsmPseudo<"clrrwi. $rA, $rS, $n",
4833                           (ins gprc:$rA, gprc:$rS, u5imm:$n)>;
4834def CLRLSLWI : PPCAsmPseudo<"clrlslwi $rA, $rS, $b, $n",
4835                            (ins gprc:$rA, gprc:$rS, u5imm:$b, u5imm:$n)>;
4836def CLRLSLWI_rec : PPCAsmPseudo<"clrlslwi. $rA, $rS, $b, $n",
4837                             (ins gprc:$rA, gprc:$rS, u5imm:$b, u5imm:$n)>;
4838
4839def : InstAlias<"isellt $rT, $rA, $rB",
4840                (ISEL gprc:$rT, gprc_nor0:$rA, gprc:$rB, CR0LT)>;
4841def : InstAlias<"iselgt $rT, $rA, $rB",
4842                (ISEL gprc:$rT, gprc_nor0:$rA, gprc:$rB, CR0GT)>;
4843def : InstAlias<"iseleq $rT, $rA, $rB",
4844                (ISEL gprc:$rT, gprc_nor0:$rA, gprc:$rB, CR0EQ)>;
4845
4846def : InstAlias<"rotlwi $rA, $rS, $n", (RLWINM gprc:$rA, gprc:$rS, u5imm:$n, 0, 31)>;
4847def : InstAlias<"rotlwi. $rA, $rS, $n", (RLWINM_rec gprc:$rA, gprc:$rS, u5imm:$n, 0, 31)>;
4848def : InstAlias<"rotlw $rA, $rS, $rB", (RLWNM gprc:$rA, gprc:$rS, gprc:$rB, 0, 31)>;
4849def : InstAlias<"rotlw. $rA, $rS, $rB", (RLWNM_rec gprc:$rA, gprc:$rS, gprc:$rB, 0, 31)>;
4850def : InstAlias<"clrlwi $rA, $rS, $n", (RLWINM gprc:$rA, gprc:$rS, 0, u5imm:$n, 31)>;
4851def : InstAlias<"clrlwi. $rA, $rS, $n", (RLWINM_rec gprc:$rA, gprc:$rS, 0, u5imm:$n, 31)>;
4852
4853def : InstAlias<"cntlzw $rA, $rS", (CNTLZW gprc:$rA, gprc:$rS)>;
4854def : InstAlias<"cntlzw. $rA, $rS", (CNTLZW_rec gprc:$rA, gprc:$rS)>;
4855// The POWER variant
4856def : MnemonicAlias<"cntlz",  "cntlzw">;
4857def : MnemonicAlias<"cntlz.", "cntlzw.">;
4858
4859def EXTLDI : PPCAsmPseudo<"extldi $rA, $rS, $n, $b",
4860                          (ins g8rc:$rA, g8rc:$rS, u6imm:$n, u6imm:$b)>;
4861def EXTLDI_rec : PPCAsmPseudo<"extldi. $rA, $rS, $n, $b",
4862                           (ins g8rc:$rA, g8rc:$rS, u6imm:$n, u6imm:$b)>;
4863def EXTRDI : PPCAsmPseudo<"extrdi $rA, $rS, $n, $b",
4864                          (ins g8rc:$rA, g8rc:$rS, u6imm:$n, u6imm:$b)>;
4865def EXTRDI_rec : PPCAsmPseudo<"extrdi. $rA, $rS, $n, $b",
4866                           (ins g8rc:$rA, g8rc:$rS, u6imm:$n, u6imm:$b)>;
4867def INSRDI : PPCAsmPseudo<"insrdi $rA, $rS, $n, $b",
4868                          (ins g8rc:$rA, g8rc:$rS, u6imm:$n, u6imm:$b)>;
4869def INSRDI_rec : PPCAsmPseudo<"insrdi. $rA, $rS, $n, $b",
4870                           (ins g8rc:$rA, g8rc:$rS, u6imm:$n, u6imm:$b)>;
4871def ROTRDI : PPCAsmPseudo<"rotrdi $rA, $rS, $n",
4872                          (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4873def ROTRDI_rec : PPCAsmPseudo<"rotrdi. $rA, $rS, $n",
4874                           (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4875def SLDI : PPCAsmPseudo<"sldi $rA, $rS, $n",
4876                        (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4877def SLDI_rec : PPCAsmPseudo<"sldi. $rA, $rS, $n",
4878                         (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4879def SRDI : PPCAsmPseudo<"srdi $rA, $rS, $n",
4880                        (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4881def SRDI_rec : PPCAsmPseudo<"srdi. $rA, $rS, $n",
4882                         (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4883def CLRRDI : PPCAsmPseudo<"clrrdi $rA, $rS, $n",
4884                          (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4885def CLRRDI_rec : PPCAsmPseudo<"clrrdi. $rA, $rS, $n",
4886                           (ins g8rc:$rA, g8rc:$rS, u6imm:$n)>;
4887def CLRLSLDI : PPCAsmPseudo<"clrlsldi $rA, $rS, $b, $n",
4888                            (ins g8rc:$rA, g8rc:$rS, u6imm:$b, u6imm:$n)>;
4889def CLRLSLDI_rec : PPCAsmPseudo<"clrlsldi. $rA, $rS, $b, $n",
4890                             (ins g8rc:$rA, g8rc:$rS, u6imm:$b, u6imm:$n)>;
4891def SUBPCIS : PPCAsmPseudo<"subpcis $RT, $D", (ins g8rc:$RT, s16imm:$D)>;
4892
4893def : InstAlias<"rotldi $rA, $rS, $n", (RLDICL g8rc:$rA, g8rc:$rS, u6imm:$n, 0)>;
4894def : InstAlias<"rotldi $rA, $rS, $n",
4895                (RLDICL_32_64 g8rc:$rA, gprc:$rS, u6imm:$n, 0)>;
4896def : InstAlias<"rotldi. $rA, $rS, $n", (RLDICL_rec g8rc:$rA, g8rc:$rS, u6imm:$n, 0)>;
4897def : InstAlias<"rotld $rA, $rS, $rB", (RLDCL g8rc:$rA, g8rc:$rS, gprc:$rB, 0)>;
4898def : InstAlias<"rotld. $rA, $rS, $rB", (RLDCL_rec g8rc:$rA, g8rc:$rS, gprc:$rB, 0)>;
4899def : InstAlias<"clrldi $rA, $rS, $n", (RLDICL g8rc:$rA, g8rc:$rS, 0, u6imm:$n)>;
4900def : InstAlias<"clrldi $rA, $rS, $n",
4901                (RLDICL_32_64 g8rc:$rA, gprc:$rS, 0, u6imm:$n)>;
4902def : InstAlias<"clrldi. $rA, $rS, $n", (RLDICL_rec g8rc:$rA, g8rc:$rS, 0, u6imm:$n)>;
4903def : InstAlias<"lnia $RT", (ADDPCIS g8rc:$RT, 0)>;
4904
4905def RLWINMbm : PPCAsmPseudo<"rlwinm $rA, $rS, $n, $b",
4906                            (ins g8rc:$rA, g8rc:$rS, u5imm:$n, i32imm:$b)>;
4907def RLWINMbm_rec : PPCAsmPseudo<"rlwinm. $rA, $rS, $n, $b",
4908                            (ins g8rc:$rA, g8rc:$rS, u5imm:$n, i32imm:$b)>;
4909def RLWIMIbm : PPCAsmPseudo<"rlwimi $rA, $rS, $n, $b",
4910                           (ins g8rc:$rA, g8rc:$rS, u5imm:$n, i32imm:$b)>;
4911def RLWIMIbm_rec : PPCAsmPseudo<"rlwimi. $rA, $rS, $n, $b",
4912                            (ins g8rc:$rA, g8rc:$rS, u5imm:$n, i32imm:$b)>;
4913def RLWNMbm : PPCAsmPseudo<"rlwnm $rA, $rS, $n, $b",
4914                          (ins g8rc:$rA, g8rc:$rS, u5imm:$n, i32imm:$b)>;
4915def RLWNMbm_rec : PPCAsmPseudo<"rlwnm. $rA, $rS, $n, $b",
4916                           (ins g8rc:$rA, g8rc:$rS, u5imm:$n, i32imm:$b)>;
4917
4918// These generic branch instruction forms are used for the assembler parser only.
4919// Defs and Uses are conservative, since we don't know the BO value.
4920let PPC970_Unit = 7, isBranch = 1 in {
4921  let Defs = [CTR], Uses = [CTR, RM] in {
4922    def gBC : BForm_3<16, 0, 0, (outs),
4923                      (ins u5imm:$bo, crbitrc:$bi, condbrtarget:$dst),
4924                      "bc $bo, $bi, $dst">;
4925    def gBCA : BForm_3<16, 1, 0, (outs),
4926                       (ins u5imm:$bo, crbitrc:$bi, abscondbrtarget:$dst),
4927                       "bca $bo, $bi, $dst">;
4928    let isAsmParserOnly = 1 in {
4929      def gBCat : BForm_3_at<16, 0, 0, (outs),
4930                             (ins u5imm:$bo, atimm:$at, crbitrc:$bi,
4931                                  condbrtarget:$dst),
4932                                  "bc$at $bo, $bi, $dst">;
4933      def gBCAat : BForm_3_at<16, 1, 0, (outs),
4934                              (ins u5imm:$bo, atimm:$at, crbitrc:$bi,
4935                                   abscondbrtarget:$dst),
4936                                   "bca$at $bo, $bi, $dst">;
4937    } // isAsmParserOnly = 1
4938  }
4939  let Defs = [LR, CTR], Uses = [CTR, RM] in {
4940    def gBCL : BForm_3<16, 0, 1, (outs),
4941                       (ins u5imm:$bo, crbitrc:$bi, condbrtarget:$dst),
4942                       "bcl $bo, $bi, $dst">;
4943    def gBCLA : BForm_3<16, 1, 1, (outs),
4944                        (ins u5imm:$bo, crbitrc:$bi, abscondbrtarget:$dst),
4945                        "bcla $bo, $bi, $dst">;
4946    let isAsmParserOnly = 1 in {
4947      def gBCLat : BForm_3_at<16, 0, 1, (outs),
4948                         (ins u5imm:$bo, atimm:$at, crbitrc:$bi,
4949                              condbrtarget:$dst),
4950                              "bcl$at $bo, $bi, $dst">;
4951      def gBCLAat : BForm_3_at<16, 1, 1, (outs),
4952                          (ins u5imm:$bo, atimm:$at, crbitrc:$bi,
4953                               abscondbrtarget:$dst),
4954                               "bcla$at $bo, $bi, $dst">;
4955    } // // isAsmParserOnly = 1
4956  }
4957  let Defs = [CTR], Uses = [CTR, LR, RM] in
4958    def gBCLR : XLForm_2<19, 16, 0, (outs),
4959                         (ins u5imm:$bo, crbitrc:$bi, i32imm:$bh),
4960                         "bclr $bo, $bi, $bh", IIC_BrB, []>;
4961  let Defs = [LR, CTR], Uses = [CTR, LR, RM] in
4962    def gBCLRL : XLForm_2<19, 16, 1, (outs),
4963                          (ins u5imm:$bo, crbitrc:$bi, i32imm:$bh),
4964                          "bclrl $bo, $bi, $bh", IIC_BrB, []>;
4965  let Defs = [CTR], Uses = [CTR, LR, RM] in
4966    def gBCCTR : XLForm_2<19, 528, 0, (outs),
4967                          (ins u5imm:$bo, crbitrc:$bi, i32imm:$bh),
4968                          "bcctr $bo, $bi, $bh", IIC_BrB, []>;
4969  let Defs = [LR, CTR], Uses = [CTR, LR, RM] in
4970    def gBCCTRL : XLForm_2<19, 528, 1, (outs),
4971                           (ins u5imm:$bo, crbitrc:$bi, i32imm:$bh),
4972                           "bcctrl $bo, $bi, $bh", IIC_BrB, []>;
4973}
4974
4975multiclass BranchSimpleMnemonicAT<string pm, int at> {
4976  def : InstAlias<"bc"#pm#" $bo, $bi, $dst", (gBCat u5imm:$bo, at, crbitrc:$bi,
4977                                                    condbrtarget:$dst)>;
4978  def : InstAlias<"bca"#pm#" $bo, $bi, $dst", (gBCAat u5imm:$bo, at, crbitrc:$bi,
4979                                                      condbrtarget:$dst)>;
4980  def : InstAlias<"bcl"#pm#" $bo, $bi, $dst", (gBCLat u5imm:$bo, at, crbitrc:$bi,
4981                                                      condbrtarget:$dst)>;
4982  def : InstAlias<"bcla"#pm#" $bo, $bi, $dst", (gBCLAat u5imm:$bo, at, crbitrc:$bi,
4983                                                        condbrtarget:$dst)>;
4984}
4985defm : BranchSimpleMnemonicAT<"+", 3>;
4986defm : BranchSimpleMnemonicAT<"-", 2>;
4987
4988def : InstAlias<"bclr $bo, $bi", (gBCLR u5imm:$bo, crbitrc:$bi, 0)>;
4989def : InstAlias<"bclrl $bo, $bi", (gBCLRL u5imm:$bo, crbitrc:$bi, 0)>;
4990def : InstAlias<"bcctr $bo, $bi", (gBCCTR u5imm:$bo, crbitrc:$bi, 0)>;
4991def : InstAlias<"bcctrl $bo, $bi", (gBCCTRL u5imm:$bo, crbitrc:$bi, 0)>;
4992
4993multiclass BranchSimpleMnemonic1<string name, string pm, int bo> {
4994  def : InstAlias<"b"#name#pm#" $bi, $dst", (gBC bo, crbitrc:$bi, condbrtarget:$dst)>;
4995  def : InstAlias<"b"#name#"a"#pm#" $bi, $dst", (gBCA bo, crbitrc:$bi, abscondbrtarget:$dst)>;
4996  def : InstAlias<"b"#name#"lr"#pm#" $bi", (gBCLR bo, crbitrc:$bi, 0)>;
4997  def : InstAlias<"b"#name#"l"#pm#" $bi, $dst", (gBCL bo, crbitrc:$bi, condbrtarget:$dst)>;
4998  def : InstAlias<"b"#name#"la"#pm#" $bi, $dst", (gBCLA bo, crbitrc:$bi, abscondbrtarget:$dst)>;
4999  def : InstAlias<"b"#name#"lrl"#pm#" $bi", (gBCLRL bo, crbitrc:$bi, 0)>;
5000}
5001multiclass BranchSimpleMnemonic2<string name, string pm, int bo>
5002  : BranchSimpleMnemonic1<name, pm, bo> {
5003  def : InstAlias<"b"#name#"ctr"#pm#" $bi", (gBCCTR bo, crbitrc:$bi, 0)>;
5004  def : InstAlias<"b"#name#"ctrl"#pm#" $bi", (gBCCTRL bo, crbitrc:$bi, 0)>;
5005}
5006defm : BranchSimpleMnemonic2<"t", "", 12>;
5007defm : BranchSimpleMnemonic2<"f", "", 4>;
5008defm : BranchSimpleMnemonic2<"t", "-", 14>;
5009defm : BranchSimpleMnemonic2<"f", "-", 6>;
5010defm : BranchSimpleMnemonic2<"t", "+", 15>;
5011defm : BranchSimpleMnemonic2<"f", "+", 7>;
5012defm : BranchSimpleMnemonic1<"dnzt", "", 8>;
5013defm : BranchSimpleMnemonic1<"dnzf", "", 0>;
5014defm : BranchSimpleMnemonic1<"dzt", "", 10>;
5015defm : BranchSimpleMnemonic1<"dzf", "", 2>;
5016
5017multiclass BranchExtendedMnemonicPM<string name, string pm, int bibo> {
5018  def : InstAlias<"b"#name#pm#" $cc, $dst",
5019                  (BCC bibo, crrc:$cc, condbrtarget:$dst)>;
5020  def : InstAlias<"b"#name#pm#" $dst",
5021                  (BCC bibo, CR0, condbrtarget:$dst)>;
5022
5023  def : InstAlias<"b"#name#"a"#pm#" $cc, $dst",
5024                  (BCCA bibo, crrc:$cc, abscondbrtarget:$dst)>;
5025  def : InstAlias<"b"#name#"a"#pm#" $dst",
5026                  (BCCA bibo, CR0, abscondbrtarget:$dst)>;
5027
5028  def : InstAlias<"b"#name#"lr"#pm#" $cc",
5029                  (BCCLR bibo, crrc:$cc)>;
5030  def : InstAlias<"b"#name#"lr"#pm,
5031                  (BCCLR bibo, CR0)>;
5032
5033  def : InstAlias<"b"#name#"ctr"#pm#" $cc",
5034                  (BCCCTR bibo, crrc:$cc)>;
5035  def : InstAlias<"b"#name#"ctr"#pm,
5036                  (BCCCTR bibo, CR0)>;
5037
5038  def : InstAlias<"b"#name#"l"#pm#" $cc, $dst",
5039                  (BCCL bibo, crrc:$cc, condbrtarget:$dst)>;
5040  def : InstAlias<"b"#name#"l"#pm#" $dst",
5041                  (BCCL bibo, CR0, condbrtarget:$dst)>;
5042
5043  def : InstAlias<"b"#name#"la"#pm#" $cc, $dst",
5044                  (BCCLA bibo, crrc:$cc, abscondbrtarget:$dst)>;
5045  def : InstAlias<"b"#name#"la"#pm#" $dst",
5046                  (BCCLA bibo, CR0, abscondbrtarget:$dst)>;
5047
5048  def : InstAlias<"b"#name#"lrl"#pm#" $cc",
5049                  (BCCLRL bibo, crrc:$cc)>;
5050  def : InstAlias<"b"#name#"lrl"#pm,
5051                  (BCCLRL bibo, CR0)>;
5052
5053  def : InstAlias<"b"#name#"ctrl"#pm#" $cc",
5054                  (BCCCTRL bibo, crrc:$cc)>;
5055  def : InstAlias<"b"#name#"ctrl"#pm,
5056                  (BCCCTRL bibo, CR0)>;
5057}
5058multiclass BranchExtendedMnemonic<string name, int bibo> {
5059  defm : BranchExtendedMnemonicPM<name, "", bibo>;
5060  defm : BranchExtendedMnemonicPM<name, "-", !add(bibo, 2)>;
5061  defm : BranchExtendedMnemonicPM<name, "+", !add(bibo, 3)>;
5062}
5063defm : BranchExtendedMnemonic<"lt", 12>;
5064defm : BranchExtendedMnemonic<"gt", 44>;
5065defm : BranchExtendedMnemonic<"eq", 76>;
5066defm : BranchExtendedMnemonic<"un", 108>;
5067defm : BranchExtendedMnemonic<"so", 108>;
5068defm : BranchExtendedMnemonic<"ge", 4>;
5069defm : BranchExtendedMnemonic<"nl", 4>;
5070defm : BranchExtendedMnemonic<"le", 36>;
5071defm : BranchExtendedMnemonic<"ng", 36>;
5072defm : BranchExtendedMnemonic<"ne", 68>;
5073defm : BranchExtendedMnemonic<"nu", 100>;
5074defm : BranchExtendedMnemonic<"ns", 100>;
5075
5076def : InstAlias<"cmpwi $rA, $imm", (CMPWI CR0, gprc:$rA, s16imm:$imm)>;
5077def : InstAlias<"cmpw $rA, $rB", (CMPW CR0, gprc:$rA, gprc:$rB)>;
5078def : InstAlias<"cmplwi $rA, $imm", (CMPLWI CR0, gprc:$rA, u16imm:$imm)>;
5079def : InstAlias<"cmplw $rA, $rB", (CMPLW CR0, gprc:$rA, gprc:$rB)>;
5080def : InstAlias<"cmpdi $rA, $imm", (CMPDI CR0, g8rc:$rA, s16imm64:$imm)>;
5081def : InstAlias<"cmpd $rA, $rB", (CMPD CR0, g8rc:$rA, g8rc:$rB)>;
5082def : InstAlias<"cmpldi $rA, $imm", (CMPLDI CR0, g8rc:$rA, u16imm64:$imm)>;
5083def : InstAlias<"cmpld $rA, $rB", (CMPLD CR0, g8rc:$rA, g8rc:$rB)>;
5084
5085def : InstAlias<"cmpi $bf, 0, $rA, $imm", (CMPWI crrc:$bf, gprc:$rA, s16imm:$imm)>;
5086def : InstAlias<"cmp $bf, 0, $rA, $rB", (CMPW crrc:$bf, gprc:$rA, gprc:$rB)>;
5087def : InstAlias<"cmpli $bf, 0, $rA, $imm", (CMPLWI crrc:$bf, gprc:$rA, u16imm:$imm)>;
5088def : InstAlias<"cmpl $bf, 0, $rA, $rB", (CMPLW crrc:$bf, gprc:$rA, gprc:$rB)>;
5089def : InstAlias<"cmpi $bf, 1, $rA, $imm", (CMPDI crrc:$bf, g8rc:$rA, s16imm64:$imm)>;
5090def : InstAlias<"cmp $bf, 1, $rA, $rB", (CMPD crrc:$bf, g8rc:$rA, g8rc:$rB)>;
5091def : InstAlias<"cmpli $bf, 1, $rA, $imm", (CMPLDI crrc:$bf, g8rc:$rA, u16imm64:$imm)>;
5092def : InstAlias<"cmpl $bf, 1, $rA, $rB", (CMPLD crrc:$bf, g8rc:$rA, g8rc:$rB)>;
5093
5094def : InstAlias<"trap", (TW 31, R0, R0)>;
5095
5096multiclass TrapExtendedMnemonic<string name, int to> {
5097  def : InstAlias<"td"#name#"i $rA, $imm", (TDI to, g8rc:$rA, s16imm:$imm)>;
5098  def : InstAlias<"td"#name#" $rA, $rB", (TD to, g8rc:$rA, g8rc:$rB)>;
5099  def : InstAlias<"tw"#name#"i $rA, $imm", (TWI to, gprc:$rA, s16imm:$imm)>;
5100  def : InstAlias<"tw"#name#" $rA, $rB", (TW to, gprc:$rA, gprc:$rB)>;
5101}
5102defm : TrapExtendedMnemonic<"lt", 16>;
5103defm : TrapExtendedMnemonic<"le", 20>;
5104defm : TrapExtendedMnemonic<"eq", 4>;
5105defm : TrapExtendedMnemonic<"ge", 12>;
5106defm : TrapExtendedMnemonic<"gt", 8>;
5107defm : TrapExtendedMnemonic<"nl", 12>;
5108defm : TrapExtendedMnemonic<"ne", 24>;
5109defm : TrapExtendedMnemonic<"ng", 20>;
5110defm : TrapExtendedMnemonic<"llt", 2>;
5111defm : TrapExtendedMnemonic<"lle", 6>;
5112defm : TrapExtendedMnemonic<"lge", 5>;
5113defm : TrapExtendedMnemonic<"lgt", 1>;
5114defm : TrapExtendedMnemonic<"lnl", 5>;
5115defm : TrapExtendedMnemonic<"lng", 6>;
5116defm : TrapExtendedMnemonic<"u", 31>;
5117
5118// Atomic loads
5119def : Pat<(atomic_load_8  iaddr:$src), (LBZ  memri:$src)>;
5120def : Pat<(atomic_load_16 iaddr:$src), (LHZ  memri:$src)>;
5121def : Pat<(atomic_load_32 iaddr:$src), (LWZ  memri:$src)>;
5122def : Pat<(atomic_load_8  xaddr:$src), (LBZX memrr:$src)>;
5123def : Pat<(atomic_load_16 xaddr:$src), (LHZX memrr:$src)>;
5124def : Pat<(atomic_load_32 xaddr:$src), (LWZX memrr:$src)>;
5125
5126// Atomic stores
5127def : Pat<(atomic_store_8  iaddr:$ptr, i32:$val), (STB  gprc:$val, memri:$ptr)>;
5128def : Pat<(atomic_store_16 iaddr:$ptr, i32:$val), (STH  gprc:$val, memri:$ptr)>;
5129def : Pat<(atomic_store_32 iaddr:$ptr, i32:$val), (STW  gprc:$val, memri:$ptr)>;
5130def : Pat<(atomic_store_8  xaddr:$ptr, i32:$val), (STBX gprc:$val, memrr:$ptr)>;
5131def : Pat<(atomic_store_16 xaddr:$ptr, i32:$val), (STHX gprc:$val, memrr:$ptr)>;
5132def : Pat<(atomic_store_32 xaddr:$ptr, i32:$val), (STWX gprc:$val, memrr:$ptr)>;
5133
5134let Predicates = [IsISA3_0] in {
5135
5136// Copy-Paste Facility
5137// We prefix 'CP' to COPY due to name conflict in Target.td. We also prefix to
5138// PASTE for naming consistency.
5139let mayLoad = 1 in
5140def CP_COPY   : X_L1_RA5_RB5<31, 774, "copy"  , gprc, IIC_LdStCOPY, []>;
5141
5142let mayStore = 1 in
5143def CP_PASTE  : X_L1_RA5_RB5<31, 902, "paste" , gprc, IIC_LdStPASTE, []>;
5144
5145let mayStore = 1, Defs = [CR0] in
5146def CP_PASTE_rec : X_L1_RA5_RB5<31, 902, "paste.", gprc, IIC_LdStPASTE, []>, isRecordForm;
5147
5148def CP_COPYx  : PPCAsmPseudo<"copy $rA, $rB" , (ins gprc:$rA, gprc:$rB)>;
5149def CP_PASTEx : PPCAsmPseudo<"paste $rA, $rB", (ins gprc:$rA, gprc:$rB)>;
5150def CP_COPY_FIRST : PPCAsmPseudo<"copy_first $rA, $rB",
5151                                  (ins gprc:$rA, gprc:$rB)>;
5152def CP_PASTE_LAST : PPCAsmPseudo<"paste_last $rA, $rB",
5153                                  (ins gprc:$rA, gprc:$rB)>;
5154def CP_ABORT : XForm_0<31, 838, (outs), (ins), "cp_abort", IIC_SprABORT, []>;
5155
5156// Message Synchronize
5157def MSGSYNC : XForm_0<31, 886, (outs), (ins), "msgsync", IIC_SprMSGSYNC, []>;
5158
5159// Power-Saving Mode Instruction:
5160def STOP : XForm_0<19, 370, (outs), (ins), "stop", IIC_SprSTOP, []>;
5161
5162} // IsISA3_0
5163
5164// Fast 32-bit reverse bits algorithm:
5165// Step 1: 1-bit swap (swap odd 1-bit and even 1-bit):
5166// n = ((n >> 1) & 0x55555555) | ((n << 1) & 0xAAAAAAAA);
5167// Step 2: 2-bit swap (swap odd 2-bit and even 2-bit):
5168// n = ((n >> 2) & 0x33333333) | ((n << 2) & 0xCCCCCCCC);
5169// Step 3: 4-bit swap (swap odd 4-bit and even 4-bit):
5170// n = ((n >> 4) & 0x0F0F0F0F) | ((n << 4) & 0xF0F0F0F0);
5171// Step 4: byte reverse (Suppose n = [B1,B2,B3,B4]):
5172// Step 4.1: Put B4,B2 in the right position (rotate left 3 bytes):
5173// n' = (n rotl 24);  After which n' = [B4, B1, B2, B3]
5174// Step 4.2: Insert B3 to the right position:
5175// n' = rlwimi n', n, 8, 8, 15;  After which n' = [B4, B3, B2, B3]
5176// Step 4.3: Insert B1 to the right position:
5177// n' = rlwimi n', n, 8, 24, 31;  After which n' = [B4, B3, B2, B1]
5178def MaskValues {
5179  dag Lo1 = (ORI (LIS 0x5555), 0x5555);
5180  dag Hi1 = (ORI (LIS 0xAAAA), 0xAAAA);
5181  dag Lo2 = (ORI (LIS 0x3333), 0x3333);
5182  dag Hi2 = (ORI (LIS 0xCCCC), 0xCCCC);
5183  dag Lo4 = (ORI (LIS 0x0F0F), 0x0F0F);
5184  dag Hi4 = (ORI (LIS 0xF0F0), 0xF0F0);
5185}
5186
5187def Shift1 {
5188  dag Right = (RLWINM $A, 31, 1, 31);
5189  dag Left = (RLWINM $A, 1, 0, 30);
5190}
5191
5192def Swap1 {
5193  dag Bit = (OR (AND Shift1.Right, MaskValues.Lo1),
5194   (AND Shift1.Left, MaskValues.Hi1));
5195}
5196
5197def Shift2 {
5198  dag Right = (RLWINM Swap1.Bit, 30, 2, 31);
5199  dag Left = (RLWINM Swap1.Bit, 2, 0, 29);
5200}
5201
5202def Swap2 {
5203  dag Bits = (OR (AND Shift2.Right, MaskValues.Lo2),
5204                 (AND Shift2.Left, MaskValues.Hi2));
5205}
5206
5207def Shift4 {
5208  dag Right = (RLWINM Swap2.Bits, 28, 4, 31);
5209  dag Left = (RLWINM Swap2.Bits, 4, 0, 27);
5210}
5211
5212def Swap4 {
5213  dag Bits = (OR (AND Shift4.Right, MaskValues.Lo4),
5214                 (AND Shift4.Left, MaskValues.Hi4));
5215}
5216
5217def Rotate {
5218  dag Left3Bytes = (RLWINM Swap4.Bits, 24, 0, 31);
5219}
5220
5221def RotateInsertByte3 {
5222  dag Left = (RLWIMI Rotate.Left3Bytes, Swap4.Bits, 8, 8, 15);
5223}
5224
5225def RotateInsertByte1 {
5226  dag Left = (RLWIMI RotateInsertByte3.Left, Swap4.Bits, 8, 24, 31);
5227}
5228
5229// Clear the upper half of the register when in 64-bit mode
5230let Predicates = [In64BitMode] in
5231def : Pat<(i32 (bitreverse i32:$A)), (RLDICL_32 RotateInsertByte1.Left, 0, 32)>;
5232let Predicates = [In32BitMode] in
5233def : Pat<(i32 (bitreverse i32:$A)), RotateInsertByte1.Left>;
5234
5235// Fast 64-bit reverse bits algorithm:
5236// Step 1: 1-bit swap (swap odd 1-bit and even 1-bit):
5237// n = ((n >> 1) & 0x5555555555555555) | ((n << 1) & 0xAAAAAAAAAAAAAAAA);
5238// Step 2: 2-bit swap (swap odd 2-bit and even 2-bit):
5239// n = ((n >> 2) & 0x3333333333333333) | ((n << 2) & 0xCCCCCCCCCCCCCCCC);
5240// Step 3: 4-bit swap (swap odd 4-bit and even 4-bit):
5241// n = ((n >> 4) & 0x0F0F0F0F0F0F0F0F) | ((n << 4) & 0xF0F0F0F0F0F0F0F0);
5242// Step 4: byte reverse (Suppose n = [B0,B1,B2,B3,B4,B5,B6,B7]):
5243// Apply the same byte reverse algorithm mentioned above for the fast 32-bit
5244// reverse to both the high 32 bit and low 32 bit of the 64 bit value. And
5245// then OR them together to get the final result.
5246def MaskValues64 {
5247  dag Lo1 = (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), MaskValues.Lo1, sub_32));
5248  dag Hi1 = (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), MaskValues.Hi1, sub_32));
5249  dag Lo2 = (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), MaskValues.Lo2, sub_32));
5250  dag Hi2 = (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), MaskValues.Hi2, sub_32));
5251  dag Lo4 = (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), MaskValues.Lo4, sub_32));
5252  dag Hi4 = (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), MaskValues.Hi4, sub_32));
5253}
5254
5255def DWMaskValues {
5256  dag Lo1 = (ORI8 (ORIS8 (RLDICR MaskValues64.Lo1, 32, 31), 0x5555), 0x5555);
5257  dag Hi1 = (ORI8 (ORIS8 (RLDICR MaskValues64.Hi1, 32, 31), 0xAAAA), 0xAAAA);
5258  dag Lo2 = (ORI8 (ORIS8 (RLDICR MaskValues64.Lo2, 32, 31), 0x3333), 0x3333);
5259  dag Hi2 = (ORI8 (ORIS8 (RLDICR MaskValues64.Hi2, 32, 31), 0xCCCC), 0xCCCC);
5260  dag Lo4 = (ORI8 (ORIS8 (RLDICR MaskValues64.Lo4, 32, 31), 0x0F0F), 0x0F0F);
5261  dag Hi4 = (ORI8 (ORIS8 (RLDICR MaskValues64.Hi4, 32, 31), 0xF0F0), 0xF0F0);
5262}
5263
5264def DWSwapInByte {
5265  dag Swap1 = (OR8 (AND8 (RLDICL $A, 63, 1), DWMaskValues.Lo1),
5266                   (AND8 (RLDICR $A, 1, 62), DWMaskValues.Hi1));
5267  dag Swap2 = (OR8 (AND8 (RLDICL Swap1, 62, 2), DWMaskValues.Lo2),
5268                   (AND8 (RLDICR Swap1, 2, 61), DWMaskValues.Hi2));
5269  dag Swap4 = (OR8 (AND8 (RLDICL Swap2, 60, 4), DWMaskValues.Lo4),
5270                   (AND8 (RLDICR Swap2, 4, 59), DWMaskValues.Hi4));
5271}
5272
5273// Intra-byte swap is done, now start inter-byte swap.
5274def DWBytes4567 {
5275  dag Word = (i32 (EXTRACT_SUBREG DWSwapInByte.Swap4, sub_32));
5276}
5277
5278def DWBytes7456 {
5279  dag Word = (RLWINM DWBytes4567.Word, 24, 0, 31);
5280}
5281
5282def DWBytes7656 {
5283  dag Word = (RLWIMI DWBytes7456.Word, DWBytes4567.Word, 8, 8, 15);
5284}
5285
5286// B7 B6 B5 B4 in the right order
5287def DWBytes7654 {
5288  dag Word = (RLWIMI DWBytes7656.Word, DWBytes4567.Word, 8, 24, 31);
5289  dag DWord =
5290    (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), Word, sub_32));
5291}
5292
5293def DWBytes0123 {
5294  dag Word = (i32 (EXTRACT_SUBREG (RLDICL DWSwapInByte.Swap4, 32, 32), sub_32));
5295}
5296
5297def DWBytes3012 {
5298  dag Word = (RLWINM DWBytes0123.Word, 24, 0, 31);
5299}
5300
5301def DWBytes3212 {
5302  dag Word = (RLWIMI DWBytes3012.Word, DWBytes0123.Word, 8, 8, 15);
5303}
5304
5305// B3 B2 B1 B0 in the right order
5306def DWBytes3210 {
5307  dag Word = (RLWIMI DWBytes3212.Word, DWBytes0123.Word, 8, 24, 31);
5308  dag DWord =
5309    (i64 (INSERT_SUBREG (i64 (IMPLICIT_DEF)), Word, sub_32));
5310}
5311
5312// Now both high word and low word are reversed, next
5313// swap the high word and low word.
5314def : Pat<(i64 (bitreverse i64:$A)),
5315  (OR8 (RLDICR DWBytes7654.DWord, 32, 31), DWBytes3210.DWord)>;
5316