Merge ISD::TRUNCSTORE to ISD::STORE. Switch to using StoreSDNode.
[oota-llvm.git] / lib / Target / Alpha / AlphaInstrInfo.td
1 //===- AlphaInstrInfo.td - The Alpha Instruction Set -------*- tablegen -*-===//
2 // 
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file was developed by the LLVM research group and is distributed under
6 // the University of Illinois Open Source License. See LICENSE.TXT for details.
7 // 
8 //===----------------------------------------------------------------------===//
9 //
10 //
11 //===----------------------------------------------------------------------===//
12
13 include "AlphaInstrFormats.td"
14
15 //********************
16 //Custom DAG Nodes
17 //********************
18
19 def SDTFPUnaryOpUnC  : SDTypeProfile<1, 1, [
20   SDTCisFP<1>, SDTCisFP<0>
21 ]>;
22 def Alpha_itoft   : SDNode<"AlphaISD::ITOFT_",    SDTIntToFPOp, []>;
23 def Alpha_ftoit   : SDNode<"AlphaISD::FTOIT_",    SDTFPToIntOp, []>;
24 def Alpha_cvtqt   : SDNode<"AlphaISD::CVTQT_",    SDTFPUnaryOpUnC, []>;
25 def Alpha_cvtqs   : SDNode<"AlphaISD::CVTQS_",    SDTFPUnaryOpUnC, []>;
26 def Alpha_cvttq   : SDNode<"AlphaISD::CVTTQ_"  ,  SDTFPUnaryOp, []>;
27 def Alpha_gprello : SDNode<"AlphaISD::GPRelLo",   SDTIntBinOp, []>;
28 def Alpha_gprelhi : SDNode<"AlphaISD::GPRelHi",   SDTIntBinOp, []>;
29 def Alpha_rellit  : SDNode<"AlphaISD::RelLit",    SDTIntBinOp, []>;
30
31 def retflag       : SDNode<"AlphaISD::RET_FLAG", SDTRet,
32                            [SDNPHasChain, SDNPOptInFlag]>;
33
34 // These are target-independent nodes, but have target-specific formats.
35 def SDT_AlphaCallSeq : SDTypeProfile<0, 1, [ SDTCisVT<0, i64> ]>;
36 def callseq_start : SDNode<"ISD::CALLSEQ_START", SDT_AlphaCallSeq,
37                            [SDNPHasChain, SDNPOutFlag]>;
38 def callseq_end   : SDNode<"ISD::CALLSEQ_END",   SDT_AlphaCallSeq,
39                            [SDNPHasChain, SDNPOutFlag]>;
40
41 //********************
42 //Paterns for matching
43 //********************
44 def invX : SDNodeXForm<imm, [{ //invert
45   return getI64Imm(~N->getValue());
46 }]>;
47 def negX : SDNodeXForm<imm, [{ //negate
48   return getI64Imm(~N->getValue() + 1);
49 }]>;
50 def SExt32 : SDNodeXForm<imm, [{ //signed extend int to long
51   return getI64Imm(((int64_t)N->getValue() << 32) >> 32);
52 }]>;
53 def SExt16 : SDNodeXForm<imm, [{ //signed extend int to long
54   return getI64Imm(((int64_t)N->getValue() << 48) >> 48);
55 }]>;
56 def LL16 : SDNodeXForm<imm, [{ //lda part of constant
57   return getI64Imm(get_lda16(N->getValue()));
58 }]>;
59 def LH16 : SDNodeXForm<imm, [{ //ldah part of constant (or more if too big)
60   return getI64Imm(get_ldah16(N->getValue()));
61 }]>;
62 def iZAPX : SDNodeXForm<and, [{ // get imm to ZAPi
63   ConstantSDNode *RHS = cast<ConstantSDNode>(N->getOperand(1));
64   return getI64Imm(get_zapImm(SDOperand(), RHS->getValue()));
65 }]>;
66 def nearP2X : SDNodeXForm<imm, [{
67   return getI64Imm(Log2_64(getNearPower2((uint64_t)N->getValue())));
68 }]>;
69 def nearP2RemX : SDNodeXForm<imm, [{
70   uint64_t x = abs(N->getValue() - getNearPower2((uint64_t)N->getValue()));
71   return getI64Imm(Log2_64(x));
72 }]>;
73
74 def immUExt8  : PatLeaf<(imm), [{ //imm fits in 8 bit zero extended field
75   return (uint64_t)N->getValue() == (uint8_t)N->getValue();
76 }]>;
77 def immUExt8inv  : PatLeaf<(imm), [{ //inverted imm fits in 8 bit zero extended field
78   return (uint64_t)~N->getValue() == (uint8_t)~N->getValue();
79 }], invX>;
80 def immUExt8neg  : PatLeaf<(imm), [{ //negated imm fits in 8 bit zero extended field
81   return ((uint64_t)~N->getValue() + 1) == (uint8_t)((uint64_t)~N->getValue() + 1);
82 }], negX>;
83 def immSExt16  : PatLeaf<(imm), [{ //imm fits in 16 bit sign extended field
84   return ((int64_t)N->getValue() << 48) >> 48 == (int64_t)N->getValue();
85 }]>;
86 def immSExt16int  : PatLeaf<(imm), [{ //(int)imm fits in a 16 bit sign extended field
87   return ((int64_t)N->getValue() << 48) >> 48 == ((int64_t)N->getValue() << 32) >> 32;
88 }], SExt16>;
89
90 def zappat : PatFrag<(ops node:$LHS), (and node:$LHS, imm:$L), [{
91   if (ConstantSDNode *RHS = dyn_cast<ConstantSDNode>(N->getOperand(1))) {
92     uint64_t build = get_zapImm(N->getOperand(0), (uint64_t)RHS->getValue());
93     return build != 0;
94   }
95   return false;
96 }]>;
97
98 def immFPZ  : PatLeaf<(fpimm), [{ //the only fpconstant nodes are +/- 0.0
99   return true;
100 }]>;
101 def immRem1 : PatLeaf<(imm), [{
102   return N->getValue() - getNearPower2((uint64_t)N->getValue()) == 1;
103 }]>;
104 def immRem3 : PatLeaf<(imm), [{
105   return N->getValue() - getNearPower2((uint64_t)N->getValue()) == 3;
106 }]>;
107 def immRem4 : PatLeaf<(imm), [{
108   return N->getValue() - getNearPower2((uint64_t)N->getValue()) == 4;
109 }]>;
110 def immRem5 : PatLeaf<(imm), [{
111   return N->getValue() - getNearPower2((uint64_t)N->getValue()) == 5;
112 }]>;
113 def immRem1n : PatLeaf<(imm), [{
114   return getNearPower2((uint64_t)N->getValue()) - N->getValue() == 1;
115 }]>;
116 def immRem3n : PatLeaf<(imm), [{
117   return getNearPower2((uint64_t)N->getValue()) - N->getValue() == 3;
118 }]>;
119 def immRem4n : PatLeaf<(imm), [{
120   return getNearPower2((uint64_t)N->getValue()) - N->getValue() == 4;
121 }]>;
122 def immRem5n : PatLeaf<(imm), [{
123   return getNearPower2((uint64_t)N->getValue()) - N->getValue() == 5;
124 }]>;
125 def immRemP2n : PatLeaf<(imm), [{
126   return isPowerOf2_64(getNearPower2((uint64_t)N->getValue()) - N->getValue());
127 }]>;
128 def immRemP2 : PatLeaf<(imm), [{
129   return isPowerOf2_64(N->getValue() - getNearPower2((uint64_t)N->getValue()));
130 }]>;
131 def immUExt8ME : PatLeaf<(imm), [{ //use this imm for mulqi
132   int64_t d =  abs((int64_t)N->getValue() - (int64_t)getNearPower2((uint64_t)N->getValue()));
133   if (isPowerOf2_64(d)) return false;
134   switch (d) {
135     case 1: case 3: case 5: return false; 
136     default: return (uint64_t)N->getValue() == (uint8_t)N->getValue();
137   };
138 }]>;
139
140 def intop : PatFrag<(ops node:$op), (sext_inreg node:$op, i32)>;
141 def add4  : PatFrag<(ops node:$op1, node:$op2),
142                     (add (shl node:$op1, 2), node:$op2)>;
143 def sub4  : PatFrag<(ops node:$op1, node:$op2),
144                     (sub (shl node:$op1, 2), node:$op2)>;
145 def add8  : PatFrag<(ops node:$op1, node:$op2),
146                     (add (shl node:$op1, 3), node:$op2)>;
147 def sub8  : PatFrag<(ops node:$op1, node:$op2),
148                     (sub (shl node:$op1, 3), node:$op2)>;
149
150
151 //Pseudo ops for selection
152
153 def IDEF_I : PseudoInstAlpha<(ops GPRC:$RA), "#idef $RA",
154              [(set GPRC:$RA, (undef))], s_pseudo>;
155 def IDEF_F32 : PseudoInstAlpha<(ops F4RC:$RA), "#idef $RA",
156              [(set F4RC:$RA, (undef))], s_pseudo>;
157 def IDEF_F64 : PseudoInstAlpha<(ops F8RC:$RA), "#idef $RA",
158              [(set F8RC:$RA, (undef))], s_pseudo>;
159
160 def WTF : PseudoInstAlpha<(ops variable_ops), "#wtf", [], s_pseudo>;
161
162 let isLoad = 1, hasCtrlDep = 1 in {
163 def ADJUSTSTACKUP : PseudoInstAlpha<(ops s64imm:$amt), "; ADJUP $amt", 
164                 [(callseq_start imm:$amt)], s_pseudo>, Imp<[R30],[R30]>;
165 def ADJUSTSTACKDOWN : PseudoInstAlpha<(ops s64imm:$amt), "; ADJDOWN $amt", 
166                 [(callseq_end imm:$amt)], s_pseudo>, Imp<[R30],[R30]>;
167 }
168 def ALTENT : PseudoInstAlpha<(ops s64imm:$TARGET), "$$$TARGET..ng:\n", [], s_pseudo>;
169 def PCLABEL : PseudoInstAlpha<(ops s64imm:$num), "PCMARKER_$num:\n",[], s_pseudo>;
170 def MEMLABEL : PseudoInstAlpha<(ops s64imm:$i, s64imm:$j, s64imm:$k, s64imm:$m),
171          "LSMARKER$$$i$$$j$$$k$$$m:", [], s_pseudo>;
172
173
174 //***********************
175 //Real instructions
176 //***********************
177
178 //Operation Form:
179
180 //conditional moves, int
181
182 def CMOVLBC  : OForm4<  0x11, 0x16, "cmovlbc $RCOND,$RTRUE,$RDEST",
183                 [(set GPRC:$RDEST, (select (xor GPRC:$RCOND, 1), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
184 def CMOVLBS  : OForm4<  0x11, 0x14, "cmovlbs $RCOND,$RTRUE,$RDEST",
185                 [(set GPRC:$RDEST, (select (and GPRC:$RCOND, 1), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
186 def CMOVEQ   : OForm4<  0x11, 0x24, "cmoveq $RCOND,$RTRUE,$RDEST",
187                 [(set GPRC:$RDEST, (select (seteq GPRC:$RCOND, 0), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
188 def CMOVGE   : OForm4<  0x11, 0x46, "cmovge $RCOND,$RTRUE,$RDEST",
189                 [(set GPRC:$RDEST, (select (setge GPRC:$RCOND, 0), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
190 def CMOVGT   : OForm4<  0x11, 0x66, "cmovgt $RCOND,$RTRUE,$RDEST",
191                 [(set GPRC:$RDEST, (select (setgt GPRC:$RCOND, 0), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
192 def CMOVLE   : OForm4<  0x11, 0x64, "cmovle $RCOND,$RTRUE,$RDEST",
193                 [(set GPRC:$RDEST, (select (setle GPRC:$RCOND, 0), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
194 def CMOVLT   : OForm4<  0x11, 0x44, "cmovlt $RCOND,$RTRUE,$RDEST",
195                 [(set GPRC:$RDEST, (select (setlt GPRC:$RCOND, 0), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
196 def CMOVNE   : OForm4<  0x11, 0x26, "cmovne $RCOND,$RTRUE,$RDEST",
197                 [(set GPRC:$RDEST, (select (setne GPRC:$RCOND, 0), GPRC:$RTRUE, GPRC:$RFALSE))], s_cmov>;
198
199 def CMOVEQi  : OForm4L< 0x11, 0x24, "cmoveq $RCOND,$RTRUE,$RDEST",
200                 [(set GPRC:$RDEST, (select (setne GPRC:$RCOND, 0), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
201 def CMOVGEi  : OForm4L< 0x11, 0x46, "cmovge $RCOND,$RTRUE,$RDEST",
202                 [(set GPRC:$RDEST, (select (setlt GPRC:$RCOND, 0), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
203 def CMOVGTi  : OForm4L< 0x11, 0x66, "cmovgt $RCOND,$RTRUE,$RDEST",
204                 [(set GPRC:$RDEST, (select (setle GPRC:$RCOND, 0), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
205 def CMOVLEi  : OForm4L< 0x11, 0x64, "cmovle $RCOND,$RTRUE,$RDEST",
206                 [(set GPRC:$RDEST, (select (setgt GPRC:$RCOND, 0), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
207 def CMOVLTi  : OForm4L< 0x11, 0x44, "cmovlt $RCOND,$RTRUE,$RDEST",
208                 [(set GPRC:$RDEST, (select (setge GPRC:$RCOND, 0), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
209 def CMOVNEi  : OForm4L< 0x11, 0x26, "cmovne $RCOND,$RTRUE,$RDEST",
210                 [(set GPRC:$RDEST, (select (seteq GPRC:$RCOND, 0), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
211 def CMOVLBCi : OForm4L< 0x11, 0x16, "cmovlbc $RCOND,$RTRUE,$RDEST",
212                 [(set GPRC:$RDEST, (select (and GPRC:$RCOND, 1), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
213 def CMOVLBSi : OForm4L< 0x11, 0x14, "cmovlbs $RCOND,$RTRUE,$RDEST",
214                 [(set GPRC:$RDEST, (select (xor GPRC:$RCOND, 1), GPRC:$RFALSE, immUExt8:$RTRUE))], s_cmov>;
215
216
217 //General pattern for cmov
218 def : Pat<(select GPRC:$which, GPRC:$src1, GPRC:$src2),
219       (CMOVNE GPRC:$src2, GPRC:$src1, GPRC:$which)>;
220 def : Pat<(select GPRC:$which, GPRC:$src1, immUExt8:$src2),
221       (CMOVEQi GPRC:$src1, immUExt8:$src2, GPRC:$which)>;
222
223 //Invert sense when we can for constants:
224 def : Pat<(select (seteq GPRC:$RCOND, 0), immUExt8:$RFALSE, GPRC:$RTRUE),
225           (CMOVEQi GPRC:$RTRUE, immUExt8:$RFALSE, GPRC:$RCOND)>;
226 def : Pat<(select (setne GPRC:$RCOND, 0), immUExt8:$RFALSE, GPRC:$RTRUE),
227           (CMOVNEi GPRC:$RTRUE, immUExt8:$RFALSE, GPRC:$RCOND)>;
228 def : Pat<(select (setgt GPRC:$RCOND, 0), immUExt8:$RFALSE, GPRC:$RTRUE),
229           (CMOVGTi GPRC:$RTRUE, immUExt8:$RFALSE, GPRC:$RCOND)>;
230 def : Pat<(select (setge GPRC:$RCOND, 0), immUExt8:$RFALSE, GPRC:$RTRUE),
231           (CMOVGEi GPRC:$RTRUE, immUExt8:$RFALSE, GPRC:$RCOND)>;
232 def : Pat<(select (setlt GPRC:$RCOND, 0), immUExt8:$RFALSE, GPRC:$RTRUE),
233           (CMOVLTi GPRC:$RTRUE, immUExt8:$RFALSE, GPRC:$RCOND)>;
234 def : Pat<(select (setle GPRC:$RCOND, 0), immUExt8:$RFALSE, GPRC:$RTRUE),
235           (CMOVLEi GPRC:$RTRUE, immUExt8:$RFALSE, GPRC:$RCOND)>;
236
237
238 def ADDL     : OForm< 0x10, 0x00, "addl $RA,$RB,$RC",
239                       [(set GPRC:$RC, (intop (add GPRC:$RA, GPRC:$RB)))], s_iadd>;
240 def ADDLi    : OFormL<0x10, 0x00, "addl $RA,$L,$RC",
241                       [(set GPRC:$RC, (intop (add GPRC:$RA, immUExt8:$L)))], s_iadd>;
242 def ADDQ     : OForm< 0x10, 0x20, "addq $RA,$RB,$RC",
243                       [(set GPRC:$RC, (add GPRC:$RA, GPRC:$RB))], s_iadd>;
244 def ADDQi    : OFormL<0x10, 0x20, "addq $RA,$L,$RC",
245                       [(set GPRC:$RC, (add GPRC:$RA, immUExt8:$L))], s_iadd>;
246 def AND      : OForm< 0x11, 0x00, "and $RA,$RB,$RC",
247                       [(set GPRC:$RC, (and GPRC:$RA, GPRC:$RB))], s_ilog>;
248 def ANDi     : OFormL<0x11, 0x00, "and $RA,$L,$RC",
249                       [(set GPRC:$RC, (and GPRC:$RA, immUExt8:$L))], s_ilog>;
250 def BIC      : OForm< 0x11, 0x08, "bic $RA,$RB,$RC",
251                       [(set GPRC:$RC, (and GPRC:$RA, (not GPRC:$RB)))], s_ilog>;
252 def BICi     : OFormL<0x11, 0x08, "bic $RA,$L,$RC", 
253                       [(set GPRC:$RC, (and GPRC:$RA, immUExt8inv:$L))], s_ilog>;
254 def BIS      : OForm< 0x11, 0x20, "bis $RA,$RB,$RC",
255                       [(set GPRC:$RC, (or GPRC:$RA, GPRC:$RB))], s_ilog>;
256 def BISi     : OFormL<0x11, 0x20, "bis $RA,$L,$RC",
257                       [(set GPRC:$RC, (or GPRC:$RA, immUExt8:$L))], s_ilog>;
258 def CTLZ     : OForm2<0x1C, 0x32, "CTLZ $RB,$RC", 
259                       [(set GPRC:$RC, (ctlz GPRC:$RB))], s_imisc>;
260 def CTPOP    : OForm2<0x1C, 0x30, "CTPOP $RB,$RC", 
261                       [(set GPRC:$RC, (ctpop GPRC:$RB))], s_imisc>;
262 def CTTZ     : OForm2<0x1C, 0x33, "CTTZ $RB,$RC", 
263                       [(set GPRC:$RC, (cttz GPRC:$RB))], s_imisc>;
264 def EQV      : OForm< 0x11, 0x48, "eqv $RA,$RB,$RC",
265                       [(set GPRC:$RC, (xor GPRC:$RA, (not GPRC:$RB)))], s_ilog>;
266 def EQVi     : OFormL<0x11, 0x48, "eqv $RA,$L,$RC", 
267                       [(set GPRC:$RC, (xor GPRC:$RA, immUExt8inv:$L))], s_ilog>;
268 def EXTBL    : OForm< 0x12, 0x06, "EXTBL $RA,$RB,$RC", 
269                       [(set GPRC:$RC, (and (srl GPRC:$RA, (shl GPRC:$RB, 3)), 255))], s_ishf>;
270 def EXTWL    : OForm< 0x12, 0x16, "EXTWL $RA,$RB,$RC", 
271                       [(set GPRC:$RC, (and (srl GPRC:$RA, (shl GPRC:$RB, 3)), 65535))], s_ishf>;
272 def EXTLL    : OForm< 0x12, 0x26, "EXTLL $RA,$RB,$RC", 
273                       [(set GPRC:$RC, (and (srl GPRC:$RA, (shl GPRC:$RB, 3)), 4294967295))], s_ishf>;
274
275 //def EXTBLi   : OFormL<0x12, 0x06, "EXTBL $RA,$L,$RC", []>; //Extract byte low
276 //def EXTLH    : OForm< 0x12, 0x6A, "EXTLH $RA,$RB,$RC", []>; //Extract longword high
277 //def EXTLHi   : OFormL<0x12, 0x6A, "EXTLH $RA,$L,$RC", []>; //Extract longword high
278 //def EXTLLi   : OFormL<0x12, 0x26, "EXTLL $RA,$L,$RC", []>; //Extract longword low
279 //def EXTQH    : OForm< 0x12, 0x7A, "EXTQH $RA,$RB,$RC", []>; //Extract quadword high
280 //def EXTQHi   : OFormL<0x12, 0x7A, "EXTQH $RA,$L,$RC", []>; //Extract quadword high
281 //def EXTQ     : OForm< 0x12, 0x36, "EXTQ $RA,$RB,$RC", []>; //Extract quadword low
282 //def EXTQi    : OFormL<0x12, 0x36, "EXTQ $RA,$L,$RC", []>; //Extract quadword low
283 //def EXTWH    : OForm< 0x12, 0x5A, "EXTWH $RA,$RB,$RC", []>; //Extract word high
284 //def EXTWHi   : OFormL<0x12, 0x5A, "EXTWH $RA,$L,$RC", []>; //Extract word high
285 //def EXTWLi   : OFormL<0x12, 0x16, "EXTWL $RA,$L,$RC", []>; //Extract word low
286
287 //def IMPLVER  : OForm< 0x11, 0x6C, "IMPLVER $RA,$RB,$RC", []>; //Implementation version
288 //def IMPLVERi : OFormL<0x11, 0x6C, "IMPLVER $RA,$L,$RC", []>; //Implementation version
289 //def INSBL    : OForm< 0x12, 0x0B, "INSBL $RA,$RB,$RC", []>; //Insert byte low
290 //def INSBLi   : OFormL<0x12, 0x0B, "INSBL $RA,$L,$RC", []>; //Insert byte low
291 //def INSLH    : OForm< 0x12, 0x67, "INSLH $RA,$RB,$RC", []>; //Insert longword high
292 //def INSLHi   : OFormL<0x12, 0x67, "INSLH $RA,$L,$RC", []>; //Insert longword high
293 //def INSLL    : OForm< 0x12, 0x2B, "INSLL $RA,$RB,$RC", []>; //Insert longword low
294 //def INSLLi   : OFormL<0x12, 0x2B, "INSLL $RA,$L,$RC", []>; //Insert longword low
295 //def INSQH    : OForm< 0x12, 0x77, "INSQH $RA,$RB,$RC", []>; //Insert quadword high
296 //def INSQHi   : OFormL<0x12, 0x77, "INSQH $RA,$L,$RC", []>; //Insert quadword high
297 //def INSQL    : OForm< 0x12, 0x3B, "INSQL $RA,$RB,$RC", []>; //Insert quadword low
298 //def INSQLi   : OFormL<0x12, 0x3B, "INSQL $RA,$L,$RC", []>; //Insert quadword low
299 //def INSWH    : OForm< 0x12, 0x57, "INSWH $RA,$RB,$RC", []>; //Insert word high
300 //def INSWHi   : OFormL<0x12, 0x57, "INSWH $RA,$L,$RC", []>; //Insert word high
301 //def INSWL    : OForm< 0x12, 0x1B, "INSWL $RA,$RB,$RC", []>; //Insert word low
302 //def INSWLi   : OFormL<0x12, 0x1B, "INSWL $RA,$L,$RC", []>; //Insert word low
303 //def MSKBL    : OForm< 0x12, 0x02, "MSKBL $RA,$RB,$RC", []>; //Mask byte low
304 //def MSKBLi   : OFormL<0x12, 0x02, "MSKBL $RA,$L,$RC", []>; //Mask byte low
305 //def MSKLH    : OForm< 0x12, 0x62, "MSKLH $RA,$RB,$RC", []>; //Mask longword high
306 //def MSKLHi   : OFormL<0x12, 0x62, "MSKLH $RA,$L,$RC", []>; //Mask longword high
307 //def MSKLL    : OForm< 0x12, 0x22, "MSKLL $RA,$RB,$RC", []>; //Mask longword low
308 //def MSKLLi   : OFormL<0x12, 0x22, "MSKLL $RA,$L,$RC", []>; //Mask longword low
309 //def MSKQH    : OForm< 0x12, 0x72, "MSKQH $RA,$RB,$RC", []>; //Mask quadword high
310 //def MSKQHi   : OFormL<0x12, 0x72, "MSKQH $RA,$L,$RC", []>; //Mask quadword high
311 //def MSKQL    : OForm< 0x12, 0x32, "MSKQL $RA,$RB,$RC", []>; //Mask quadword low
312 //def MSKQLi   : OFormL<0x12, 0x32, "MSKQL $RA,$L,$RC", []>; //Mask quadword low
313 //def MSKWH    : OForm< 0x12, 0x52, "MSKWH $RA,$RB,$RC", []>; //Mask word high
314 //def MSKWHi   : OFormL<0x12, 0x52, "MSKWH $RA,$L,$RC", []>; //Mask word high
315 //def MSKWL    : OForm< 0x12, 0x12, "MSKWL $RA,$RB,$RC", []>; //Mask word low
316 //def MSKWLi   : OFormL<0x12, 0x12, "MSKWL $RA,$L,$RC", []>; //Mask word low
317
318 def MULL     : OForm< 0x13, 0x00, "mull $RA,$RB,$RC",
319                       [(set GPRC:$RC, (intop (mul GPRC:$RA, GPRC:$RB)))], s_imul>;
320 def MULLi    : OFormL<0x13, 0x00, "mull $RA,$L,$RC",
321                       [(set GPRC:$RC, (intop (mul GPRC:$RA, immUExt8:$L)))], s_imul>;
322 def MULQ     : OForm< 0x13, 0x20, "mulq $RA,$RB,$RC",
323                       [(set GPRC:$RC, (mul GPRC:$RA, GPRC:$RB))], s_imul>;
324 def MULQi    : OFormL<0x13, 0x20, "mulq $RA,$L,$RC",
325                       [(set GPRC:$RC, (mul GPRC:$RA, immUExt8ME:$L))], s_imul>;
326 def ORNOT    : OForm< 0x11, 0x28, "ornot $RA,$RB,$RC",
327                       [(set GPRC:$RC, (or GPRC:$RA, (not GPRC:$RB)))], s_ilog>;
328 def ORNOTi   : OFormL<0x11, 0x28, "ornot $RA,$L,$RC", 
329                       [(set GPRC:$RC, (or GPRC:$RA, immUExt8inv:$L))], s_ilog>;
330 def S4ADDL   : OForm< 0x10, 0x02, "s4addl $RA,$RB,$RC", 
331                       [(set GPRC:$RC, (intop (add4 GPRC:$RA, GPRC:$RB)))], s_iadd>;
332 def S4ADDLi  : OFormL<0x10, 0x02, "s4addl $RA,$L,$RC", 
333                       [(set GPRC:$RC, (intop (add4 GPRC:$RA, immUExt8:$L)))], s_iadd>;
334 def S4ADDQ   : OForm< 0x10, 0x22, "s4addq $RA,$RB,$RC", 
335                       [(set GPRC:$RC, (add4 GPRC:$RA, GPRC:$RB))], s_iadd>;
336 def S4ADDQi  : OFormL<0x10, 0x22, "s4addq $RA,$L,$RC", 
337                       [(set GPRC:$RC, (add4 GPRC:$RA, immUExt8:$L))], s_iadd>;
338 def S4SUBL   : OForm< 0x10, 0x0B, "s4subl $RA,$RB,$RC",
339                       [(set GPRC:$RC, (intop (sub4 GPRC:$RA, GPRC:$RB)))], s_iadd>;
340 def S4SUBLi  : OFormL<0x10, 0x0B, "s4subl $RA,$L,$RC",
341                       [(set GPRC:$RC, (intop (sub4 GPRC:$RA, immUExt8:$L)))], s_iadd>;
342 def S4SUBQ   : OForm< 0x10, 0x2B, "s4subq $RA,$RB,$RC", 
343                       [(set GPRC:$RC, (sub4 GPRC:$RA, GPRC:$RB))], s_iadd>;
344 def S4SUBQi  : OFormL<0x10, 0x2B, "s4subq $RA,$L,$RC", 
345                       [(set GPRC:$RC, (sub4 GPRC:$RA, immUExt8:$L))], s_iadd>;
346 def S8ADDL   : OForm< 0x10, 0x12, "s8addl $RA,$RB,$RC", 
347                       [(set GPRC:$RC, (intop (add8 GPRC:$RA, GPRC:$RB)))], s_iadd>;
348 def S8ADDLi  : OFormL<0x10, 0x12, "s8addl $RA,$L,$RC", 
349                       [(set GPRC:$RC, (intop (add8 GPRC:$RA, immUExt8:$L)))], s_iadd>;
350 def S8ADDQ   : OForm< 0x10, 0x32, "s8addq $RA,$RB,$RC", 
351                       [(set GPRC:$RC, (add8 GPRC:$RA, GPRC:$RB))], s_iadd>;
352 def S8ADDQi  : OFormL<0x10, 0x32, "s8addq $RA,$L,$RC", 
353                       [(set GPRC:$RC, (add8 GPRC:$RA, immUExt8:$L))], s_iadd>;
354 def S8SUBL   : OForm< 0x10, 0x1B, "s8subl $RA,$RB,$RC", 
355                       [(set GPRC:$RC, (intop (sub8 GPRC:$RA, GPRC:$RB)))], s_iadd>;
356 def S8SUBLi  : OFormL<0x10, 0x1B, "s8subl $RA,$L,$RC", 
357                       [(set GPRC:$RC, (intop (add8 GPRC:$RA, immUExt8neg:$L)))], s_iadd>;
358 def S8SUBQ   : OForm< 0x10, 0x3B, "s8subq $RA,$RB,$RC", 
359                       [(set GPRC:$RC, (sub8 GPRC:$RA, GPRC:$RB))], s_iadd>;
360 def S8SUBQi  : OFormL<0x10, 0x3B, "s8subq $RA,$L,$RC", 
361                       [(set GPRC:$RC, (add8 GPRC:$RA, immUExt8neg:$L))], s_iadd>;
362 def SEXTB    : OForm2<0x1C, 0x00, "sextb $RB,$RC", 
363                       [(set GPRC:$RC, (sext_inreg GPRC:$RB, i8))], s_ishf>;
364 def SEXTW    : OForm2<0x1C, 0x01, "sextw $RB,$RC", 
365                       [(set GPRC:$RC, (sext_inreg GPRC:$RB, i16))], s_ishf>;
366 def SL       : OForm< 0x12, 0x39, "sll $RA,$RB,$RC",
367                       [(set GPRC:$RC, (shl GPRC:$RA, GPRC:$RB))], s_ishf>;
368 def SLi      : OFormL<0x12, 0x39, "sll $RA,$L,$RC",
369                       [(set GPRC:$RC, (shl GPRC:$RA, immUExt8:$L))], s_ishf>;
370 def SRA      : OForm< 0x12, 0x3C, "sra $RA,$RB,$RC",
371                       [(set GPRC:$RC, (sra GPRC:$RA, GPRC:$RB))], s_ishf>;
372 def SRAi     : OFormL<0x12, 0x3C, "sra $RA,$L,$RC",
373                       [(set GPRC:$RC, (sra GPRC:$RA, immUExt8:$L))], s_ishf>;
374 def SRL      : OForm< 0x12, 0x34, "srl $RA,$RB,$RC",
375                       [(set GPRC:$RC, (srl GPRC:$RA, GPRC:$RB))], s_ishf>;
376 def SRLi     : OFormL<0x12, 0x34, "srl $RA,$L,$RC",
377                       [(set GPRC:$RC, (srl GPRC:$RA, immUExt8:$L))], s_ishf>;
378 def SUBL     : OForm< 0x10, 0x09, "subl $RA,$RB,$RC",
379                       [(set GPRC:$RC, (intop (sub GPRC:$RA, GPRC:$RB)))], s_iadd>;
380 def SUBLi    : OFormL<0x10, 0x09, "subl $RA,$L,$RC",
381                       [(set GPRC:$RC, (intop (add GPRC:$RA, immUExt8neg:$L)))], s_iadd>;
382 def SUBQ     : OForm< 0x10, 0x29, "subq $RA,$RB,$RC",
383                       [(set GPRC:$RC, (sub GPRC:$RA, GPRC:$RB))], s_iadd>;
384 def SUBQi    : OFormL<0x10, 0x29, "subq $RA,$L,$RC",
385                       [(set GPRC:$RC, (add GPRC:$RA, immUExt8neg:$L))], s_iadd>;
386 def UMULH    : OForm< 0x13, 0x30, "umulh $RA,$RB,$RC",
387                       [(set GPRC:$RC, (mulhu GPRC:$RA, GPRC:$RB))], s_imul>;                     
388 def UMULHi   : OFormL<0x13, 0x30, "umulh $RA,$L,$RC", 
389                       [(set GPRC:$RC, (mulhu GPRC:$RA, immUExt8:$L))], s_imul>;
390 def XOR      : OForm< 0x11, 0x40, "xor $RA,$RB,$RC",
391                       [(set GPRC:$RC, (xor GPRC:$RA, GPRC:$RB))], s_ilog>;
392 def XORi     : OFormL<0x11, 0x40, "xor $RA,$L,$RC",
393                       [(set GPRC:$RC, (xor GPRC:$RA, immUExt8:$L))], s_ilog>;
394                       
395 def ZAPNOTi  : OFormL<0x12, 0x31, "zapnot $RA,$L,$RC", [], s_ishf>;
396
397 // Define the pattern that produces ZAPNOTi.
398 def : Pat<(i64 (zappat GPRC:$RA):$imm),
399           (ZAPNOTi GPRC:$RA, (iZAPX GPRC:$imm))>;
400
401
402 //Comparison, int
403 //So this is a waste of what this instruction can do, but it still saves something
404 def CMPBGE  : OForm< 0x10, 0x0F, "cmpbge $RA,$RB,$RC", 
405                      [(set GPRC:$RC, (setuge (and GPRC:$RA, 255), (and GPRC:$RB, 255)))], s_ilog>;
406 def CMPBGEi : OFormL<0x10, 0x0F, "cmpbge $RA,$L,$RC",
407                      [(set GPRC:$RC, (setuge (and GPRC:$RA, 255), immUExt8:$L))], s_ilog>;
408 def CMPEQ   : OForm< 0x10, 0x2D, "cmpeq $RA,$RB,$RC", 
409                      [(set GPRC:$RC, (seteq GPRC:$RA, GPRC:$RB))], s_iadd>;
410 def CMPEQi  : OFormL<0x10, 0x2D, "cmpeq $RA,$L,$RC", 
411                      [(set GPRC:$RC, (seteq GPRC:$RA, immUExt8:$L))], s_iadd>;
412 def CMPLE   : OForm< 0x10, 0x6D, "cmple $RA,$RB,$RC", 
413                      [(set GPRC:$RC, (setle GPRC:$RA, GPRC:$RB))], s_iadd>;
414 def CMPLEi  : OFormL<0x10, 0x6D, "cmple $RA,$L,$RC",
415                      [(set GPRC:$RC, (setle GPRC:$RA, immUExt8:$L))], s_iadd>;
416 def CMPLT   : OForm< 0x10, 0x4D, "cmplt $RA,$RB,$RC",
417                      [(set GPRC:$RC, (setlt GPRC:$RA, GPRC:$RB))], s_iadd>;
418 def CMPLTi  : OFormL<0x10, 0x4D, "cmplt $RA,$L,$RC",
419                      [(set GPRC:$RC, (setlt GPRC:$RA, immUExt8:$L))], s_iadd>;
420 def CMPULE  : OForm< 0x10, 0x3D, "cmpule $RA,$RB,$RC",
421                      [(set GPRC:$RC, (setule GPRC:$RA, GPRC:$RB))], s_iadd>;
422 def CMPULEi : OFormL<0x10, 0x3D, "cmpule $RA,$L,$RC",
423                      [(set GPRC:$RC, (setule GPRC:$RA, immUExt8:$L))], s_iadd>;
424 def CMPULT  : OForm< 0x10, 0x1D, "cmpult $RA,$RB,$RC",
425                      [(set GPRC:$RC, (setult GPRC:$RA, GPRC:$RB))], s_iadd>;
426 def CMPULTi : OFormL<0x10, 0x1D, "cmpult $RA,$L,$RC", 
427                       [(set GPRC:$RC, (setult GPRC:$RA, immUExt8:$L))], s_iadd>;
428
429 //Patterns for unsupported int comparisons
430 def : Pat<(setueq GPRC:$X, GPRC:$Y), (CMPEQ GPRC:$X, GPRC:$Y)>;
431 def : Pat<(setueq GPRC:$X, immUExt8:$Y), (CMPEQi GPRC:$X, immUExt8:$Y)>;
432
433 def : Pat<(setugt GPRC:$X, GPRC:$Y), (CMPULT GPRC:$Y, GPRC:$X)>;
434 def : Pat<(setugt immUExt8:$X, GPRC:$Y), (CMPULTi GPRC:$Y, immUExt8:$X)>;
435
436 def : Pat<(setuge GPRC:$X, GPRC:$Y), (CMPULE GPRC:$Y, GPRC:$X)>;
437 def : Pat<(setuge immUExt8:$X, GPRC:$Y), (CMPULEi GPRC:$Y, immUExt8:$X)>;
438
439 def : Pat<(setgt GPRC:$X, GPRC:$Y), (CMPLT GPRC:$Y, GPRC:$X)>;
440 def : Pat<(setgt immUExt8:$X, GPRC:$Y), (CMPLTi GPRC:$Y, immUExt8:$X)>;
441
442 def : Pat<(setge GPRC:$X, GPRC:$Y), (CMPLE GPRC:$Y, GPRC:$X)>;
443 def : Pat<(setge immUExt8:$X, GPRC:$Y), (CMPLEi GPRC:$Y, immUExt8:$X)>;
444
445 def : Pat<(setne GPRC:$X, GPRC:$Y), (CMPEQi (CMPEQ GPRC:$X, GPRC:$Y), 0)>;
446 def : Pat<(setne GPRC:$X, immUExt8:$Y), (CMPEQi (CMPEQi GPRC:$X, immUExt8:$Y), 0)>;
447
448 def : Pat<(setune GPRC:$X, GPRC:$Y), (CMPEQi (CMPEQ GPRC:$X, GPRC:$Y), 0)>;
449 def : Pat<(setune GPRC:$X, immUExt8:$Y), (CMPEQi (CMPEQ GPRC:$X, immUExt8:$Y), 0)>;
450
451
452 let isReturn = 1, isTerminator = 1, noResults = 1, Ra = 31, Rb = 26, disp = 1, Uses = [R26] in {
453   def RETDAG : MbrForm< 0x1A, 0x02, (ops), "ret $$31,($$26),1", s_jsr>; //Return from subroutine
454   def RETDAGp : MbrpForm< 0x1A, 0x02, (ops), "ret $$31,($$26),1", [(retflag)], s_jsr>; //Return from subroutine
455 }
456
457 let isBranch = 1, isTerminator = 1, noResults = 1, isBarrier = 1,
458 Ra = 31, disp = 0 in
459 def JMP : MbrpForm< 0x1A, 0x00, (ops GPRC:$RS), "jmp $$31,($RS),0", 
460           [(brind GPRC:$RS)], s_jsr>; //Jump
461
462 let isCall = 1, noResults = 1, Ra = 26,
463     Defs = [R0, R1, R2, R3, R4, R5, R6, R7, R8, R16, R17, R18, R19,
464             R20, R21, R22, R23, R24, R25, R26, R27, R28, R29,
465             F0, F1,
466             F10, F11, F12, F13, F14, F15, F16, F17, F18, F19,
467             F20, F21, F22, F23, F24, F25, F26, F27, F28, F29, F30], Uses = [R29] in {
468     def BSR : BFormD<0x34, "bsr $$26,$$$DISP..ng", [], s_jsr>; //Branch to subroutine
469 }
470 let isCall = 1, noResults = 1, Ra = 26, Rb = 27, disp = 0,
471     Defs = [R0, R1, R2, R3, R4, R5, R6, R7, R8, R16, R17, R18, R19,
472             R20, R21, R22, R23, R24, R25, R26, R27, R28, R29,
473             F0, F1,
474             F10, F11, F12, F13, F14, F15, F16, F17, F18, F19,
475             F20, F21, F22, F23, F24, F25, F26, F27, F28, F29, F30], Uses = [R27, R29] in {
476     def JSR : MbrForm< 0x1A, 0x01, (ops ), "jsr $$26,($$27),0", s_jsr>; //Jump to subroutine
477 }
478
479 let isCall = 1, noResults = 1, Ra = 23, Rb = 27, disp = 0,
480     Defs = [R23, R24, R25, R27, R28], Uses = [R24, R25, R27] in
481   def JSRs : MbrForm< 0x1A, 0x01, (ops ), "jsr $$23,($$27),0", s_jsr>; //Jump to div or rem
482
483
484 def JSR_COROUTINE : MbrForm< 0x1A, 0x03, (ops GPRC:$RD, GPRC:$RS, s14imm:$DISP), "jsr_coroutine $RD,($RS),$DISP", s_jsr>; //Jump to subroutine return
485
486 let OperandList = (ops GPRC:$RA, s64imm:$DISP, GPRC:$RB) in {
487 def LDQ   : MForm<0x29, 0, 1, "ldq $RA,$DISP($RB)",
488                  [(set GPRC:$RA, (load (add GPRC:$RB, immSExt16:$DISP)))], s_ild>;
489 def LDQr  : MForm<0x29, 0, 1, "ldq $RA,$DISP($RB)\t\t!gprellow",
490                  [(set GPRC:$RA, (load (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB)))], s_ild>;
491 def LDL   : MForm<0x28, 0, 1, "ldl $RA,$DISP($RB)",
492                  [(set GPRC:$RA, (sextloadi32 (add GPRC:$RB, immSExt16:$DISP)))], s_ild>;
493 def LDLr  : MForm<0x28, 0, 1, "ldl $RA,$DISP($RB)\t\t!gprellow",
494                  [(set GPRC:$RA, (sextloadi32 (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB)))], s_ild>;
495 def LDBU  : MForm<0x0A, 0, 1, "ldbu $RA,$DISP($RB)",
496                  [(set GPRC:$RA, (zextloadi8 (add GPRC:$RB, immSExt16:$DISP)))], s_ild>;
497 def LDBUr : MForm<0x0A, 0, 1, "ldbu $RA,$DISP($RB)\t\t!gprellow",
498                  [(set GPRC:$RA, (zextloadi8 (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB)))], s_ild>;
499 def LDWU  : MForm<0x0C, 0, 1, "ldwu $RA,$DISP($RB)",
500                  [(set GPRC:$RA, (zextloadi16 (add GPRC:$RB, immSExt16:$DISP)))], s_ild>;
501 def LDWUr : MForm<0x0C, 0, 1, "ldwu $RA,$DISP($RB)\t\t!gprellow",
502                  [(set GPRC:$RA, (zextloadi16 (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB)))], s_ild>;
503 def STB   : MForm<0x0E, 1, 0, "stb $RA,$DISP($RB)",
504                  [(truncstorei8 GPRC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_ist>;
505 def STBr  : MForm<0x0E, 1, 0, "stb $RA,$DISP($RB)\t\t!gprellow",
506                  [(truncstorei8 GPRC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_ist>;
507 def STW   : MForm<0x0D, 1, 0, "stw $RA,$DISP($RB)",
508                  [(truncstorei16 GPRC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_ist>;
509 def STWr  : MForm<0x0D, 1, 0, "stw $RA,$DISP($RB)\t\t!gprellow",
510                  [(truncstorei16 GPRC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_ist>;
511 def STL   : MForm<0x2C, 1, 0, "stl $RA,$DISP($RB)",
512                  [(truncstorei32 GPRC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_ist>;
513 def STLr  : MForm<0x2C, 1, 0, "stl $RA,$DISP($RB)\t\t!gprellow",
514                  [(truncstorei32 GPRC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_ist>;
515 def STQ   : MForm<0x2D, 1, 0, "stq $RA,$DISP($RB)",
516                  [(store GPRC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_ist>;
517 def STQr  : MForm<0x2D, 1, 0, "stq $RA,$DISP($RB)\t\t!gprellow",
518                  [(store GPRC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_ist>;
519
520 //Load address
521 def LDA   : MForm<0x08, 0, 0, "lda $RA,$DISP($RB)",
522                  [(set GPRC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_lda>;
523 def LDAr  : MForm<0x08, 0, 0, "lda $RA,$DISP($RB)\t\t!gprellow",
524                  [(set GPRC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_lda>;  //Load address
525 def LDAH  : MForm<0x09, 0, 0, "ldah $RA,$DISP($RB)",
526                  [], s_lda>;  //Load address high
527 def LDAHr : MForm<0x09, 0, 0, "ldah $RA,$DISP($RB)\t\t!gprelhigh",
528                  [(set GPRC:$RA, (Alpha_gprelhi tglobaladdr:$DISP, GPRC:$RB))], s_lda>;  //Load address high
529 }
530
531 let OperandList = (ops F4RC:$RA, s64imm:$DISP, GPRC:$RB) in {
532 def STS  : MForm<0x26, 1, 0, "sts $RA,$DISP($RB)",
533                 [(store F4RC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_fst>;
534 def STSr : MForm<0x26, 1, 0, "sts $RA,$DISP($RB)\t\t!gprellow",
535                 [(store F4RC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_fst>;
536 def LDS  : MForm<0x22, 0, 1, "lds $RA,$DISP($RB)",
537                 [(set F4RC:$RA, (load (add GPRC:$RB, immSExt16:$DISP)))], s_fld>;
538 def LDSr : MForm<0x22, 0, 1, "lds $RA,$DISP($RB)\t\t!gprellow",
539                 [(set F4RC:$RA, (load (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB)))], s_fld>;
540 }
541 let OperandList = (ops F8RC:$RA, s64imm:$DISP, GPRC:$RB) in {
542 def STT  : MForm<0x27, 1, 0, "stt $RA,$DISP($RB)",
543                 [(store F8RC:$RA, (add GPRC:$RB, immSExt16:$DISP))], s_fst>;
544 def STTr : MForm<0x27, 1, 0, "stt $RA,$DISP($RB)\t\t!gprellow",
545                 [(store F8RC:$RA, (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB))], s_fst>;
546 def LDT  : MForm<0x23, 0, 1, "ldt $RA,$DISP($RB)",
547                 [(set F8RC:$RA, (load (add GPRC:$RB, immSExt16:$DISP)))], s_fld>;
548 def LDTr : MForm<0x23, 0, 1, "ldt $RA,$DISP($RB)\t\t!gprellow",
549                 [(set F8RC:$RA, (load (Alpha_gprello tglobaladdr:$DISP, GPRC:$RB)))], s_fld>;
550 }
551
552
553 //constpool rels
554 def : Pat<(i64 (load (Alpha_gprello tconstpool:$DISP, GPRC:$RB))),
555           (LDQr tconstpool:$DISP, GPRC:$RB)>;
556 def : Pat<(i64 (sextloadi32 (Alpha_gprello tconstpool:$DISP, GPRC:$RB))),
557           (LDLr tconstpool:$DISP, GPRC:$RB)>;
558 def : Pat<(i64 (zextloadi8 (Alpha_gprello tconstpool:$DISP, GPRC:$RB))),
559           (LDBUr tconstpool:$DISP, GPRC:$RB)>;
560 def : Pat<(i64 (zextloadi16 (Alpha_gprello tconstpool:$DISP, GPRC:$RB))),
561           (LDWUr tconstpool:$DISP, GPRC:$RB)>;
562 def : Pat<(i64 (Alpha_gprello tconstpool:$DISP, GPRC:$RB)),
563           (LDAr tconstpool:$DISP, GPRC:$RB)>;
564 def : Pat<(i64 (Alpha_gprelhi tconstpool:$DISP, GPRC:$RB)),
565           (LDAHr tconstpool:$DISP, GPRC:$RB)>;
566 def : Pat<(f32 (load (Alpha_gprello tconstpool:$DISP, GPRC:$RB))),
567           (LDSr tconstpool:$DISP, GPRC:$RB)>;
568 def : Pat<(f64 (load (Alpha_gprello tconstpool:$DISP, GPRC:$RB))),
569           (LDTr tconstpool:$DISP, GPRC:$RB)>;
570
571 //jumptable rels
572 def : Pat<(i64 (Alpha_gprelhi tjumptable:$DISP, GPRC:$RB)),
573           (LDAHr tjumptable:$DISP, GPRC:$RB)>;
574 def : Pat<(i64 (Alpha_gprello tjumptable:$DISP, GPRC:$RB)),
575           (LDAr tjumptable:$DISP, GPRC:$RB)>;
576
577
578 //misc ext patterns
579 def : Pat<(i64 (extloadi8 (add GPRC:$RB, immSExt16:$DISP))),
580           (LDBU   immSExt16:$DISP, GPRC:$RB)>;
581 def : Pat<(i64 (extloadi16 (add GPRC:$RB, immSExt16:$DISP))),
582           (LDWU  immSExt16:$DISP, GPRC:$RB)>;
583 def : Pat<(i64 (extloadi32 (add GPRC:$RB, immSExt16:$DISP))),
584           (LDL   immSExt16:$DISP, GPRC:$RB)>;
585
586 //0 disp patterns
587 def : Pat<(i64 (load GPRC:$addr)),
588           (LDQ  0, GPRC:$addr)>;
589 def : Pat<(f64 (load GPRC:$addr)),
590           (LDT  0, GPRC:$addr)>;
591 def : Pat<(f32 (load GPRC:$addr)),
592           (LDS  0, GPRC:$addr)>;
593 def : Pat<(i64 (sextloadi32 GPRC:$addr)),
594           (LDL  0, GPRC:$addr)>;
595 def : Pat<(i64 (zextloadi16 GPRC:$addr)),
596           (LDWU 0, GPRC:$addr)>;
597 def : Pat<(i64 (zextloadi8 GPRC:$addr)),
598           (LDBU 0, GPRC:$addr)>;
599 def : Pat<(i64 (extloadi8 GPRC:$addr)),
600           (LDBU 0, GPRC:$addr)>;
601 def : Pat<(i64 (extloadi16 GPRC:$addr)),
602           (LDWU 0, GPRC:$addr)>;
603 def : Pat<(i64 (extloadi32 GPRC:$addr)),
604           (LDL  0, GPRC:$addr)>;
605
606 def : Pat<(store GPRC:$DATA, GPRC:$addr),
607           (STQ  GPRC:$DATA, 0, GPRC:$addr)>;
608 def : Pat<(store F8RC:$DATA, GPRC:$addr),
609           (STT  F8RC:$DATA, 0, GPRC:$addr)>;
610 def : Pat<(store F4RC:$DATA, GPRC:$addr),
611           (STS  F4RC:$DATA, 0, GPRC:$addr)>;
612 def : Pat<(truncstorei32 GPRC:$DATA, GPRC:$addr),
613           (STL  GPRC:$DATA, 0, GPRC:$addr)>;
614 def : Pat<(truncstorei16 GPRC:$DATA, GPRC:$addr),
615           (STW GPRC:$DATA, 0, GPRC:$addr)>;
616 def : Pat<(truncstorei8 GPRC:$DATA, GPRC:$addr),
617           (STB GPRC:$DATA, 0, GPRC:$addr)>;
618
619
620 //load address, rellocated gpdist form
621 let OperandList = (ops GPRC:$RA, s16imm:$DISP, GPRC:$RB, s16imm:$NUM) in {
622 def LDAg  : MForm<0x08, 0, 1, "lda $RA,0($RB)\t\t!gpdisp!$NUM", [], s_lda>;  //Load address
623 def LDAHg : MForm<0x09, 0, 1, "ldah $RA,0($RB)\t\t!gpdisp!$NUM", [], s_lda>;  //Load address
624 }
625
626 //Load quad, rellocated literal form
627 let OperandList = (ops GPRC:$RA, s64imm:$DISP, GPRC:$RB) in 
628 def LDQl : MForm<0x29, 0, 1, "ldq $RA,$DISP($RB)\t\t!literal",
629                  [(set GPRC:$RA, (Alpha_rellit tglobaladdr:$DISP, GPRC:$RB))], s_ild>;
630 def : Pat<(Alpha_rellit texternalsym:$ext, GPRC:$RB),
631           (LDQl texternalsym:$ext, GPRC:$RB)>;
632
633
634 def RPCC : MfcForm<0x18, 0xC000, "rpcc $RA", s_rpcc>; //Read process cycle counter
635
636 //Basic Floating point ops
637
638 //Floats
639
640 let OperandList = (ops F4RC:$RC, F4RC:$RB), Fa = 31 in 
641 def SQRTS : FPForm<0x14, 0x58B, "sqrts/su $RB,$RC",
642                    [(set F4RC:$RC, (fsqrt F4RC:$RB))], s_fsqrts>;
643
644 let OperandList = (ops F4RC:$RC, F4RC:$RA, F4RC:$RB) in {
645 def ADDS  : FPForm<0x16, 0x580, "adds/su $RA,$RB,$RC",
646                    [(set F4RC:$RC, (fadd F4RC:$RA, F4RC:$RB))], s_fadd>;
647 def SUBS  : FPForm<0x16, 0x581, "subs/su $RA,$RB,$RC",
648                    [(set F4RC:$RC, (fsub F4RC:$RA, F4RC:$RB))], s_fadd>;
649 def DIVS  : FPForm<0x16, 0x583, "divs/su $RA,$RB,$RC",
650                    [(set F4RC:$RC, (fdiv F4RC:$RA, F4RC:$RB))], s_fdivs>;
651 def MULS  : FPForm<0x16, 0x582, "muls/su $RA,$RB,$RC",
652                    [(set F4RC:$RC, (fmul F4RC:$RA, F4RC:$RB))], s_fmul>;
653
654 def CPYSS  : FPForm<0x17, 0x020, "cpys $RA,$RB,$RC",
655                    [(set F4RC:$RC, (fcopysign F4RC:$RB, F4RC:$RA))], s_fadd>;
656 def CPYSES : FPForm<0x17, 0x022, "cpyse $RA,$RB,$RC",[], s_fadd>; //Copy sign and exponent
657 def CPYSNS : FPForm<0x17, 0x021, "cpysn $RA,$RB,$RC",
658                    [(set F4RC:$RC, (fneg (fcopysign F4RC:$RB, F4RC:$RA)))], s_fadd>;
659 }
660
661 //Doubles
662
663 let OperandList = (ops F8RC:$RC, F8RC:$RB), Fa = 31 in 
664 def SQRTT : FPForm<0x14, 0x5AB, "sqrtt/su $RB,$RC",
665                    [(set F8RC:$RC, (fsqrt F8RC:$RB))], s_fsqrtt>;
666
667 let OperandList = (ops F8RC:$RC, F8RC:$RA, F8RC:$RB) in {
668 def ADDT  : FPForm<0x16, 0x5A0, "addt/su $RA,$RB,$RC",
669                    [(set F8RC:$RC, (fadd F8RC:$RA, F8RC:$RB))], s_fadd>;
670 def SUBT  : FPForm<0x16, 0x5A1, "subt/su $RA,$RB,$RC",
671                    [(set F8RC:$RC, (fsub F8RC:$RA, F8RC:$RB))], s_fadd>;
672 def DIVT  : FPForm<0x16, 0x5A3, "divt/su $RA,$RB,$RC",
673                    [(set F8RC:$RC, (fdiv F8RC:$RA, F8RC:$RB))], s_fdivt>;
674 def MULT  : FPForm<0x16, 0x5A2, "mult/su $RA,$RB,$RC",
675                    [(set F8RC:$RC, (fmul F8RC:$RA, F8RC:$RB))], s_fmul>;
676
677 def CPYST  : FPForm<0x17, 0x020, "cpys $RA,$RB,$RC",
678                    [(set F8RC:$RC, (fcopysign F8RC:$RB, F8RC:$RA))], s_fadd>;
679 def CPYSET : FPForm<0x17, 0x022, "cpyse $RA,$RB,$RC",[], s_fadd>; //Copy sign and exponent
680 def CPYSNT : FPForm<0x17, 0x021, "cpysn $RA,$RB,$RC",
681                    [(set F8RC:$RC, (fneg (fcopysign F8RC:$RB, F8RC:$RA)))], s_fadd>;
682
683 def CMPTEQ : FPForm<0x16, 0x5A5, "cmpteq/su $RA,$RB,$RC", [], s_fadd>;
684 //                    [(set F8RC:$RC, (seteq F8RC:$RA, F8RC:$RB))]>;
685 def CMPTLE : FPForm<0x16, 0x5A7, "cmptle/su $RA,$RB,$RC", [], s_fadd>;
686 //                    [(set F8RC:$RC, (setle F8RC:$RA, F8RC:$RB))]>;
687 def CMPTLT : FPForm<0x16, 0x5A6, "cmptlt/su $RA,$RB,$RC", [], s_fadd>;
688 //                    [(set F8RC:$RC, (setlt F8RC:$RA, F8RC:$RB))]>;
689 def CMPTUN : FPForm<0x16, 0x5A4, "cmptun/su $RA,$RB,$RC", [], s_fadd>;
690 //                    [(set F8RC:$RC, (setuo F8RC:$RA, F8RC:$RB))]>;
691 }
692
693 //More CPYS forms:
694 let OperandList = (ops F8RC:$RC, F4RC:$RA, F8RC:$RB) in {
695 def CPYSTs  : FPForm<0x17, 0x020, "cpys $RA,$RB,$RC",
696                    [(set F8RC:$RC, (fcopysign F8RC:$RB, F4RC:$RA))], s_fadd>;
697 def CPYSNTs : FPForm<0x17, 0x021, "cpysn $RA,$RB,$RC",
698                    [(set F8RC:$RC, (fneg (fcopysign F8RC:$RB, F4RC:$RA)))], s_fadd>;
699 }
700 let OperandList = (ops F4RC:$RC, F8RC:$RA, F4RC:$RB) in {
701 def CPYSSt  : FPForm<0x17, 0x020, "cpys $RA,$RB,$RC",
702                    [(set F4RC:$RC, (fcopysign F4RC:$RB, F8RC:$RA))], s_fadd>;
703 def CPYSESt : FPForm<0x17, 0x022, "cpyse $RA,$RB,$RC",[], s_fadd>; //Copy sign and exponent
704 def CPYSNSt : FPForm<0x17, 0x021, "cpysn $RA,$RB,$RC",
705                    [(set F4RC:$RC, (fneg (fcopysign F4RC:$RB, F8RC:$RA)))], s_fadd>;
706 }
707
708 //conditional moves, floats
709 let OperandList = (ops F4RC:$RDEST, F4RC:$RFALSE, F4RC:$RTRUE, F8RC:$RCOND),
710     isTwoAddress = 1 in {
711 def FCMOVEQS : FPForm<0x17, 0x02A, "fcmoveq $RCOND,$RTRUE,$RDEST",[], s_fcmov>; //FCMOVE if = zero
712 def FCMOVGES : FPForm<0x17, 0x02D, "fcmovge $RCOND,$RTRUE,$RDEST",[], s_fcmov>; //FCMOVE if >= zero
713 def FCMOVGTS : FPForm<0x17, 0x02F, "fcmovgt $RCOND,$RTRUE,$RDEST",[], s_fcmov>; //FCMOVE if > zero
714 def FCMOVLES : FPForm<0x17, 0x02E, "fcmovle $RCOND,$RTRUE,$RDEST",[], s_fcmov>; //FCMOVE if <= zero
715 def FCMOVLTS : FPForm<0x17, 0x02C, "fcmovlt $RCOND,$RTRUE,$RDEST",[], s_fcmov>; // FCMOVE if < zero
716 def FCMOVNES : FPForm<0x17, 0x02B, "fcmovne $RCOND,$RTRUE,$RDEST",[], s_fcmov>; //FCMOVE if != zero
717 }
718 //conditional moves, doubles
719 let OperandList = (ops F8RC:$RDEST, F8RC:$RFALSE, F8RC:$RTRUE, F8RC:$RCOND),
720     isTwoAddress = 1 in {
721 def FCMOVEQT : FPForm<0x17, 0x02A, "fcmoveq $RCOND,$RTRUE,$RDEST", [], s_fcmov>;
722 def FCMOVGET : FPForm<0x17, 0x02D, "fcmovge $RCOND,$RTRUE,$RDEST", [], s_fcmov>;
723 def FCMOVGTT : FPForm<0x17, 0x02F, "fcmovgt $RCOND,$RTRUE,$RDEST", [], s_fcmov>;
724 def FCMOVLET : FPForm<0x17, 0x02E, "fcmovle $RCOND,$RTRUE,$RDEST", [], s_fcmov>;
725 def FCMOVLTT : FPForm<0x17, 0x02C, "fcmovlt $RCOND,$RTRUE,$RDEST", [], s_fcmov>;
726 def FCMOVNET : FPForm<0x17, 0x02B, "fcmovne $RCOND,$RTRUE,$RDEST", [], s_fcmov>;
727 }
728
729 //misc FP selects
730 //Select double
731 def : Pat<(select (seteq F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
732       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
733 def : Pat<(select (setoeq F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
734       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
735 def : Pat<(select (setueq F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
736       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
737
738 def : Pat<(select (setne F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
739       (FCMOVEQT F8RC:$sf, F8RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
740 def : Pat<(select (setone F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
741       (FCMOVEQT F8RC:$sf, F8RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
742 def : Pat<(select (setune F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
743       (FCMOVEQT F8RC:$sf, F8RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
744
745 def : Pat<(select (setgt F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
746       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLT F8RC:$RB, F8RC:$RA))>;
747 def : Pat<(select (setogt F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
748       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLT F8RC:$RB, F8RC:$RA))>;
749 def : Pat<(select (setugt F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
750       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLT F8RC:$RB, F8RC:$RA))>;
751
752 def : Pat<(select (setge F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
753       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLE F8RC:$RB, F8RC:$RA))>;
754 def : Pat<(select (setoge F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
755       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLE F8RC:$RB, F8RC:$RA))>;
756 def : Pat<(select (setuge F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
757       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLE F8RC:$RB, F8RC:$RA))>;
758
759 def : Pat<(select (setlt F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
760       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLT F8RC:$RA, F8RC:$RB))>;
761 def : Pat<(select (setolt F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
762       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLT F8RC:$RA, F8RC:$RB))>;
763 def : Pat<(select (setult F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
764       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLT F8RC:$RA, F8RC:$RB))>;
765
766 def : Pat<(select (setle F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
767       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLE F8RC:$RA, F8RC:$RB))>;
768 def : Pat<(select (setole F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
769       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLE F8RC:$RA, F8RC:$RB))>;
770 def : Pat<(select (setule F8RC:$RA, F8RC:$RB), F8RC:$st, F8RC:$sf),
771       (FCMOVNET F8RC:$sf, F8RC:$st, (CMPTLE F8RC:$RA, F8RC:$RB))>;
772
773 //Select single
774 def : Pat<(select (seteq F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
775       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
776 def : Pat<(select (setoeq F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
777       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
778 def : Pat<(select (setueq F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
779       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
780
781 def : Pat<(select (setne F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
782       (FCMOVEQS F4RC:$sf, F4RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
783 def : Pat<(select (setone F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
784       (FCMOVEQS F4RC:$sf, F4RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
785 def : Pat<(select (setune F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
786       (FCMOVEQS F4RC:$sf, F4RC:$st, (CMPTEQ F8RC:$RA, F8RC:$RB))>;
787
788 def : Pat<(select (setgt F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
789       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLT F8RC:$RB, F8RC:$RA))>;
790 def : Pat<(select (setogt F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
791       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLT F8RC:$RB, F8RC:$RA))>;
792 def : Pat<(select (setugt F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
793       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLT F8RC:$RB, F8RC:$RA))>;
794
795 def : Pat<(select (setge F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
796       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLE F8RC:$RB, F8RC:$RA))>;
797 def : Pat<(select (setoge F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
798       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLE F8RC:$RB, F8RC:$RA))>;
799 def : Pat<(select (setuge F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
800       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLE F8RC:$RB, F8RC:$RA))>;
801
802 def : Pat<(select (setlt F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
803       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLT F8RC:$RA, F8RC:$RB))>;
804 def : Pat<(select (setolt F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
805       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLT F8RC:$RA, F8RC:$RB))>;
806 def : Pat<(select (setult F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
807       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLT F8RC:$RA, F8RC:$RB))>;
808
809 def : Pat<(select (setle F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
810       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLE F8RC:$RA, F8RC:$RB))>;
811 def : Pat<(select (setole F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
812       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLE F8RC:$RA, F8RC:$RB))>;
813 def : Pat<(select (setule F8RC:$RA, F8RC:$RB), F4RC:$st, F4RC:$sf),
814       (FCMOVNES F4RC:$sf, F4RC:$st, (CMPTLE F8RC:$RA, F8RC:$RB))>;
815
816
817
818 let OperandList = (ops GPRC:$RC, F4RC:$RA), Fb = 31 in 
819 def FTOIS : FPForm<0x1C, 0x078, "ftois $RA,$RC",[], s_ftoi>; //Floating to integer move, S_floating
820 let OperandList = (ops GPRC:$RC, F8RC:$RA), Fb = 31 in 
821 def FTOIT : FPForm<0x1C, 0x070, "ftoit $RA,$RC",
822         [(set GPRC:$RC, (Alpha_ftoit F8RC:$RA))], s_ftoi>; //Floating to integer move
823 let OperandList = (ops F4RC:$RC, GPRC:$RA), Fb = 31 in 
824 def ITOFS : FPForm<0x14, 0x004, "itofs $RA,$RC",[], s_itof>; //Integer to floating move, S_floating
825 let OperandList = (ops F8RC:$RC, GPRC:$RA), Fb = 31 in 
826 def ITOFT : FPForm<0x14, 0x024, "itoft $RA,$RC",
827         [(set F8RC:$RC, (Alpha_itoft GPRC:$RA))], s_itof>; //Integer to floating move
828
829
830 let OperandList = (ops F4RC:$RC, F8RC:$RB), Fa = 31 in 
831 def CVTQS : FPForm<0x16, 0x7BC, "cvtqs/sui $RB,$RC",
832         [(set F4RC:$RC, (Alpha_cvtqs F8RC:$RB))], s_fadd>;
833 let OperandList = (ops F8RC:$RC, F8RC:$RB), Fa = 31 in 
834 def CVTQT : FPForm<0x16, 0x7BE, "cvtqt/sui $RB,$RC",
835         [(set F8RC:$RC, (Alpha_cvtqt F8RC:$RB))], s_fadd>;
836 let OperandList = (ops F8RC:$RC, F8RC:$RB), Fa = 31 in 
837 def CVTTQ : FPForm<0x16, 0x52F, "cvttq/svc $RB,$RC",
838         [(set F8RC:$RC, (Alpha_cvttq F8RC:$RB))], s_fadd>;
839 let OperandList = (ops F8RC:$RC, F4RC:$RB), Fa = 31 in 
840 def CVTST : FPForm<0x16, 0x6AC, "cvtst/s $RB,$RC",
841                    [(set F8RC:$RC, (fextend F4RC:$RB))], s_fadd>;
842 let OperandList = (ops F4RC:$RC, F8RC:$RB), Fa = 31 in 
843 def CVTTS : FPForm<0x16, 0x7AC, "cvtts/sui $RB,$RC",
844                    [(set F4RC:$RC, (fround F8RC:$RB))], s_fadd>;
845
846
847 /////////////////////////////////////////////////////////
848 //Branching
849 /////////////////////////////////////////////////////////
850 let isBranch = 1, isTerminator = 1, hasCtrlDep = 1, noResults = 1 in {
851 let Ra = 31 in
852 def BR : BFormD<0x30, "br $$31,$DISP", [(br bb:$DISP)], s_ubr>;
853
854 //Branches, int
855 def BEQ  : BForm<0x39, "beq $RA,$DISP", 
856                  [(brcond (seteq GPRC:$RA, 0), bb:$DISP)], s_icbr>;
857 def BGE  : BForm<0x3E, "bge $RA,$DISP", 
858                  [(brcond (setge GPRC:$RA, 0), bb:$DISP)], s_icbr>;
859 def BGT  : BForm<0x3F, "bgt $RA,$DISP",
860                  [(brcond (setgt GPRC:$RA, 0), bb:$DISP)], s_icbr>;
861 def BLBC : BForm<0x38, "blbc $RA,$DISP", [], s_icbr>; //TODO: Low bit clear
862 def BLBS : BForm<0x3C, "blbs $RA,$DISP",
863                  [(brcond (and GPRC:$RA, 1), bb:$DISP)], s_icbr>;
864 def BLE  : BForm<0x3B, "ble $RA,$DISP",
865                  [(brcond (setle GPRC:$RA, 0), bb:$DISP)], s_icbr>;
866 def BLT  : BForm<0x3A, "blt $RA,$DISP",
867                  [(brcond (setlt GPRC:$RA, 0), bb:$DISP)], s_icbr>;
868 def BNE  : BForm<0x3D, "bne $RA,$DISP",
869                  [(brcond (setne GPRC:$RA, 0), bb:$DISP)], s_icbr>;
870
871 //Branches, float
872 def FBEQ : FBForm<0x31, "fbeq $RA,$DISP", 
873                   [(brcond (seteq F8RC:$RA, immFPZ), bb:$DISP)], s_fbr>;
874 def FBGE : FBForm<0x36, "fbge $RA,$DISP",
875                   [(brcond (setge F8RC:$RA, immFPZ), bb:$DISP)], s_fbr>;
876 def FBGT : FBForm<0x37, "fbgt $RA,$DISP",
877                   [(brcond (setgt F8RC:$RA, immFPZ), bb:$DISP)], s_fbr>;
878 def FBLE : FBForm<0x33, "fble $RA,$DISP",
879                   [(brcond (setle F8RC:$RA, immFPZ), bb:$DISP)], s_fbr>;
880 def FBLT : FBForm<0x32, "fblt $RA,$DISP",
881                   [(brcond (setlt F8RC:$RA, immFPZ), bb:$DISP)], s_fbr>;
882 def FBNE : FBForm<0x35, "fbne $RA,$DISP",
883                   [(brcond (setne F8RC:$RA, immFPZ), bb:$DISP)], s_fbr>;
884 }
885
886 def : Pat<(brcond GPRC:$RA, bb:$DISP), (BNE GPRC:$RA, bb:$DISP)>;
887 def : Pat<(brcond (setne GPRC:$RA, GPRC:$RB), bb:$DISP),
888           (BEQ (CMPEQ GPRC:$RA, GPRC:$RB), bb:$DISP)>;
889 def : Pat<(brcond (setne GPRC:$RA, immUExt8:$L), bb:$DISP),
890           (BEQ (CMPEQi GPRC:$RA, immUExt8:$L), bb:$DISP)>;
891
892 def : Pat<(brcond (seteq F8RC:$RA, F8RC:$RB), bb:$DISP),
893           (FBNE  (CMPTEQ F8RC:$RA, F8RC:$RB), bb:$DISP)>;
894 def : Pat<(brcond (setoeq F8RC:$RA, F8RC:$RB), bb:$DISP),
895           (FBNE  (CMPTEQ F8RC:$RA, F8RC:$RB), bb:$DISP)>;
896 def : Pat<(brcond (setueq F8RC:$RA, F8RC:$RB), bb:$DISP),
897           (FBNE  (CMPTEQ F8RC:$RA, F8RC:$RB), bb:$DISP)>;
898
899 def : Pat<(brcond (setlt F8RC:$RA, F8RC:$RB), bb:$DISP),
900           (FBNE  (CMPTLT F8RC:$RA, F8RC:$RB), bb:$DISP)>;
901 def : Pat<(brcond (setolt F8RC:$RA, F8RC:$RB), bb:$DISP),
902           (FBNE  (CMPTLT F8RC:$RA, F8RC:$RB), bb:$DISP)>;
903 def : Pat<(brcond (setult F8RC:$RA, F8RC:$RB), bb:$DISP),
904           (FBNE  (CMPTLT F8RC:$RA, F8RC:$RB), bb:$DISP)>;
905
906 def : Pat<(brcond (setle F8RC:$RA, F8RC:$RB), bb:$DISP),
907           (FBNE  (CMPTLE F8RC:$RA, F8RC:$RB), bb:$DISP)>;
908 def : Pat<(brcond (setole F8RC:$RA, F8RC:$RB), bb:$DISP),
909           (FBNE  (CMPTLE F8RC:$RA, F8RC:$RB), bb:$DISP)>;
910 def : Pat<(brcond (setule F8RC:$RA, F8RC:$RB), bb:$DISP),
911           (FBNE  (CMPTLE F8RC:$RA, F8RC:$RB), bb:$DISP)>;
912
913 def : Pat<(brcond (setgt F8RC:$RA, F8RC:$RB), bb:$DISP),
914           (FBNE  (CMPTLT F8RC:$RB, F8RC:$RA), bb:$DISP)>;
915 def : Pat<(brcond (setogt F8RC:$RA, F8RC:$RB), bb:$DISP),
916           (FBNE  (CMPTLT F8RC:$RB, F8RC:$RA), bb:$DISP)>;
917 def : Pat<(brcond (setugt F8RC:$RA, F8RC:$RB), bb:$DISP),
918           (FBNE  (CMPTLT F8RC:$RB, F8RC:$RA), bb:$DISP)>;
919
920 def : Pat<(brcond (setge F8RC:$RA, F8RC:$RB), bb:$DISP),
921           (FBNE  (CMPTLE F8RC:$RB, F8RC:$RA), bb:$DISP)>;
922 def : Pat<(brcond (setoge F8RC:$RA, F8RC:$RB), bb:$DISP),
923           (FBNE  (CMPTLE F8RC:$RB, F8RC:$RA), bb:$DISP)>;
924 def : Pat<(brcond (setuge F8RC:$RA, F8RC:$RB), bb:$DISP),
925           (FBNE  (CMPTLE F8RC:$RB, F8RC:$RA), bb:$DISP)>;
926
927 def : Pat<(brcond (setne F8RC:$RA, F8RC:$RB), bb:$DISP),
928           (FBEQ  (CMPTEQ F8RC:$RA, F8RC:$RB), bb:$DISP)>;
929 def : Pat<(brcond (setone F8RC:$RA, F8RC:$RB), bb:$DISP),
930           (FBEQ  (CMPTEQ F8RC:$RA, F8RC:$RB), bb:$DISP)>;
931 def : Pat<(brcond (setune F8RC:$RA, F8RC:$RB), bb:$DISP),
932           (FBEQ  (CMPTEQ F8RC:$RA, F8RC:$RB), bb:$DISP)>;
933
934
935 def : Pat<(brcond (setoeq F8RC:$RA, immFPZ), bb:$DISP),
936           (FBEQ F8RC:$RA,bb:$DISP)>;
937 def : Pat<(brcond (setueq F8RC:$RA, immFPZ), bb:$DISP),
938           (FBEQ F8RC:$RA,bb:$DISP)>;
939
940 def : Pat<(brcond (setoge F8RC:$RA, immFPZ), bb:$DISP),
941           (FBGE F8RC:$RA,bb:$DISP)>;
942 def : Pat<(brcond (setuge F8RC:$RA, immFPZ), bb:$DISP),
943           (FBGE F8RC:$RA,bb:$DISP)>;
944
945 def : Pat<(brcond (setogt F8RC:$RA, immFPZ), bb:$DISP),
946           (FBGT F8RC:$RA,bb:$DISP)>;
947 def : Pat<(brcond (setugt F8RC:$RA, immFPZ), bb:$DISP),
948           (FBGT F8RC:$RA,bb:$DISP)>;
949
950 def : Pat<(brcond (setole F8RC:$RA, immFPZ), bb:$DISP),
951           (FBLE F8RC:$RA,bb:$DISP)>;
952 def : Pat<(brcond (setule F8RC:$RA, immFPZ), bb:$DISP),
953           (FBLE F8RC:$RA,bb:$DISP)>;
954
955 def : Pat<(brcond (setolt F8RC:$RA, immFPZ), bb:$DISP),
956           (FBLT F8RC:$RA,bb:$DISP)>;
957 def : Pat<(brcond (setult F8RC:$RA, immFPZ), bb:$DISP),
958           (FBLT F8RC:$RA,bb:$DISP)>;
959
960 def : Pat<(brcond (setone F8RC:$RA, immFPZ), bb:$DISP),
961           (FBNE F8RC:$RA,bb:$DISP)>;
962 def : Pat<(brcond (setune F8RC:$RA, immFPZ), bb:$DISP),
963           (FBNE F8RC:$RA,bb:$DISP)>;
964
965 //End Branches
966
967 //S_floating : IEEE Single
968 //T_floating : IEEE Double
969
970 //Unused instructions
971 //Mnemonic Format Opcode Description
972 //CALL_PAL Pcd 00 Trap to PALcode
973 //ECB Mfc 18.E800 Evict cache block
974 //EXCB Mfc 18.0400 Exception barrier
975 //FETCH Mfc 18.8000 Prefetch data
976 //FETCH_M Mfc 18.A000 Prefetch data, modify intent
977 //LDL_L Mem 2A Load sign-extended longword locked
978 //LDQ_L Mem 2B Load quadword locked
979 //LDQ_U Mem 0B Load unaligned quadword
980 //MB Mfc 18.4000 Memory barrier
981 //STL_C Mem 2E Store longword conditional
982 //STQ_C Mem 2F Store quadword conditional
983 //STQ_U Mem 0F Store unaligned quadword
984 //TRAPB Mfc 18.0000 Trap barrier
985 //WH64 Mfc 18.F800 Write hint \14 64 bytes
986 //WMB Mfc 18.4400 Write memory barrier
987 //MF_FPCR F-P 17.025 Move from FPCR
988 //MT_FPCR F-P 17.024 Move to FPCR
989 //There are in the Multimedia extentions, so let's not use them yet
990 //def MAXSB8  : OForm<0x1C, 0x3E, "MAXSB8 $RA,$RB,$RC">; //Vector signed byte maximum
991 //def MAXSW4 : OForm< 0x1C, 0x3F, "MAXSW4 $RA,$RB,$RC">; //Vector signed word maximum
992 //def MAXUB8  : OForm<0x1C, 0x3C, "MAXUB8 $RA,$RB,$RC">; //Vector unsigned byte maximum
993 //def MAXUW4 : OForm< 0x1C, 0x3D, "MAXUW4 $RA,$RB,$RC">; //Vector unsigned word maximum
994 //def MINSB8 : OForm< 0x1C, 0x38, "MINSB8 $RA,$RB,$RC">; //Vector signed byte minimum
995 //def MINSW4 : OForm< 0x1C, 0x39, "MINSW4 $RA,$RB,$RC">; //Vector signed word minimum
996 //def MINUB8 : OForm< 0x1C, 0x3A, "MINUB8 $RA,$RB,$RC">; //Vector unsigned byte minimum
997 //def MINUW4 : OForm< 0x1C, 0x3B, "MINUW4 $RA,$RB,$RC">; //Vector unsigned word minimum
998 //def PERR : OForm< 0x1C, 0x31, "PERR $RA,$RB,$RC">; //Pixel error
999 //def PKLB : OForm< 0x1C, 0x37, "PKLB $RA,$RB,$RC">; //Pack longwords to bytes
1000 //def PKWB  : OForm<0x1C, 0x36, "PKWB $RA,$RB,$RC">; //Pack words to bytes
1001 //def UNPKBL : OForm< 0x1C, 0x35, "UNPKBL $RA,$RB,$RC">; //Unpack bytes to longwords
1002 //def UNPKBW : OForm< 0x1C, 0x34, "UNPKBW $RA,$RB,$RC">; //Unpack bytes to words
1003 //CVTLQ F-P 17.010 Convert longword to quadword
1004 //CVTQL F-P 17.030 Convert quadword to longword
1005 //def AMASK    : OForm< 0x11, 0x61, "AMASK $RA,$RB,$RC", []>; //Architecture mask
1006 //def AMASKi   : OFormL<0x11, 0x61, "AMASK $RA,$L,$RC", []>; //Architecture mask
1007
1008
1009 //Constant handling
1010
1011 def immConst2Part  : PatLeaf<(imm), [{
1012   //true if imm fits in a LDAH LDA pair
1013   int64_t val = (int64_t)N->getValue();
1014   return (val <= IMM_FULLHIGH  && val >= IMM_FULLLOW);
1015 }]>;
1016 def immConst2PartInt  : PatLeaf<(imm), [{
1017   //true if imm fits in a LDAH LDA pair with zeroext
1018   uint64_t uval = N->getValue();
1019   int32_t val32 = (int32_t)uval;
1020   return ((uval >> 32) == 0 && //empty upper bits
1021           val32 <= IMM_FULLHIGH);
1022 //          val32 >= IMM_FULLLOW  + IMM_LOW  * IMM_MULT); //Always True
1023 }], SExt32>;
1024
1025 def : Pat<(i64 immConst2Part:$imm),
1026           (LDA (LL16 immConst2Part:$imm), (LDAH (LH16 immConst2Part:$imm), R31))>;
1027
1028 def : Pat<(i64 immSExt16:$imm),
1029           (LDA immSExt16:$imm, R31)>;
1030
1031 def : Pat<(i64 immSExt16int:$imm),
1032           (ZAPNOTi (LDA (SExt16 immSExt16int:$imm), R31), 15)>;
1033 def : Pat<(i64 immConst2PartInt:$imm),
1034           (ZAPNOTi (LDA (LL16 (SExt32 immConst2PartInt:$imm)), 
1035                         (LDAH (LH16 (SExt32 immConst2PartInt:$imm)), R31)), 15)>;
1036
1037
1038 //TODO: I want to just define these like this!
1039 //def : Pat<(i64 0),
1040 //          (R31)>;
1041 //def : Pat<(f64 0.0),
1042 //          (F31)>;
1043 //def : Pat<(f64 -0.0),
1044 //          (CPYSNT F31, F31)>;
1045 //def : Pat<(f32 0.0),
1046 //          (F31)>;
1047 //def : Pat<(f32 -0.0),
1048 //          (CPYSNS F31, F31)>;
1049
1050 //Misc Patterns:
1051
1052 def : Pat<(sext_inreg GPRC:$RB, i32),
1053           (ADDLi GPRC:$RB, 0)>;
1054
1055 def : Pat<(fabs F8RC:$RB),
1056           (CPYST F31, F8RC:$RB)>;
1057 def : Pat<(fabs F4RC:$RB),
1058           (CPYSS F31, F4RC:$RB)>;
1059 def : Pat<(fneg F8RC:$RB),
1060           (CPYSNT F8RC:$RB, F8RC:$RB)>;
1061 def : Pat<(fneg F4RC:$RB),
1062           (CPYSNS F4RC:$RB, F4RC:$RB)>;
1063
1064 def : Pat<(fcopysign F4RC:$A, (fneg F4RC:$B)),
1065           (CPYSNS F4RC:$B, F4RC:$A)>;
1066 def : Pat<(fcopysign F8RC:$A, (fneg F8RC:$B)),
1067           (CPYSNT F8RC:$B, F8RC:$A)>;
1068 def : Pat<(fcopysign F4RC:$A, (fneg F8RC:$B)),
1069           (CPYSNSt F8RC:$B, F4RC:$A)>;
1070 def : Pat<(fcopysign F8RC:$A, (fneg F4RC:$B)),
1071           (CPYSNTs F4RC:$B, F8RC:$A)>;
1072
1073 //Yes, signed multiply high is ugly
1074 def : Pat<(mulhs GPRC:$RA, GPRC:$RB),
1075           (SUBQ (UMULH GPRC:$RA, GPRC:$RB), (ADDQ (CMOVGE GPRC:$RB, R31, GPRC:$RA), 
1076                                                  (CMOVGE GPRC:$RA, R31, GPRC:$RB)))>;
1077
1078 //Stupid crazy arithmetic stuff:
1079 def : Pat<(mul GPRC:$RA, 5), (S4ADDQ GPRC:$RA, GPRC:$RA)>;
1080 def : Pat<(mul GPRC:$RA, 3), (S4SUBQ GPRC:$RA, GPRC:$RA)>;
1081
1082 def : Pat<(mul GPRC:$RA, immRem1:$imm), 
1083           (ADDQ (SL GPRC:$RA, (nearP2X immRem1:$imm)), GPRC:$RA)>;
1084 def : Pat<(mul GPRC:$RA, immRem3:$imm),
1085           (ADDQ (SL GPRC:$RA, (nearP2X immRem3:$imm)), (S4SUBQ GPRC:$RA, GPRC:$RA))>;
1086 def : Pat<(mul GPRC:$RA, immRem5:$imm),
1087           (ADDQ (SL GPRC:$RA, (nearP2X immRem5:$imm)), (S4ADDQ GPRC:$RA, GPRC:$RA))>;
1088 def : Pat<(mul GPRC:$RA, immRem4:$imm),
1089           (S4ADDQ GPRC:$RA, (SL GPRC:$RA, (nearP2X immRem4:$imm)))>;
1090 def : Pat<(mul GPRC:$RA, immRemP2:$imm),
1091           (ADDQ (SL GPRC:$RA, (nearP2X immRemP2:$imm)), (SLi GPRC:$RA, (nearP2RemX immRemP2:$imm)))>;
1092
1093 def : Pat<(mul GPRC:$RA, immRem1n:$imm), 
1094           (SUBQ (SL GPRC:$RA, (nearP2X immRem1n:$imm)), GPRC:$RA)>;
1095 def : Pat<(mul GPRC:$RA, immRem3n:$imm),
1096           (SUBQ (SL GPRC:$RA, (nearP2X immRem3n:$imm)), (S4SUBQ GPRC:$RA, GPRC:$RA))>;
1097 def : Pat<(mul GPRC:$RA, immRem5n:$imm),
1098           (SUBQ (SL GPRC:$RA, (nearP2X immRem5n:$imm)), (S4ADDQ GPRC:$RA, GPRC:$RA))>;
1099 def : Pat<(mul GPRC:$RA, immRemP2n:$imm),
1100           (SUBQ (SL GPRC:$RA, (nearP2X immRemP2n:$imm)), (SLi GPRC:$RA, (nearP2RemX immRemP2n:$imm)))>;