Fix the encodings of these new instructions, hopefully fixing the JIT
[oota-llvm.git] / lib / Target / X86 / X86InstrInfo.td
1 //===- X86InstrInfo.td - Describe the X86 Instruction Set -------*- C++ -*-===//
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 // This file describes the X86 instruction set, defining the instructions, and
11 // properties of the instructions which are needed for code generation, machine
12 // code emission, and analysis.
13 //
14 //===----------------------------------------------------------------------===//
15
16 //===----------------------------------------------------------------------===//
17 // X86 specific DAG Nodes.
18 //
19
20 def SDTIntShiftDOp: SDTypeProfile<1, 3,
21                                   [SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>,
22                                    SDTCisInt<0>, SDTCisInt<3>]>;
23
24 def SDTX86CmpTest : SDTypeProfile<0, 2, [SDTCisSameAs<0, 1>]>;
25
26 def SDTX86Cmov    : SDTypeProfile<1, 3,
27                                   [SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>,
28                                    SDTCisVT<3, i8>]>;
29
30 def SDTX86BrCond  : SDTypeProfile<0, 2,
31                                   [SDTCisVT<0, OtherVT>, SDTCisVT<1, i8>]>;
32
33 def SDTX86SetCC   : SDTypeProfile<1, 1,
34                                   [SDTCisVT<0, i8>, SDTCisVT<1, i8>]>;
35
36 def SDTX86Ret     : SDTypeProfile<0, 1, [SDTCisVT<0, i16>]>;
37
38 def SDT_X86CallSeqStart : SDTypeProfile<0, 1, [ SDTCisVT<0, i32> ]>;
39 def SDT_X86CallSeqEnd   : SDTypeProfile<0, 2, [ SDTCisVT<0, i32>,
40                                                 SDTCisVT<1, i32> ]>;
41
42 def SDT_X86Call   : SDTypeProfile<0, 1, [SDTCisVT<0, i32>]>;
43
44 def SDTX86RepStr  : SDTypeProfile<0, 1, [SDTCisVT<0, OtherVT>]>;
45
46 def SDTX86RdTsc   : SDTypeProfile<0, 0, []>;
47
48 def SDTX86Wrapper : SDTypeProfile<1, 1, [SDTCisSameAs<0, 1>, SDTCisPtrTy<0>]>;
49
50 def X86shld    : SDNode<"X86ISD::SHLD",     SDTIntShiftDOp>;
51 def X86shrd    : SDNode<"X86ISD::SHRD",     SDTIntShiftDOp>;
52
53 def X86cmp     : SDNode<"X86ISD::CMP" ,     SDTX86CmpTest,
54                         [SDNPOutFlag]>;
55 def X86test    : SDNode<"X86ISD::TEST",     SDTX86CmpTest,
56                         [SDNPOutFlag]>;
57
58 def X86cmov    : SDNode<"X86ISD::CMOV",     SDTX86Cmov,    
59                         [SDNPInFlag, SDNPOutFlag]>;
60 def X86brcond  : SDNode<"X86ISD::BRCOND",   SDTX86BrCond,
61                         [SDNPHasChain, SDNPInFlag]>;
62 def X86setcc   : SDNode<"X86ISD::SETCC",    SDTX86SetCC,
63                         [SDNPInFlag, SDNPOutFlag]>;
64
65 def X86retflag : SDNode<"X86ISD::RET_FLAG", SDTX86Ret,
66                         [SDNPHasChain, SDNPOptInFlag]>;
67
68 def X86callseq_start :
69                  SDNode<"ISD::CALLSEQ_START", SDT_X86CallSeqStart,
70                         [SDNPHasChain]>;
71 def X86callseq_end :
72                  SDNode<"ISD::CALLSEQ_END",   SDT_X86CallSeqEnd,
73                         [SDNPHasChain, SDNPInFlag, SDNPOutFlag]>;
74
75 def X86call    : SDNode<"X86ISD::CALL",     SDT_X86Call,
76                         [SDNPHasChain, SDNPOutFlag, SDNPOptInFlag]>;
77
78 def X86rep_stos: SDNode<"X86ISD::REP_STOS", SDTX86RepStr,
79                         [SDNPHasChain, SDNPInFlag, SDNPOutFlag]>;
80 def X86rep_movs: SDNode<"X86ISD::REP_MOVS", SDTX86RepStr,
81                         [SDNPHasChain, SDNPInFlag, SDNPOutFlag]>;
82
83 def X86rdtsc   : SDNode<"X86ISD::RDTSC_DAG",SDTX86RdTsc,
84                         [SDNPHasChain, SDNPOutFlag]>;
85
86 def X86Wrapper : SDNode<"X86ISD::Wrapper",  SDTX86Wrapper>;
87
88 //===----------------------------------------------------------------------===//
89 // X86 Operand Definitions.
90 //
91
92 // *mem - Operand definitions for the funky X86 addressing mode operands.
93 //
94 class X86MemOperand<string printMethod> : Operand<i32> {
95   let PrintMethod = printMethod;
96   let NumMIOperands = 4;
97   let MIOperandInfo = (ops R32, i8imm, R32, i32imm);
98 }
99
100 def i8mem   : X86MemOperand<"printi8mem">;
101 def i16mem  : X86MemOperand<"printi16mem">;
102 def i32mem  : X86MemOperand<"printi32mem">;
103 def i64mem  : X86MemOperand<"printi64mem">;
104 def i128mem : X86MemOperand<"printi128mem">;
105 def f32mem  : X86MemOperand<"printf32mem">;
106 def f64mem  : X86MemOperand<"printf64mem">;
107 def f128mem : X86MemOperand<"printf128mem">;
108
109 def SSECC : Operand<i8> {
110   let PrintMethod = "printSSECC";
111 }
112
113 def piclabel: Operand<i32> {
114   let PrintMethod = "printPICLabel";
115 }
116
117 // A couple of more descriptive operand definitions.
118 // 16-bits but only 8 bits are significant.
119 def i16i8imm  : Operand<i16>;
120 // 32-bits but only 8 bits are significant.
121 def i32i8imm  : Operand<i32>;
122
123 // Branch targets have OtherVT type.
124 def brtarget : Operand<OtherVT>;
125
126 //===----------------------------------------------------------------------===//
127 // X86 Complex Pattern Definitions.
128 //
129
130 // Define X86 specific addressing mode.
131 def addr    : ComplexPattern<i32, 4, "SelectAddr", []>;
132 def leaaddr : ComplexPattern<i32, 4, "SelectLEAAddr",
133                              [add, mul, shl, frameindex]>;
134
135 //===----------------------------------------------------------------------===//
136 // X86 Instruction Format Definitions.
137 //
138
139 // Format specifies the encoding used by the instruction.  This is part of the
140 // ad-hoc solution used to emit machine instruction encodings by our machine
141 // code emitter.
142 class Format<bits<6> val> {
143   bits<6> Value = val;
144 }
145
146 def Pseudo     : Format<0>; def RawFrm     : Format<1>;
147 def AddRegFrm  : Format<2>; def MRMDestReg : Format<3>;
148 def MRMDestMem : Format<4>; def MRMSrcReg  : Format<5>;
149 def MRMSrcMem  : Format<6>;
150 def MRM0r  : Format<16>; def MRM1r  : Format<17>; def MRM2r  : Format<18>;
151 def MRM3r  : Format<19>; def MRM4r  : Format<20>; def MRM5r  : Format<21>;
152 def MRM6r  : Format<22>; def MRM7r  : Format<23>;
153 def MRM0m  : Format<24>; def MRM1m  : Format<25>; def MRM2m  : Format<26>;
154 def MRM3m  : Format<27>; def MRM4m  : Format<28>; def MRM5m  : Format<29>;
155 def MRM6m  : Format<30>; def MRM7m  : Format<31>;
156 def MRMInitReg : Format<32>;
157
158 //===----------------------------------------------------------------------===//
159 // X86 Instruction Predicate Definitions.
160 def HasMMX  : Predicate<"Subtarget->hasMMX()">;
161 def HasSSE1 : Predicate<"Subtarget->hasSSE1()">;
162 def HasSSE2 : Predicate<"Subtarget->hasSSE2()">;
163 def HasSSE3 : Predicate<"Subtarget->hasSSE3()">;
164 def FPStack : Predicate<"!Subtarget->hasSSE2()">;
165
166 //===----------------------------------------------------------------------===//
167 // X86 specific pattern fragments.
168 //
169
170 // ImmType - This specifies the immediate type used by an instruction. This is
171 // part of the ad-hoc solution used to emit machine instruction encodings by our
172 // machine code emitter.
173 class ImmType<bits<2> val> {
174   bits<2> Value = val;
175 }
176 def NoImm  : ImmType<0>;
177 def Imm8   : ImmType<1>;
178 def Imm16  : ImmType<2>;
179 def Imm32  : ImmType<3>;
180
181 // FPFormat - This specifies what form this FP instruction has.  This is used by
182 // the Floating-Point stackifier pass.
183 class FPFormat<bits<3> val> {
184   bits<3> Value = val;
185 }
186 def NotFP      : FPFormat<0>;
187 def ZeroArgFP  : FPFormat<1>;
188 def OneArgFP   : FPFormat<2>;
189 def OneArgFPRW : FPFormat<3>;
190 def TwoArgFP   : FPFormat<4>;
191 def CompareFP  : FPFormat<5>;
192 def CondMovFP  : FPFormat<6>;
193 def SpecialFP  : FPFormat<7>;
194
195
196 class X86Inst<bits<8> opcod, Format f, ImmType i, dag ops, string AsmStr>
197   : Instruction {
198   let Namespace = "X86";
199
200   bits<8> Opcode = opcod;
201   Format Form = f;
202   bits<6> FormBits = Form.Value;
203   ImmType ImmT = i;
204   bits<2> ImmTypeBits = ImmT.Value;
205
206   dag OperandList = ops;
207   string AsmString = AsmStr;
208
209   //
210   // Attributes specific to X86 instructions...
211   //
212   bit hasOpSizePrefix = 0; // Does this inst have a 0x66 prefix?
213
214   bits<4> Prefix = 0;       // Which prefix byte does this inst have?
215   FPFormat FPForm;          // What flavor of FP instruction is this?
216   bits<3> FPFormBits = 0;
217 }
218
219 class Imp<list<Register> uses, list<Register> defs> {
220   list<Register> Uses = uses;
221   list<Register> Defs = defs;
222 }
223
224
225 // Prefix byte classes which are used to indicate to the ad-hoc machine code
226 // emitter that various prefix bytes are required.
227 class OpSize { bit hasOpSizePrefix = 1; }
228 class TB     { bits<4> Prefix = 1; }
229 class REP    { bits<4> Prefix = 2; }
230 class D8     { bits<4> Prefix = 3; }
231 class D9     { bits<4> Prefix = 4; }
232 class DA     { bits<4> Prefix = 5; }
233 class DB     { bits<4> Prefix = 6; }
234 class DC     { bits<4> Prefix = 7; }
235 class DD     { bits<4> Prefix = 8; }
236 class DE     { bits<4> Prefix = 9; }
237 class DF     { bits<4> Prefix = 10; }
238 class XD     { bits<4> Prefix = 11; }
239 class XS     { bits<4> Prefix = 12; }
240
241
242 //===----------------------------------------------------------------------===//
243 // Pattern fragments...
244 //
245
246 // X86 specific condition code. These correspond to CondCode in
247 // X86ISelLowering.h. They must be kept in synch.
248 def X86_COND_A   : PatLeaf<(i8 0)>;
249 def X86_COND_AE  : PatLeaf<(i8 1)>;
250 def X86_COND_B   : PatLeaf<(i8 2)>;
251 def X86_COND_BE  : PatLeaf<(i8 3)>;
252 def X86_COND_E   : PatLeaf<(i8 4)>;
253 def X86_COND_G   : PatLeaf<(i8 5)>;
254 def X86_COND_GE  : PatLeaf<(i8 6)>;
255 def X86_COND_L   : PatLeaf<(i8 7)>;
256 def X86_COND_LE  : PatLeaf<(i8 8)>;
257 def X86_COND_NE  : PatLeaf<(i8 9)>;
258 def X86_COND_NO  : PatLeaf<(i8 10)>;
259 def X86_COND_NP  : PatLeaf<(i8 11)>;
260 def X86_COND_NS  : PatLeaf<(i8 12)>;
261 def X86_COND_O   : PatLeaf<(i8 13)>;
262 def X86_COND_P   : PatLeaf<(i8 14)>;
263 def X86_COND_S   : PatLeaf<(i8 15)>;
264
265 def i16immSExt8  : PatLeaf<(i16 imm), [{
266   // i16immSExt8 predicate - True if the 16-bit immediate fits in a 8-bit
267   // sign extended field.
268   return (int)N->getValue() == (signed char)N->getValue();
269 }]>;
270
271 def i32immSExt8  : PatLeaf<(i32 imm), [{
272   // i32immSExt8 predicate - True if the 32-bit immediate fits in a 8-bit
273   // sign extended field.
274   return (int)N->getValue() == (signed char)N->getValue();
275 }]>;
276
277 def i16immZExt8  : PatLeaf<(i16 imm), [{
278   // i16immZExt8 predicate - True if the 16-bit immediate fits in a 8-bit zero
279   // extended field.
280   return (unsigned)N->getValue() == (unsigned char)N->getValue();
281 }]>;
282
283 // Helper fragments for loads.
284 def loadi8  : PatFrag<(ops node:$ptr), (i8  (load node:$ptr))>;
285 def loadi16 : PatFrag<(ops node:$ptr), (i16 (load node:$ptr))>;
286 def loadi32 : PatFrag<(ops node:$ptr), (i32 (load node:$ptr))>;
287
288 def loadf32 : PatFrag<(ops node:$ptr), (f32 (load node:$ptr))>;
289 def loadf64 : PatFrag<(ops node:$ptr), (f64 (load node:$ptr))>;
290
291 def sextloadi16i1  : PatFrag<(ops node:$ptr), (i16 (sextload node:$ptr, i1))>;
292 def sextloadi32i1  : PatFrag<(ops node:$ptr), (i32 (sextload node:$ptr, i1))>;
293 def sextloadi16i8  : PatFrag<(ops node:$ptr), (i16 (sextload node:$ptr, i8))>;
294 def sextloadi32i8  : PatFrag<(ops node:$ptr), (i32 (sextload node:$ptr, i8))>;
295 def sextloadi32i16 : PatFrag<(ops node:$ptr), (i32 (sextload node:$ptr, i16))>;
296
297 def zextloadi8i1   : PatFrag<(ops node:$ptr), (i8  (zextload node:$ptr, i1))>;
298 def zextloadi16i1  : PatFrag<(ops node:$ptr), (i16 (zextload node:$ptr, i1))>;
299 def zextloadi32i1  : PatFrag<(ops node:$ptr), (i32 (zextload node:$ptr, i1))>;
300 def zextloadi16i8  : PatFrag<(ops node:$ptr), (i16 (zextload node:$ptr, i8))>;
301 def zextloadi32i8  : PatFrag<(ops node:$ptr), (i32 (zextload node:$ptr, i8))>;
302 def zextloadi32i16 : PatFrag<(ops node:$ptr), (i32 (zextload node:$ptr, i16))>;
303
304 def extloadi8i1    : PatFrag<(ops node:$ptr), (i8  (extload node:$ptr, i1))>;
305
306 //===----------------------------------------------------------------------===//
307 // Instruction templates...
308
309 class I<bits<8> o, Format f, dag ops, string asm, list<dag> pattern>
310   : X86Inst<o, f, NoImm, ops, asm> {
311   let Pattern = pattern;
312 }
313 class Ii8 <bits<8> o, Format f, dag ops, string asm, list<dag> pattern>
314   : X86Inst<o, f, Imm8 , ops, asm> {
315   let Pattern = pattern;
316 }
317 class Ii16<bits<8> o, Format f, dag ops, string asm, list<dag> pattern>
318   : X86Inst<o, f, Imm16, ops, asm> {
319   let Pattern = pattern;
320 }
321 class Ii32<bits<8> o, Format f, dag ops, string asm, list<dag> pattern>
322   : X86Inst<o, f, Imm32, ops, asm> {
323   let Pattern = pattern;
324 }
325
326 //===----------------------------------------------------------------------===//
327 // Instruction list...
328 //
329
330 def ADJCALLSTACKDOWN : I<0, Pseudo, (ops i32imm:$amt), "#ADJCALLSTACKDOWN",
331                          [(X86callseq_start imm:$amt)]>;
332 def ADJCALLSTACKUP   : I<0, Pseudo, (ops i32imm:$amt1, i32imm:$amt2),
333                          "#ADJCALLSTACKUP",
334                          [(X86callseq_end imm:$amt1, imm:$amt2)]>;
335 def IMPLICIT_USE     : I<0, Pseudo, (ops variable_ops), "#IMPLICIT_USE", []>;
336 def IMPLICIT_DEF     : I<0, Pseudo, (ops variable_ops), "#IMPLICIT_DEF", []>;
337 def IMPLICIT_DEF_R8  : I<0, Pseudo, (ops R8:$dst),
338                          "#IMPLICIT_DEF $dst",
339                          [(set R8:$dst, (undef))]>;
340 def IMPLICIT_DEF_R16  : I<0, Pseudo, (ops R16:$dst),
341                          "#IMPLICIT_DEF $dst",
342                          [(set R16:$dst, (undef))]>;
343 def IMPLICIT_DEF_R32  : I<0, Pseudo, (ops R32:$dst),
344                          "#IMPLICIT_DEF $dst",
345                          [(set R32:$dst, (undef))]>;
346
347 // Nop
348 def NOOP : I<0x90, RawFrm, (ops), "nop", []>;
349
350 //===----------------------------------------------------------------------===//
351 //  Control Flow Instructions...
352 //
353
354 // Return instructions.
355 let isTerminator = 1, isReturn = 1, isBarrier = 1,
356     hasCtrlDep = 1, noResults = 1 in {
357   def RET    : I<0xC3, RawFrm, (ops), "ret", [(X86retflag 0)]>;
358   def RETI   : Ii16<0xC2, RawFrm, (ops i16imm:$amt), "ret $amt",
359                     [(X86retflag imm:$amt)]>;
360 }
361
362 // All branches are RawFrm, Void, Branch, and Terminators
363 let isBranch = 1, isTerminator = 1, noResults = 1 in
364   class IBr<bits<8> opcode, dag ops, string asm, list<dag> pattern> :
365         I<opcode, RawFrm, ops, asm, pattern>;
366
367 // Conditional branches
368 let isBarrier = 1 in
369   def JMP : IBr<0xE9, (ops brtarget:$dst), "jmp $dst", [(br bb:$dst)]>;
370
371 def JE  : IBr<0x84, (ops brtarget:$dst), "je $dst",
372               [(X86brcond bb:$dst, X86_COND_E)]>, TB;
373 def JNE : IBr<0x85, (ops brtarget:$dst), "jne $dst",
374               [(X86brcond bb:$dst, X86_COND_NE)]>, TB;
375 def JL  : IBr<0x8C, (ops brtarget:$dst), "jl $dst",
376               [(X86brcond bb:$dst, X86_COND_L)]>, TB;
377 def JLE : IBr<0x8E, (ops brtarget:$dst), "jle $dst",
378               [(X86brcond bb:$dst, X86_COND_LE)]>, TB;
379 def JG  : IBr<0x8F, (ops brtarget:$dst), "jg $dst",
380               [(X86brcond bb:$dst, X86_COND_G)]>, TB;
381 def JGE : IBr<0x8D, (ops brtarget:$dst), "jge $dst",
382               [(X86brcond bb:$dst, X86_COND_GE)]>, TB;
383
384 def JB  : IBr<0x82, (ops brtarget:$dst), "jb $dst",
385               [(X86brcond bb:$dst, X86_COND_B)]>, TB;
386 def JBE : IBr<0x86, (ops brtarget:$dst), "jbe $dst",
387               [(X86brcond bb:$dst, X86_COND_BE)]>, TB;
388 def JA  : IBr<0x87, (ops brtarget:$dst), "ja $dst",
389               [(X86brcond bb:$dst, X86_COND_A)]>, TB;
390 def JAE : IBr<0x83, (ops brtarget:$dst), "jae $dst",
391               [(X86brcond bb:$dst, X86_COND_AE)]>, TB;
392
393 def JS  : IBr<0x88, (ops brtarget:$dst), "js $dst",
394               [(X86brcond bb:$dst, X86_COND_S)]>, TB;
395 def JNS : IBr<0x89, (ops brtarget:$dst), "jns $dst",
396               [(X86brcond bb:$dst, X86_COND_NS)]>, TB;
397 def JP  : IBr<0x8A, (ops brtarget:$dst), "jp $dst",
398               [(X86brcond bb:$dst, X86_COND_P)]>, TB;
399 def JNP : IBr<0x8B, (ops brtarget:$dst), "jnp $dst",
400               [(X86brcond bb:$dst, X86_COND_NP)]>, TB;
401 def JO  : IBr<0x80, (ops brtarget:$dst), "jo $dst",
402               [(X86brcond bb:$dst, X86_COND_O)]>, TB;
403 def JNO : IBr<0x81, (ops brtarget:$dst), "jno $dst",
404               [(X86brcond bb:$dst, X86_COND_NO)]>, TB;
405
406 //===----------------------------------------------------------------------===//
407 //  Call Instructions...
408 //
409 let isCall = 1, noResults = 1 in
410   // All calls clobber the non-callee saved registers...
411   let Defs = [EAX, ECX, EDX, FP0, FP1, FP2, FP3, FP4, FP5, FP6, ST0,
412               XMM0, XMM1, XMM2, XMM3, XMM4, XMM5, XMM6, XMM7] in {
413     def CALLpcrel32 : I<0xE8, RawFrm, (ops i32imm:$dst), "call ${dst:call}",
414                       []>;
415     def CALL32r     : I<0xFF, MRM2r, (ops R32:$dst), "call {*}$dst",
416                       [(X86call R32:$dst)]>;
417     def CALL32m     : I<0xFF, MRM2m, (ops i32mem:$dst), "call {*}$dst",
418                       [(X86call (loadi32 addr:$dst))]>;
419   }
420
421 // Tail call stuff.
422 let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1, noResults = 1 in
423   def TAILJMPd : IBr<0xE9, (ops i32imm:$dst), "jmp ${dst:call}  # TAIL CALL", []>;
424 let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1, noResults = 1 in
425   def TAILJMPr : I<0xFF, MRM4r, (ops R32:$dst), "jmp {*}$dst  # TAIL CALL", []>;
426 let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1, noResults = 1 in
427   def TAILJMPm : I<0xFF, MRM4m, (ops i32mem:$dst),
428                    "jmp {*}$dst  # TAIL CALL", []>;
429
430 // ADJSTACKPTRri - This is a standard ADD32ri instruction, identical in every
431 // way, except that it is marked as being a terminator.  This causes the epilog
432 // inserter to insert reloads of callee saved registers BEFORE this.  We need
433 // this until we have a more accurate way of tracking where the stack pointer is
434 // within a function.
435 let isTerminator = 1, isTwoAddress = 1 in
436   def ADJSTACKPTRri : Ii32<0x81, MRM0r, (ops R32:$dst, R32:$src1, i32imm:$src2),
437                            "add{l} {$src2, $dst|$dst, $src2}", []>;
438
439 //===----------------------------------------------------------------------===//
440 //  Miscellaneous Instructions...
441 //
442 def LEAVE    : I<0xC9, RawFrm,
443                  (ops), "leave", []>, Imp<[EBP,ESP],[EBP,ESP]>;
444 def POP32r   : I<0x58, AddRegFrm,
445                  (ops R32:$reg), "pop{l} $reg", []>, Imp<[ESP],[ESP]>;
446
447 def MovePCtoStack : I<0, Pseudo, (ops piclabel:$label),
448                       "call $label", []>;
449
450 let isTwoAddress = 1 in                               // R32 = bswap R32
451   def BSWAP32r : I<0xC8, AddRegFrm,
452                    (ops R32:$dst, R32:$src),
453                    "bswap{l} $dst", 
454                    [(set R32:$dst, (bswap R32:$src))]>, TB;
455
456 def XCHG8rr  : I<0x86, MRMDestReg,                    // xchg R8, R8
457                  (ops R8:$src1, R8:$src2),
458                  "xchg{b} {$src2|$src1}, {$src1|$src2}", []>;
459 def XCHG16rr : I<0x87, MRMDestReg,                    // xchg R16, R16
460                  (ops R16:$src1, R16:$src2),
461                  "xchg{w} {$src2|$src1}, {$src1|$src2}", []>, OpSize;
462 def XCHG32rr : I<0x87, MRMDestReg,                    // xchg R32, R32
463                  (ops R32:$src1, R32:$src2),
464                  "xchg{l} {$src2|$src1}, {$src1|$src2}", []>;
465
466 def XCHG8mr  : I<0x86, MRMDestMem,
467                  (ops i8mem:$src1, R8:$src2),
468                  "xchg{b} {$src2|$src1}, {$src1|$src2}", []>;
469 def XCHG16mr : I<0x87, MRMDestMem,
470                  (ops i16mem:$src1, R16:$src2),
471                  "xchg{w} {$src2|$src1}, {$src1|$src2}", []>, OpSize;
472 def XCHG32mr : I<0x87, MRMDestMem,
473                  (ops i32mem:$src1, R32:$src2),
474                  "xchg{l} {$src2|$src1}, {$src1|$src2}", []>;
475 def XCHG8rm  : I<0x86, MRMSrcMem,
476                  (ops R8:$src1, i8mem:$src2),
477                  "xchg{b} {$src2|$src1}, {$src1|$src2}", []>;
478 def XCHG16rm : I<0x87, MRMSrcMem,
479                  (ops R16:$src1, i16mem:$src2),
480                  "xchg{w} {$src2|$src1}, {$src1|$src2}", []>, OpSize;
481 def XCHG32rm : I<0x87, MRMSrcMem,
482                  (ops R32:$src1, i32mem:$src2),
483                  "xchg{l} {$src2|$src1}, {$src1|$src2}", []>;
484
485 def LEA16r   : I<0x8D, MRMSrcMem,
486                  (ops R16:$dst, i32mem:$src),
487                  "lea{w} {$src|$dst}, {$dst|$src}", []>, OpSize;
488 def LEA32r   : I<0x8D, MRMSrcMem,
489                  (ops R32:$dst, i32mem:$src),
490                  "lea{l} {$src|$dst}, {$dst|$src}",
491                  [(set R32:$dst, leaaddr:$src)]>;
492
493 def REP_MOVSB : I<0xA4, RawFrm, (ops), "{rep;movsb|rep movsb}",
494                   [(X86rep_movs i8)]>,
495                 Imp<[ECX,EDI,ESI], [ECX,EDI,ESI]>, REP;
496 def REP_MOVSW : I<0xA5, RawFrm, (ops), "{rep;movsw|rep movsw}",
497                   [(X86rep_movs i16)]>,
498                 Imp<[ECX,EDI,ESI], [ECX,EDI,ESI]>, REP, OpSize;
499 def REP_MOVSD : I<0xA5, RawFrm, (ops), "{rep;movsd|rep movsd}",
500                   [(X86rep_movs i32)]>,
501                 Imp<[ECX,EDI,ESI], [ECX,EDI,ESI]>, REP;
502
503 def REP_STOSB : I<0xAA, RawFrm, (ops), "{rep;stosb|rep stosb}",
504                   [(X86rep_stos i8)]>,
505                 Imp<[AL,ECX,EDI], [ECX,EDI]>, REP;
506 def REP_STOSW : I<0xAB, RawFrm, (ops), "{rep;stosw|rep stosw}",
507                   [(X86rep_stos i16)]>,
508                 Imp<[AX,ECX,EDI], [ECX,EDI]>, REP, OpSize;
509 def REP_STOSD : I<0xAB, RawFrm, (ops), "{rep;stosl|rep stosd}",
510                   [(X86rep_stos i32)]>,
511                 Imp<[EAX,ECX,EDI], [ECX,EDI]>, REP;
512
513
514 //===----------------------------------------------------------------------===//
515 //  Input/Output Instructions...
516 //
517 def IN8rr  : I<0xEC, RawFrm, (ops),
518                "in{b} {%dx, %al|%AL, %DX}",
519                []>,  Imp<[DX], [AL]>;
520 def IN16rr : I<0xED, RawFrm, (ops),
521                "in{w} {%dx, %ax|%AX, %DX}",
522                []>,  Imp<[DX], [AX]>, OpSize;
523 def IN32rr : I<0xED, RawFrm, (ops),
524                "in{l} {%dx, %eax|%EAX, %DX}",
525                []>, Imp<[DX],[EAX]>;
526
527 def IN8ri  : Ii8<0xE4, RawFrm, (ops i16i8imm:$port),
528                   "in{b} {$port, %al|%AL, $port}",
529                  []>,
530              Imp<[], [AL]>;
531 def IN16ri : Ii8<0xE5, RawFrm, (ops i16i8imm:$port),
532                   "in{w} {$port, %ax|%AX, $port}",
533                  []>,
534              Imp<[], [AX]>, OpSize;
535 def IN32ri : Ii8<0xE5, RawFrm, (ops i16i8imm:$port),
536                   "in{l} {$port, %eax|%EAX, $port}",
537                  []>,
538              Imp<[],[EAX]>;
539
540 def OUT8rr  : I<0xEE, RawFrm, (ops),
541                 "out{b} {%al, %dx|%DX, %AL}",
542                 []>,  Imp<[DX,  AL], []>;
543 def OUT16rr : I<0xEF, RawFrm, (ops),
544                 "out{w} {%ax, %dx|%DX, %AX}",
545                 []>,  Imp<[DX,  AX], []>, OpSize;
546 def OUT32rr : I<0xEF, RawFrm, (ops),
547                 "out{l} {%eax, %dx|%DX, %EAX}",
548                 []>, Imp<[DX, EAX], []>;
549
550 def OUT8ir  : Ii8<0xE6, RawFrm, (ops i16i8imm:$port),
551                    "out{b} {%al, $port|$port, %AL}",
552                    []>,
553               Imp<[AL], []>;
554 def OUT16ir : Ii8<0xE7, RawFrm, (ops i16i8imm:$port),
555                    "out{w} {%ax, $port|$port, %AX}",
556                    []>,
557               Imp<[AX], []>, OpSize;
558 def OUT32ir : Ii8<0xE7, RawFrm, (ops i16i8imm:$port),
559                    "out{l} {%eax, $port|$port, %EAX}",
560                    []>,
561               Imp<[EAX], []>;
562
563 //===----------------------------------------------------------------------===//
564 //  Move Instructions...
565 //
566 def MOV8rr  : I<0x88, MRMDestReg, (ops R8 :$dst, R8 :$src),
567                 "mov{b} {$src, $dst|$dst, $src}", []>;
568 def MOV16rr : I<0x89, MRMDestReg, (ops R16:$dst, R16:$src),
569                 "mov{w} {$src, $dst|$dst, $src}", []>, OpSize;
570 def MOV32rr : I<0x89, MRMDestReg, (ops R32:$dst, R32:$src),
571                 "mov{l} {$src, $dst|$dst, $src}", []>;
572 def MOV8ri  : Ii8 <0xB0, AddRegFrm, (ops R8 :$dst, i8imm :$src),
573                    "mov{b} {$src, $dst|$dst, $src}",
574                    [(set R8:$dst, imm:$src)]>;
575 def MOV16ri : Ii16<0xB8, AddRegFrm, (ops R16:$dst, i16imm:$src),
576                    "mov{w} {$src, $dst|$dst, $src}",
577                    [(set R16:$dst, imm:$src)]>, OpSize;
578 def MOV32ri : Ii32<0xB8, AddRegFrm, (ops R32:$dst, i32imm:$src),
579                    "mov{l} {$src, $dst|$dst, $src}",
580                    [(set R32:$dst, imm:$src)]>;
581 def MOV8mi  : Ii8 <0xC6, MRM0m, (ops i8mem :$dst, i8imm :$src),
582                    "mov{b} {$src, $dst|$dst, $src}",
583                    [(store (i8 imm:$src), addr:$dst)]>;
584 def MOV16mi : Ii16<0xC7, MRM0m, (ops i16mem:$dst, i16imm:$src),
585                    "mov{w} {$src, $dst|$dst, $src}",
586                    [(store (i16 imm:$src), addr:$dst)]>, OpSize;
587 def MOV32mi : Ii32<0xC7, MRM0m, (ops i32mem:$dst, i32imm:$src),
588                    "mov{l} {$src, $dst|$dst, $src}",
589                    [(store (i32 imm:$src), addr:$dst)]>;
590
591 def MOV8rm  : I<0x8A, MRMSrcMem, (ops R8 :$dst, i8mem :$src),
592                 "mov{b} {$src, $dst|$dst, $src}",
593                 [(set R8:$dst, (load addr:$src))]>;
594 def MOV16rm : I<0x8B, MRMSrcMem, (ops R16:$dst, i16mem:$src),
595                 "mov{w} {$src, $dst|$dst, $src}",
596                 [(set R16:$dst, (load addr:$src))]>, OpSize;
597 def MOV32rm : I<0x8B, MRMSrcMem, (ops R32:$dst, i32mem:$src),
598                 "mov{l} {$src, $dst|$dst, $src}",
599                 [(set R32:$dst, (load addr:$src))]>;
600
601 def MOV8mr  : I<0x88, MRMDestMem, (ops i8mem :$dst, R8 :$src),
602                 "mov{b} {$src, $dst|$dst, $src}",
603                 [(store R8:$src, addr:$dst)]>;
604 def MOV16mr : I<0x89, MRMDestMem, (ops i16mem:$dst, R16:$src),
605                 "mov{w} {$src, $dst|$dst, $src}",
606                 [(store R16:$src, addr:$dst)]>, OpSize;
607 def MOV32mr : I<0x89, MRMDestMem, (ops i32mem:$dst, R32:$src),
608                 "mov{l} {$src, $dst|$dst, $src}",
609                 [(store R32:$src, addr:$dst)]>;
610                 
611 //===----------------------------------------------------------------------===//
612 //  Fixed-Register Multiplication and Division Instructions...
613 //
614
615 // Extra precision multiplication
616 def MUL8r  : I<0xF6, MRM4r, (ops R8:$src), "mul{b} $src",
617                // FIXME: Used for 8-bit mul, ignore result upper 8 bits.
618                // This probably ought to be moved to a def : Pat<> if the
619                // syntax can be accepted.
620                [(set AL, (mul AL, R8:$src))]>,
621              Imp<[AL],[AX]>;               // AL,AH = AL*R8
622 def MUL16r : I<0xF7, MRM4r, (ops R16:$src), "mul{w} $src", []>,
623              Imp<[AX],[AX,DX]>, OpSize;    // AX,DX = AX*R16
624 def MUL32r : I<0xF7, MRM4r, (ops R32:$src), "mul{l} $src", []>,
625              Imp<[EAX],[EAX,EDX]>;         // EAX,EDX = EAX*R32
626 def MUL8m  : I<0xF6, MRM4m, (ops i8mem :$src),
627                "mul{b} $src",
628                // FIXME: Used for 8-bit mul, ignore result upper 8 bits.
629                // This probably ought to be moved to a def : Pat<> if the
630                // syntax can be accepted.
631                [(set AL, (mul AL, (loadi8 addr:$src)))]>,
632              Imp<[AL],[AX]>;          // AL,AH = AL*[mem8]
633 def MUL16m : I<0xF7, MRM4m, (ops i16mem:$src),
634                "mul{w} $src", []>, Imp<[AX],[AX,DX]>,
635                OpSize; // AX,DX = AX*[mem16]
636 def MUL32m : I<0xF7, MRM4m, (ops i32mem:$src),
637                "mul{l} $src", []>, Imp<[EAX],[EAX,EDX]>;// EAX,EDX = EAX*[mem32]
638
639 def IMUL8r  : I<0xF6, MRM5r, (ops R8:$src), "imul{b} $src", []>,
640               Imp<[AL],[AX]>;               // AL,AH = AL*R8
641 def IMUL16r : I<0xF7, MRM5r, (ops R16:$src), "imul{w} $src", []>,
642               Imp<[AX],[AX,DX]>, OpSize;    // AX,DX = AX*R16
643 def IMUL32r : I<0xF7, MRM5r, (ops R32:$src), "imul{l} $src", []>,
644               Imp<[EAX],[EAX,EDX]>;         // EAX,EDX = EAX*R32
645 def IMUL8m  : I<0xF6, MRM5m, (ops i8mem :$src),
646                 "imul{b} $src", []>, Imp<[AL],[AX]>;        // AL,AH = AL*[mem8]
647 def IMUL16m : I<0xF7, MRM5m, (ops i16mem:$src),
648                 "imul{w} $src", []>, Imp<[AX],[AX,DX]>,
649                 OpSize; // AX,DX = AX*[mem16]
650 def IMUL32m : I<0xF7, MRM5m, (ops i32mem:$src),
651                 "imul{l} $src", []>,
652                 Imp<[EAX],[EAX,EDX]>;  // EAX,EDX = EAX*[mem32]
653
654 // unsigned division/remainder
655 def DIV8r  : I<0xF6, MRM6r, (ops R8:$src),          // AX/r8 = AL,AH
656                "div{b} $src", []>, Imp<[AX],[AX]>;
657 def DIV16r : I<0xF7, MRM6r, (ops R16:$src),         // DX:AX/r16 = AX,DX
658                "div{w} $src", []>, Imp<[AX,DX],[AX,DX]>, OpSize;
659 def DIV32r : I<0xF7, MRM6r, (ops R32:$src),         // EDX:EAX/r32 = EAX,EDX
660                "div{l} $src", []>, Imp<[EAX,EDX],[EAX,EDX]>;
661 def DIV8m  : I<0xF6, MRM6m, (ops i8mem:$src),       // AX/[mem8] = AL,AH
662                "div{b} $src", []>, Imp<[AX],[AX]>;
663 def DIV16m : I<0xF7, MRM6m, (ops i16mem:$src),      // DX:AX/[mem16] = AX,DX
664                "div{w} $src", []>, Imp<[AX,DX],[AX,DX]>, OpSize;
665 def DIV32m : I<0xF7, MRM6m, (ops i32mem:$src),      // EDX:EAX/[mem32] = EAX,EDX
666                "div{l} $src", []>, Imp<[EAX,EDX],[EAX,EDX]>;
667
668 // Signed division/remainder.
669 def IDIV8r : I<0xF6, MRM7r, (ops R8:$src),          // AX/r8 = AL,AH
670                "idiv{b} $src", []>, Imp<[AX],[AX]>;
671 def IDIV16r: I<0xF7, MRM7r, (ops R16:$src),         // DX:AX/r16 = AX,DX
672                "idiv{w} $src", []>, Imp<[AX,DX],[AX,DX]>, OpSize;
673 def IDIV32r: I<0xF7, MRM7r, (ops R32:$src),         // EDX:EAX/r32 = EAX,EDX
674                "idiv{l} $src", []>, Imp<[EAX,EDX],[EAX,EDX]>;
675 def IDIV8m : I<0xF6, MRM7m, (ops i8mem:$src),      // AX/[mem8] = AL,AH
676                "idiv{b} $src", []>, Imp<[AX],[AX]>;
677 def IDIV16m: I<0xF7, MRM7m, (ops i16mem:$src),     // DX:AX/[mem16] = AX,DX
678                "idiv{w} $src", []>, Imp<[AX,DX],[AX,DX]>, OpSize;
679 def IDIV32m: I<0xF7, MRM7m, (ops i32mem:$src),     // EDX:EAX/[mem32] = EAX,EDX
680                "idiv{l} $src", []>, Imp<[EAX,EDX],[EAX,EDX]>;
681
682 // Sign-extenders for division.
683 def CBW : I<0x98, RawFrm, (ops),
684             "{cbtw|cbw}", []>, Imp<[AL],[AH]>;   // AX = signext(AL)
685 def CWD : I<0x99, RawFrm, (ops),
686             "{cwtd|cwd}", []>, Imp<[AX],[DX]>;   // DX:AX = signext(AX)
687 def CDQ : I<0x99, RawFrm, (ops),
688             "{cltd|cdq}", []>, Imp<[EAX],[EDX]>; // EDX:EAX = signext(EAX)
689           
690
691 //===----------------------------------------------------------------------===//
692 //  Two address Instructions...
693 //
694 let isTwoAddress = 1 in {
695
696 // Conditional moves
697 def CMOVB16rr : I<0x42, MRMSrcReg,       // if <u, R16 = R16
698                   (ops R16:$dst, R16:$src1, R16:$src2),
699                   "cmovb {$src2, $dst|$dst, $src2}",
700                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
701                                    X86_COND_B))]>,
702                   TB, OpSize;
703 def CMOVB16rm : I<0x42, MRMSrcMem,       // if <u, R16 = [mem16]
704                   (ops R16:$dst, R16:$src1, i16mem:$src2),
705                   "cmovb {$src2, $dst|$dst, $src2}",
706                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
707                                    X86_COND_B))]>,
708                   TB, OpSize;
709 def CMOVB32rr : I<0x42, MRMSrcReg,       // if <u, R32 = R32
710                   (ops R32:$dst, R32:$src1, R32:$src2),
711                   "cmovb {$src2, $dst|$dst, $src2}",
712                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
713                                    X86_COND_B))]>,
714                    TB;
715 def CMOVB32rm : I<0x42, MRMSrcMem,       // if <u, R32 = [mem32]
716                   (ops R32:$dst, R32:$src1, i32mem:$src2),
717                   "cmovb {$src2, $dst|$dst, $src2}",
718                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
719                                    X86_COND_B))]>,
720                    TB;
721
722 def CMOVAE16rr: I<0x43, MRMSrcReg,       // if >=u, R16 = R16
723                   (ops R16:$dst, R16:$src1, R16:$src2),
724                   "cmovae {$src2, $dst|$dst, $src2}",
725                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
726                                    X86_COND_AE))]>,
727                    TB, OpSize;
728 def CMOVAE16rm: I<0x43, MRMSrcMem,       // if >=u, R16 = [mem16]
729                   (ops R16:$dst, R16:$src1, i16mem:$src2),
730                   "cmovae {$src2, $dst|$dst, $src2}",
731                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
732                                    X86_COND_AE))]>,
733                    TB, OpSize;
734 def CMOVAE32rr: I<0x43, MRMSrcReg,       // if >=u, R32 = R32
735                   (ops R32:$dst, R32:$src1, R32:$src2),
736                   "cmovae {$src2, $dst|$dst, $src2}",
737                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
738                                    X86_COND_AE))]>,
739                    TB;
740 def CMOVAE32rm: I<0x43, MRMSrcMem,       // if >=u, R32 = [mem32]
741                   (ops R32:$dst, R32:$src1, i32mem:$src2),
742                   "cmovae {$src2, $dst|$dst, $src2}",
743                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
744                                    X86_COND_AE))]>,
745                    TB;
746
747 def CMOVE16rr : I<0x44, MRMSrcReg,       // if ==, R16 = R16
748                   (ops R16:$dst, R16:$src1, R16:$src2),
749                   "cmove {$src2, $dst|$dst, $src2}",
750                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
751                                    X86_COND_E))]>,
752                    TB, OpSize;
753 def CMOVE16rm : I<0x44, MRMSrcMem,       // if ==, R16 = [mem16]
754                   (ops R16:$dst, R16:$src1, i16mem:$src2),
755                   "cmove {$src2, $dst|$dst, $src2}",
756                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
757                                    X86_COND_E))]>,
758                    TB, OpSize;
759 def CMOVE32rr : I<0x44, MRMSrcReg,       // if ==, R32 = R32
760                   (ops R32:$dst, R32:$src1, R32:$src2),
761                   "cmove {$src2, $dst|$dst, $src2}",
762                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
763                                    X86_COND_E))]>,
764                    TB;
765 def CMOVE32rm : I<0x44, MRMSrcMem,       // if ==, R32 = [mem32]
766                   (ops R32:$dst, R32:$src1, i32mem:$src2),
767                   "cmove {$src2, $dst|$dst, $src2}",
768                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
769                                    X86_COND_E))]>,
770                    TB;
771
772 def CMOVNE16rr: I<0x45, MRMSrcReg,       // if !=, R16 = R16
773                   (ops R16:$dst, R16:$src1, R16:$src2),
774                   "cmovne {$src2, $dst|$dst, $src2}",
775                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
776                                    X86_COND_NE))]>,
777                    TB, OpSize;
778 def CMOVNE16rm: I<0x45, MRMSrcMem,       // if !=, R16 = [mem16]
779                   (ops R16:$dst, R16:$src1, i16mem:$src2),
780                   "cmovne {$src2, $dst|$dst, $src2}",
781                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
782                                    X86_COND_NE))]>,
783                    TB, OpSize;
784 def CMOVNE32rr: I<0x45, MRMSrcReg,       // if !=, R32 = R32
785                   (ops R32:$dst, R32:$src1, R32:$src2),
786                   "cmovne {$src2, $dst|$dst, $src2}",
787                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
788                                    X86_COND_NE))]>,
789                    TB;
790 def CMOVNE32rm: I<0x45, MRMSrcMem,       // if !=, R32 = [mem32]
791                   (ops R32:$dst, R32:$src1, i32mem:$src2),
792                   "cmovne {$src2, $dst|$dst, $src2}",
793                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
794                                    X86_COND_NE))]>,
795                    TB;
796
797 def CMOVBE16rr: I<0x46, MRMSrcReg,       // if <=u, R16 = R16
798                   (ops R16:$dst, R16:$src1, R16:$src2),
799                   "cmovbe {$src2, $dst|$dst, $src2}",
800                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
801                                    X86_COND_BE))]>,
802                    TB, OpSize;
803 def CMOVBE16rm: I<0x46, MRMSrcMem,       // if <=u, R16 = [mem16]
804                   (ops R16:$dst, R16:$src1, i16mem:$src2),
805                   "cmovbe {$src2, $dst|$dst, $src2}",
806                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
807                                    X86_COND_BE))]>,
808                    TB, OpSize;
809 def CMOVBE32rr: I<0x46, MRMSrcReg,       // if <=u, R32 = R32
810                   (ops R32:$dst, R32:$src1, R32:$src2),
811                   "cmovbe {$src2, $dst|$dst, $src2}",
812                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
813                                    X86_COND_BE))]>,
814                    TB;
815 def CMOVBE32rm: I<0x46, MRMSrcMem,       // if <=u, R32 = [mem32]
816                   (ops R32:$dst, R32:$src1, i32mem:$src2),
817                   "cmovbe {$src2, $dst|$dst, $src2}",
818                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
819                                    X86_COND_BE))]>,
820                    TB;
821
822 def CMOVA16rr : I<0x47, MRMSrcReg,       // if >u, R16 = R16
823                   (ops R16:$dst, R16:$src1, R16:$src2),
824                   "cmova {$src2, $dst|$dst, $src2}",
825                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
826                                    X86_COND_A))]>,
827                    TB, OpSize;
828 def CMOVA16rm : I<0x47, MRMSrcMem,       // if >u, R16 = [mem16]
829                   (ops R16:$dst, R16:$src1, i16mem:$src2),
830                   "cmova {$src2, $dst|$dst, $src2}",
831                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
832                                    X86_COND_A))]>,
833                    TB, OpSize;
834 def CMOVA32rr : I<0x47, MRMSrcReg,       // if >u, R32 = R32
835                   (ops R32:$dst, R32:$src1, R32:$src2),
836                   "cmova {$src2, $dst|$dst, $src2}",
837                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
838                                    X86_COND_A))]>,
839                    TB;
840 def CMOVA32rm : I<0x47, MRMSrcMem,       // if >u, R32 = [mem32]
841                   (ops R32:$dst, R32:$src1, i32mem:$src2),
842                   "cmova {$src2, $dst|$dst, $src2}",
843                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
844                                    X86_COND_A))]>,
845                    TB;
846
847 def CMOVL16rr : I<0x4C, MRMSrcReg,       // if <s, R16 = R16
848                   (ops R16:$dst, R16:$src1, R16:$src2),
849                   "cmovl {$src2, $dst|$dst, $src2}",
850                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
851                                    X86_COND_L))]>,
852                    TB, OpSize;
853 def CMOVL16rm : I<0x4C, MRMSrcMem,       // if <s, R16 = [mem16]
854                   (ops R16:$dst, R16:$src1, i16mem:$src2),
855                   "cmovl {$src2, $dst|$dst, $src2}",
856                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
857                                    X86_COND_L))]>,
858                    TB, OpSize;
859 def CMOVL32rr : I<0x4C, MRMSrcReg,       // if <s, R32 = R32
860                   (ops R32:$dst, R32:$src1, R32:$src2),
861                   "cmovl {$src2, $dst|$dst, $src2}",
862                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
863                                    X86_COND_L))]>,
864                    TB;
865 def CMOVL32rm : I<0x4C, MRMSrcMem,       // if <s, R32 = [mem32]
866                   (ops R32:$dst, R32:$src1, i32mem:$src2),
867                   "cmovl {$src2, $dst|$dst, $src2}",
868                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
869                                    X86_COND_L))]>,
870                    TB;
871
872 def CMOVGE16rr: I<0x4D, MRMSrcReg,       // if >=s, R16 = R16
873                   (ops R16:$dst, R16:$src1, R16:$src2),
874                   "cmovge {$src2, $dst|$dst, $src2}",
875                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
876                                    X86_COND_GE))]>,
877                    TB, OpSize;
878 def CMOVGE16rm: I<0x4D, MRMSrcMem,       // if >=s, R16 = [mem16]
879                   (ops R16:$dst, R16:$src1, i16mem:$src2),
880                   "cmovge {$src2, $dst|$dst, $src2}",
881                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
882                                    X86_COND_GE))]>,
883                    TB, OpSize;
884 def CMOVGE32rr: I<0x4D, MRMSrcReg,       // if >=s, R32 = R32
885                   (ops R32:$dst, R32:$src1, R32:$src2),
886                   "cmovge {$src2, $dst|$dst, $src2}",
887                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
888                                    X86_COND_GE))]>,
889                    TB;
890 def CMOVGE32rm: I<0x4D, MRMSrcMem,       // if >=s, R32 = [mem32]
891                   (ops R32:$dst, R32:$src1, i32mem:$src2),
892                   "cmovge {$src2, $dst|$dst, $src2}",
893                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
894                                    X86_COND_GE))]>,
895                    TB;
896
897 def CMOVLE16rr: I<0x4E, MRMSrcReg,       // if <=s, R16 = R16
898                   (ops R16:$dst, R16:$src1, R16:$src2),
899                   "cmovle {$src2, $dst|$dst, $src2}",
900                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
901                                    X86_COND_LE))]>,
902                    TB, OpSize;
903 def CMOVLE16rm: I<0x4E, MRMSrcMem,       // if <=s, R16 = [mem16]
904                   (ops R16:$dst, R16:$src1, i16mem:$src2),
905                   "cmovle {$src2, $dst|$dst, $src2}",
906                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
907                                    X86_COND_LE))]>,
908                    TB, OpSize;
909 def CMOVLE32rr: I<0x4E, MRMSrcReg,       // if <=s, R32 = R32
910                   (ops R32:$dst, R32:$src1, R32:$src2),
911                   "cmovle {$src2, $dst|$dst, $src2}",
912                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
913                                    X86_COND_LE))]>,
914                    TB;
915 def CMOVLE32rm: I<0x4E, MRMSrcMem,       // if <=s, R32 = [mem32]
916                   (ops R32:$dst, R32:$src1, i32mem:$src2),
917                   "cmovle {$src2, $dst|$dst, $src2}",
918                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
919                                    X86_COND_LE))]>,
920                    TB;
921
922 def CMOVG16rr : I<0x4F, MRMSrcReg,       // if >s, R16 = R16
923                   (ops R16:$dst, R16:$src1, R16:$src2),
924                   "cmovg {$src2, $dst|$dst, $src2}",
925                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
926                                    X86_COND_G))]>,
927                    TB, OpSize;
928 def CMOVG16rm : I<0x4F, MRMSrcMem,       // if >s, R16 = [mem16]
929                   (ops R16:$dst, R16:$src1, i16mem:$src2),
930                   "cmovg {$src2, $dst|$dst, $src2}",
931                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
932                                    X86_COND_G))]>,
933                    TB, OpSize;
934 def CMOVG32rr : I<0x4F, MRMSrcReg,       // if >s, R32 = R32
935                   (ops R32:$dst, R32:$src1, R32:$src2),
936                   "cmovg {$src2, $dst|$dst, $src2}",
937                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
938                                    X86_COND_G))]>,
939                    TB;
940 def CMOVG32rm : I<0x4F, MRMSrcMem,       // if >s, R32 = [mem32]
941                   (ops R32:$dst, R32:$src1, i32mem:$src2),
942                   "cmovg {$src2, $dst|$dst, $src2}",
943                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
944                                    X86_COND_G))]>,
945                    TB;
946
947 def CMOVS16rr : I<0x48, MRMSrcReg,       // if signed, R16 = R16
948                   (ops R16:$dst, R16:$src1, R16:$src2),
949                   "cmovs {$src2, $dst|$dst, $src2}",
950                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
951                                    X86_COND_S))]>,
952                   TB, OpSize;
953 def CMOVS16rm : I<0x48, MRMSrcMem,       // if signed, R16 = [mem16]
954                   (ops R16:$dst, R16:$src1, i16mem:$src2),
955                   "cmovs {$src2, $dst|$dst, $src2}",
956                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
957                                    X86_COND_S))]>,
958                   TB, OpSize;
959 def CMOVS32rr : I<0x48, MRMSrcReg,       // if signed, R32 = R32
960                   (ops R32:$dst, R32:$src1, R32:$src2),
961                   "cmovs {$src2, $dst|$dst, $src2}",
962                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
963                                    X86_COND_S))]>,
964                   TB;
965 def CMOVS32rm : I<0x48, MRMSrcMem,       // if signed, R32 = [mem32]
966                   (ops R32:$dst, R32:$src1, i32mem:$src2),
967                   "cmovs {$src2, $dst|$dst, $src2}",
968                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
969                                    X86_COND_S))]>,
970                   TB;
971
972 def CMOVNS16rr: I<0x49, MRMSrcReg,       // if !signed, R16 = R16
973                   (ops R16:$dst, R16:$src1, R16:$src2),
974                   "cmovns {$src2, $dst|$dst, $src2}",
975                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
976                                    X86_COND_NS))]>,
977                   TB, OpSize;
978 def CMOVNS16rm: I<0x49, MRMSrcMem,       // if !signed, R16 = [mem16]
979                   (ops R16:$dst, R16:$src1, i16mem:$src2),
980                   "cmovns {$src2, $dst|$dst, $src2}",
981                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
982                                    X86_COND_NS))]>,
983                   TB, OpSize;
984 def CMOVNS32rr: I<0x49, MRMSrcReg,       // if !signed, R32 = R32
985                   (ops R32:$dst, R32:$src1, R32:$src2),
986                   "cmovns {$src2, $dst|$dst, $src2}",
987                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
988                                    X86_COND_NS))]>,
989                   TB;
990 def CMOVNS32rm: I<0x49, MRMSrcMem,       // if !signed, R32 = [mem32]
991                   (ops R32:$dst, R32:$src1, i32mem:$src2),
992                   "cmovns {$src2, $dst|$dst, $src2}",
993                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
994                                    X86_COND_NS))]>,
995                   TB;
996
997 def CMOVP16rr : I<0x4A, MRMSrcReg,       // if parity, R16 = R16
998                   (ops R16:$dst, R16:$src1, R16:$src2),
999                   "cmovp {$src2, $dst|$dst, $src2}",
1000                   [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
1001                                    X86_COND_P))]>,
1002                   TB, OpSize;
1003 def CMOVP16rm : I<0x4A, MRMSrcMem,       // if parity, R16 = [mem16]
1004                   (ops R16:$dst, R16:$src1, i16mem:$src2),
1005                   "cmovp {$src2, $dst|$dst, $src2}",
1006                   [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
1007                                    X86_COND_P))]>,
1008                   TB, OpSize;
1009 def CMOVP32rr : I<0x4A, MRMSrcReg,       // if parity, R32 = R32
1010                   (ops R32:$dst, R32:$src1, R32:$src2),
1011                   "cmovp {$src2, $dst|$dst, $src2}",
1012                   [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
1013                                    X86_COND_P))]>,
1014                   TB;
1015 def CMOVP32rm : I<0x4A, MRMSrcMem,       // if parity, R32 = [mem32]
1016                   (ops R32:$dst, R32:$src1, i32mem:$src2),
1017                   "cmovp {$src2, $dst|$dst, $src2}",
1018                   [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
1019                                    X86_COND_P))]>,
1020                   TB;
1021
1022 def CMOVNP16rr : I<0x4B, MRMSrcReg,       // if !parity, R16 = R16
1023                   (ops R16:$dst, R16:$src1, R16:$src2),
1024                   "cmovnp {$src2, $dst|$dst, $src2}",
1025                    [(set R16:$dst, (X86cmov R16:$src1, R16:$src2,
1026                                     X86_COND_NP))]>,
1027                   TB, OpSize;
1028 def CMOVNP16rm : I<0x4B, MRMSrcMem,       // if !parity, R16 = [mem16]
1029                   (ops R16:$dst, R16:$src1, i16mem:$src2),
1030                   "cmovnp {$src2, $dst|$dst, $src2}",
1031                    [(set R16:$dst, (X86cmov R16:$src1, (loadi16 addr:$src2),
1032                                     X86_COND_NP))]>,
1033                   TB, OpSize;
1034 def CMOVNP32rr : I<0x4B, MRMSrcReg,       // if !parity, R32 = R32
1035                   (ops R32:$dst, R32:$src1, R32:$src2),
1036                   "cmovnp {$src2, $dst|$dst, $src2}",
1037                    [(set R32:$dst, (X86cmov R32:$src1, R32:$src2,
1038                                     X86_COND_NP))]>,
1039                   TB;
1040 def CMOVNP32rm : I<0x4B, MRMSrcMem,       // if !parity, R32 = [mem32]
1041                   (ops R32:$dst, R32:$src1, i32mem:$src2),
1042                   "cmovnp {$src2, $dst|$dst, $src2}",
1043                    [(set R32:$dst, (X86cmov R32:$src1, (loadi32 addr:$src2),
1044                                     X86_COND_NP))]>,
1045                   TB;
1046
1047
1048 // unary instructions
1049 def NEG8r  : I<0xF6, MRM3r, (ops R8 :$dst, R8 :$src), "neg{b} $dst",
1050                [(set R8:$dst, (ineg R8:$src))]>;
1051 def NEG16r : I<0xF7, MRM3r, (ops R16:$dst, R16:$src), "neg{w} $dst",
1052                [(set R16:$dst, (ineg R16:$src))]>, OpSize;
1053 def NEG32r : I<0xF7, MRM3r, (ops R32:$dst, R32:$src), "neg{l} $dst",
1054                [(set R32:$dst, (ineg R32:$src))]>;
1055 let isTwoAddress = 0 in {
1056   def NEG8m  : I<0xF6, MRM3m, (ops i8mem :$dst), "neg{b} $dst",
1057                  [(store (ineg (loadi8 addr:$dst)), addr:$dst)]>;
1058   def NEG16m : I<0xF7, MRM3m, (ops i16mem:$dst), "neg{w} $dst",
1059                  [(store (ineg (loadi16 addr:$dst)), addr:$dst)]>, OpSize;
1060   def NEG32m : I<0xF7, MRM3m, (ops i32mem:$dst), "neg{l} $dst",
1061                  [(store (ineg (loadi32 addr:$dst)), addr:$dst)]>;
1062
1063 }
1064
1065 def NOT8r  : I<0xF6, MRM2r, (ops R8 :$dst, R8 :$src), "not{b} $dst",
1066                [(set R8:$dst, (not R8:$src))]>;
1067 def NOT16r : I<0xF7, MRM2r, (ops R16:$dst, R16:$src), "not{w} $dst",
1068                [(set R16:$dst, (not R16:$src))]>, OpSize;
1069 def NOT32r : I<0xF7, MRM2r, (ops R32:$dst, R32:$src), "not{l} $dst",
1070                [(set R32:$dst, (not R32:$src))]>;
1071 let isTwoAddress = 0 in {
1072   def NOT8m  : I<0xF6, MRM2m, (ops i8mem :$dst), "not{b} $dst",
1073                  [(store (not (loadi8 addr:$dst)), addr:$dst)]>;
1074   def NOT16m : I<0xF7, MRM2m, (ops i16mem:$dst), "not{w} $dst",
1075                  [(store (not (loadi16 addr:$dst)), addr:$dst)]>, OpSize;
1076   def NOT32m : I<0xF7, MRM2m, (ops i32mem:$dst), "not{l} $dst",
1077                  [(store (not (loadi32 addr:$dst)), addr:$dst)]>;
1078 }
1079
1080 // TODO: inc/dec is slow for P4, but fast for Pentium-M.
1081 def INC8r  : I<0xFE, MRM0r, (ops R8 :$dst, R8 :$src), "inc{b} $dst",
1082                [(set R8:$dst, (add R8:$src, 1))]>;
1083 let isConvertibleToThreeAddress = 1 in {   // Can transform into LEA.
1084 def INC16r : I<0xFF, MRM0r, (ops R16:$dst, R16:$src), "inc{w} $dst",
1085                [(set R16:$dst, (add R16:$src, 1))]>, OpSize;
1086 def INC32r : I<0xFF, MRM0r, (ops R32:$dst, R32:$src), "inc{l} $dst",
1087                [(set R32:$dst, (add R32:$src, 1))]>;
1088 }
1089 let isTwoAddress = 0 in {
1090   def INC8m  : I<0xFE, MRM0m, (ops i8mem :$dst), "inc{b} $dst",
1091                [(store (add (loadi8 addr:$dst), 1), addr:$dst)]>;
1092   def INC16m : I<0xFF, MRM0m, (ops i16mem:$dst), "inc{w} $dst",
1093                [(store (add (loadi16 addr:$dst), 1), addr:$dst)]>, OpSize;
1094   def INC32m : I<0xFF, MRM0m, (ops i32mem:$dst), "inc{l} $dst",
1095                [(store (add (loadi32 addr:$dst), 1), addr:$dst)]>;
1096 }
1097
1098 def DEC8r  : I<0xFE, MRM1r, (ops R8 :$dst, R8 :$src), "dec{b} $dst",
1099                [(set R8:$dst, (add R8:$src, -1))]>;
1100 let isConvertibleToThreeAddress = 1 in {   // Can transform into LEA.
1101 def DEC16r : I<0xFF, MRM1r, (ops R16:$dst, R16:$src), "dec{w} $dst",
1102                [(set R16:$dst, (add R16:$src, -1))]>, OpSize;
1103 def DEC32r : I<0xFF, MRM1r, (ops R32:$dst, R32:$src), "dec{l} $dst",
1104                [(set R32:$dst, (add R32:$src, -1))]>;
1105 }
1106
1107 let isTwoAddress = 0 in {
1108   def DEC8m  : I<0xFE, MRM1m, (ops i8mem :$dst), "dec{b} $dst",
1109                [(store (add (loadi8 addr:$dst), -1), addr:$dst)]>;
1110   def DEC16m : I<0xFF, MRM1m, (ops i16mem:$dst), "dec{w} $dst",
1111                [(store (add (loadi16 addr:$dst), -1), addr:$dst)]>, OpSize;
1112   def DEC32m : I<0xFF, MRM1m, (ops i32mem:$dst), "dec{l} $dst",
1113                [(store (add (loadi32 addr:$dst), -1), addr:$dst)]>;
1114 }
1115
1116 // Logical operators...
1117 let isCommutable = 1 in {   // X = AND Y, Z   --> X = AND Z, Y
1118 def AND8rr   : I<0x20, MRMDestReg,
1119                 (ops R8 :$dst, R8 :$src1, R8 :$src2),
1120                 "and{b} {$src2, $dst|$dst, $src2}",
1121                 [(set R8:$dst, (and R8:$src1, R8:$src2))]>;
1122 def AND16rr  : I<0x21, MRMDestReg,
1123                  (ops R16:$dst, R16:$src1, R16:$src2),
1124                  "and{w} {$src2, $dst|$dst, $src2}",
1125                  [(set R16:$dst, (and R16:$src1, R16:$src2))]>, OpSize;
1126 def AND32rr  : I<0x21, MRMDestReg, 
1127                  (ops R32:$dst, R32:$src1, R32:$src2),
1128                  "and{l} {$src2, $dst|$dst, $src2}",
1129                  [(set R32:$dst, (and R32:$src1, R32:$src2))]>;
1130 }
1131
1132 def AND8rm   : I<0x22, MRMSrcMem, 
1133                  (ops R8 :$dst, R8 :$src1, i8mem :$src2),
1134                  "and{b} {$src2, $dst|$dst, $src2}",
1135                 [(set R8:$dst, (and R8:$src1, (load addr:$src2)))]>;
1136 def AND16rm  : I<0x23, MRMSrcMem, 
1137                  (ops R16:$dst, R16:$src1, i16mem:$src2),
1138                  "and{w} {$src2, $dst|$dst, $src2}",
1139                 [(set R16:$dst, (and R16:$src1, (load addr:$src2)))]>, OpSize;
1140 def AND32rm  : I<0x23, MRMSrcMem,
1141                  (ops R32:$dst, R32:$src1, i32mem:$src2),
1142                  "and{l} {$src2, $dst|$dst, $src2}",
1143                 [(set R32:$dst, (and R32:$src1, (load addr:$src2)))]>;
1144
1145 def AND8ri   : Ii8<0x80, MRM4r, 
1146                    (ops R8 :$dst, R8 :$src1, i8imm :$src2),
1147                    "and{b} {$src2, $dst|$dst, $src2}",
1148                    [(set R8:$dst, (and R8:$src1, imm:$src2))]>;
1149 def AND16ri  : Ii16<0x81, MRM4r, 
1150                     (ops R16:$dst, R16:$src1, i16imm:$src2),
1151                     "and{w} {$src2, $dst|$dst, $src2}",
1152                     [(set R16:$dst, (and R16:$src1, imm:$src2))]>, OpSize;
1153 def AND32ri  : Ii32<0x81, MRM4r, 
1154                     (ops R32:$dst, R32:$src1, i32imm:$src2),
1155                     "and{l} {$src2, $dst|$dst, $src2}",
1156                     [(set R32:$dst, (and R32:$src1, imm:$src2))]>;
1157 def AND16ri8 : Ii8<0x83, MRM4r, 
1158                    (ops R16:$dst, R16:$src1, i16i8imm:$src2),
1159                    "and{w} {$src2, $dst|$dst, $src2}",
1160                    [(set R16:$dst, (and R16:$src1, i16immSExt8:$src2))]>,
1161                    OpSize;
1162 def AND32ri8 : Ii8<0x83, MRM4r, 
1163                    (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1164                    "and{l} {$src2, $dst|$dst, $src2}",
1165                    [(set R32:$dst, (and R32:$src1, i32immSExt8:$src2))]>;
1166
1167 let isTwoAddress = 0 in {
1168   def AND8mr   : I<0x20, MRMDestMem,
1169                    (ops i8mem :$dst, R8 :$src),
1170                    "and{b} {$src, $dst|$dst, $src}",
1171                    [(store (and (load addr:$dst), R8:$src), addr:$dst)]>;
1172   def AND16mr  : I<0x21, MRMDestMem,
1173                    (ops i16mem:$dst, R16:$src),
1174                    "and{w} {$src, $dst|$dst, $src}",
1175                    [(store (and (load addr:$dst), R16:$src), addr:$dst)]>,
1176                    OpSize;
1177   def AND32mr  : I<0x21, MRMDestMem,
1178                    (ops i32mem:$dst, R32:$src),
1179                    "and{l} {$src, $dst|$dst, $src}",
1180                    [(store (and (load addr:$dst), R32:$src), addr:$dst)]>;
1181   def AND8mi   : Ii8<0x80, MRM4m,
1182                      (ops i8mem :$dst, i8imm :$src),
1183                      "and{b} {$src, $dst|$dst, $src}",
1184                       [(store (and (loadi8 addr:$dst), imm:$src), addr:$dst)]>;
1185   def AND16mi  : Ii16<0x81, MRM4m,
1186                       (ops i16mem:$dst, i16imm:$src),
1187                       "and{w} {$src, $dst|$dst, $src}",
1188                       [(store (and (loadi16 addr:$dst), imm:$src), addr:$dst)]>,
1189                       OpSize;
1190   def AND32mi  : Ii32<0x81, MRM4m,
1191                       (ops i32mem:$dst, i32imm:$src),
1192                       "and{l} {$src, $dst|$dst, $src}",
1193                       [(store (and (loadi32 addr:$dst), imm:$src), addr:$dst)]>;
1194   def AND16mi8 : Ii8<0x83, MRM4m,
1195                      (ops i16mem:$dst, i16i8imm :$src),
1196                      "and{w} {$src, $dst|$dst, $src}",
1197                 [(store (and (load addr:$dst), i16immSExt8:$src), addr:$dst)]>,
1198                      OpSize;
1199   def AND32mi8 : Ii8<0x83, MRM4m,
1200                      (ops i32mem:$dst, i32i8imm :$src),
1201                      "and{l} {$src, $dst|$dst, $src}",
1202                 [(store (and (load addr:$dst), i32immSExt8:$src), addr:$dst)]>;
1203 }
1204
1205
1206 let isCommutable = 1 in {   // X = OR Y, Z   --> X = OR Z, Y
1207 def OR8rr    : I<0x08, MRMDestReg, (ops R8 :$dst, R8 :$src1, R8 :$src2),
1208                  "or{b} {$src2, $dst|$dst, $src2}",
1209                  [(set R8:$dst, (or R8:$src1, R8:$src2))]>;
1210 def OR16rr   : I<0x09, MRMDestReg, (ops R16:$dst, R16:$src1, R16:$src2),
1211                  "or{w} {$src2, $dst|$dst, $src2}",
1212                  [(set R16:$dst, (or R16:$src1, R16:$src2))]>, OpSize;
1213 def OR32rr   : I<0x09, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1214                  "or{l} {$src2, $dst|$dst, $src2}",
1215                  [(set R32:$dst, (or R32:$src1, R32:$src2))]>;
1216 }
1217 def OR8rm    : I<0x0A, MRMSrcMem , (ops R8 :$dst, R8 :$src1, i8mem :$src2),
1218                  "or{b} {$src2, $dst|$dst, $src2}",
1219                 [(set R8:$dst, (or R8:$src1, (load addr:$src2)))]>;
1220 def OR16rm   : I<0x0B, MRMSrcMem , (ops R16:$dst, R16:$src1, i16mem:$src2),
1221                  "or{w} {$src2, $dst|$dst, $src2}",
1222                 [(set R16:$dst, (or R16:$src1, (load addr:$src2)))]>, OpSize;
1223 def OR32rm   : I<0x0B, MRMSrcMem , (ops R32:$dst, R32:$src1, i32mem:$src2),
1224                  "or{l} {$src2, $dst|$dst, $src2}",
1225                 [(set R32:$dst, (or R32:$src1, (load addr:$src2)))]>;
1226
1227 def OR8ri    : Ii8 <0x80, MRM1r, (ops R8 :$dst, R8 :$src1, i8imm:$src2),
1228                     "or{b} {$src2, $dst|$dst, $src2}",
1229                     [(set R8:$dst, (or R8:$src1, imm:$src2))]>;
1230 def OR16ri   : Ii16<0x81, MRM1r, (ops R16:$dst, R16:$src1, i16imm:$src2),
1231                     "or{w} {$src2, $dst|$dst, $src2}", 
1232                     [(set R16:$dst, (or R16:$src1, imm:$src2))]>, OpSize;
1233 def OR32ri   : Ii32<0x81, MRM1r, (ops R32:$dst, R32:$src1, i32imm:$src2),
1234                     "or{l} {$src2, $dst|$dst, $src2}",
1235                     [(set R32:$dst, (or R32:$src1, imm:$src2))]>;
1236
1237 def OR16ri8  : Ii8<0x83, MRM1r, (ops R16:$dst, R16:$src1, i16i8imm:$src2),
1238                    "or{w} {$src2, $dst|$dst, $src2}",
1239                    [(set R16:$dst, (or R16:$src1, i16immSExt8:$src2))]>, OpSize;
1240 def OR32ri8  : Ii8<0x83, MRM1r, (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1241                    "or{l} {$src2, $dst|$dst, $src2}",
1242                    [(set R32:$dst, (or R32:$src1, i32immSExt8:$src2))]>;
1243 let isTwoAddress = 0 in {
1244   def OR8mr  : I<0x08, MRMDestMem, (ops i8mem:$dst, R8:$src),
1245                  "or{b} {$src, $dst|$dst, $src}",
1246                  [(store (or (load addr:$dst), R8:$src), addr:$dst)]>;
1247   def OR16mr : I<0x09, MRMDestMem, (ops i16mem:$dst, R16:$src),
1248                  "or{w} {$src, $dst|$dst, $src}",
1249                  [(store (or (load addr:$dst), R16:$src), addr:$dst)]>, OpSize;
1250   def OR32mr : I<0x09, MRMDestMem, (ops i32mem:$dst, R32:$src),
1251                  "or{l} {$src, $dst|$dst, $src}",
1252                  [(store (or (load addr:$dst), R32:$src), addr:$dst)]>;
1253   def OR8mi    : Ii8<0x80, MRM1m, (ops i8mem :$dst, i8imm:$src),
1254                  "or{b} {$src, $dst|$dst, $src}",
1255                  [(store (or (loadi8 addr:$dst), imm:$src), addr:$dst)]>;
1256   def OR16mi   : Ii16<0x81, MRM1m, (ops i16mem:$dst, i16imm:$src),
1257                  "or{w} {$src, $dst|$dst, $src}",
1258                  [(store (or (loadi16 addr:$dst), imm:$src), addr:$dst)]>,
1259                  OpSize;
1260   def OR32mi   : Ii32<0x81, MRM1m, (ops i32mem:$dst, i32imm:$src),
1261                  "or{l} {$src, $dst|$dst, $src}",
1262                  [(store (or (loadi32 addr:$dst), imm:$src), addr:$dst)]>;
1263   def OR16mi8  : Ii8<0x83, MRM1m, (ops i16mem:$dst, i16i8imm:$src),
1264                  "or{w} {$src, $dst|$dst, $src}",
1265                  [(store (or (load addr:$dst), i16immSExt8:$src), addr:$dst)]>,
1266                      OpSize;
1267   def OR32mi8  : Ii8<0x83, MRM1m, (ops i32mem:$dst, i32i8imm:$src),
1268                  "or{l} {$src, $dst|$dst, $src}",
1269                  [(store (or (load addr:$dst), i32immSExt8:$src), addr:$dst)]>;
1270 }
1271
1272
1273 let isCommutable = 1 in {   // X = XOR Y, Z   --> X = XOR Z, Y
1274 def XOR8rr   : I<0x30, MRMDestReg,
1275                  (ops R8 :$dst, R8 :$src1, R8 :$src2),
1276                  "xor{b} {$src2, $dst|$dst, $src2}",
1277                  [(set R8:$dst, (xor R8:$src1, R8:$src2))]>;
1278 def XOR16rr  : I<0x31, MRMDestReg, 
1279                  (ops R16:$dst, R16:$src1, R16:$src2), 
1280                  "xor{w} {$src2, $dst|$dst, $src2}",
1281                  [(set R16:$dst, (xor R16:$src1, R16:$src2))]>, OpSize;
1282 def XOR32rr  : I<0x31, MRMDestReg, 
1283                  (ops R32:$dst, R32:$src1, R32:$src2), 
1284                  "xor{l} {$src2, $dst|$dst, $src2}",
1285                  [(set R32:$dst, (xor R32:$src1, R32:$src2))]>;
1286 }
1287
1288 def XOR8rm   : I<0x32, MRMSrcMem , 
1289                  (ops R8 :$dst, R8:$src1, i8mem :$src2), 
1290                  "xor{b} {$src2, $dst|$dst, $src2}",
1291                  [(set R8:$dst, (xor R8:$src1, (load addr:$src2)))]>;
1292 def XOR16rm  : I<0x33, MRMSrcMem , 
1293                  (ops R16:$dst, R16:$src1, i16mem:$src2), 
1294                  "xor{w} {$src2, $dst|$dst, $src2}",
1295                  [(set R16:$dst, (xor R16:$src1, (load addr:$src2)))]>, OpSize;
1296 def XOR32rm  : I<0x33, MRMSrcMem , 
1297                  (ops R32:$dst, R32:$src1, i32mem:$src2), 
1298                  "xor{l} {$src2, $dst|$dst, $src2}",
1299                  [(set R32:$dst, (xor R32:$src1, (load addr:$src2)))]>;
1300
1301 def XOR8ri   : Ii8<0x80, MRM6r, 
1302                    (ops R8:$dst, R8:$src1, i8imm:$src2), 
1303                    "xor{b} {$src2, $dst|$dst, $src2}",
1304                    [(set R8:$dst, (xor R8:$src1, imm:$src2))]>;
1305 def XOR16ri  : Ii16<0x81, MRM6r, 
1306                     (ops R16:$dst, R16:$src1, i16imm:$src2), 
1307                     "xor{w} {$src2, $dst|$dst, $src2}",
1308                     [(set R16:$dst, (xor R16:$src1, imm:$src2))]>, OpSize;
1309 def XOR32ri  : Ii32<0x81, MRM6r, 
1310                     (ops R32:$dst, R32:$src1, i32imm:$src2), 
1311                     "xor{l} {$src2, $dst|$dst, $src2}",
1312                     [(set R32:$dst, (xor R32:$src1, imm:$src2))]>;
1313 def XOR16ri8 : Ii8<0x83, MRM6r, 
1314                    (ops R16:$dst, R16:$src1, i16i8imm:$src2),
1315                    "xor{w} {$src2, $dst|$dst, $src2}",
1316                    [(set R16:$dst, (xor R16:$src1, i16immSExt8:$src2))]>,
1317                    OpSize;
1318 def XOR32ri8 : Ii8<0x83, MRM6r, 
1319                    (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1320                    "xor{l} {$src2, $dst|$dst, $src2}",
1321                    [(set R32:$dst, (xor R32:$src1, i32immSExt8:$src2))]>;
1322 let isTwoAddress = 0 in {
1323   def XOR8mr   : I<0x30, MRMDestMem,
1324                    (ops i8mem :$dst, R8 :$src),
1325                    "xor{b} {$src, $dst|$dst, $src}",
1326                    [(store (xor (load addr:$dst), R8:$src), addr:$dst)]>;
1327   def XOR16mr  : I<0x31, MRMDestMem,
1328                    (ops i16mem:$dst, R16:$src),
1329                    "xor{w} {$src, $dst|$dst, $src}",
1330                    [(store (xor (load addr:$dst), R16:$src), addr:$dst)]>,
1331                    OpSize;
1332   def XOR32mr  : I<0x31, MRMDestMem,
1333                    (ops i32mem:$dst, R32:$src),
1334                    "xor{l} {$src, $dst|$dst, $src}",
1335                    [(store (xor (load addr:$dst), R32:$src), addr:$dst)]>;
1336   def XOR8mi   : Ii8<0x80, MRM6m,
1337                      (ops i8mem :$dst, i8imm :$src),
1338                      "xor{b} {$src, $dst|$dst, $src}",
1339                     [(store (xor (loadi8 addr:$dst), imm:$src), addr:$dst)]>;
1340   def XOR16mi  : Ii16<0x81, MRM6m,
1341                       (ops i16mem:$dst, i16imm:$src),
1342                       "xor{w} {$src, $dst|$dst, $src}",
1343                    [(store (xor (loadi16 addr:$dst), imm:$src), addr:$dst)]>,
1344                       OpSize;
1345   def XOR32mi  : Ii32<0x81, MRM6m,
1346                       (ops i32mem:$dst, i32imm:$src),
1347                       "xor{l} {$src, $dst|$dst, $src}",
1348                    [(store (xor (loadi32 addr:$dst), imm:$src), addr:$dst)]>;
1349   def XOR16mi8 : Ii8<0x83, MRM6m,
1350                      (ops i16mem:$dst, i16i8imm :$src),
1351                      "xor{w} {$src, $dst|$dst, $src}",
1352                  [(store (xor (load addr:$dst), i16immSExt8:$src), addr:$dst)]>,
1353                      OpSize;
1354   def XOR32mi8 : Ii8<0x83, MRM6m,
1355                      (ops i32mem:$dst, i32i8imm :$src),
1356                      "xor{l} {$src, $dst|$dst, $src}",
1357                  [(store (xor (load addr:$dst), i32immSExt8:$src), addr:$dst)]>;
1358 }
1359
1360 // Shift instructions
1361 def SHL8rCL  : I<0xD2, MRM4r, (ops R8 :$dst, R8 :$src),
1362                  "shl{b} {%cl, $dst|$dst, %CL}",
1363                  [(set R8:$dst, (shl R8:$src, CL))]>, Imp<[CL],[]>;
1364 def SHL16rCL : I<0xD3, MRM4r, (ops R16:$dst, R16:$src),
1365                  "shl{w} {%cl, $dst|$dst, %CL}",
1366                  [(set R16:$dst, (shl R16:$src, CL))]>, Imp<[CL],[]>, OpSize;
1367 def SHL32rCL : I<0xD3, MRM4r, (ops R32:$dst, R32:$src),
1368                  "shl{l} {%cl, $dst|$dst, %CL}",
1369                  [(set R32:$dst, (shl R32:$src, CL))]>, Imp<[CL],[]>;
1370
1371 def SHL8ri   : Ii8<0xC0, MRM4r, (ops R8 :$dst, R8 :$src1, i8imm:$src2),
1372                    "shl{b} {$src2, $dst|$dst, $src2}",
1373                    [(set R8:$dst, (shl R8:$src1, (i8 imm:$src2)))]>;
1374 let isConvertibleToThreeAddress = 1 in {   // Can transform into LEA.
1375 def SHL16ri  : Ii8<0xC1, MRM4r, (ops R16:$dst, R16:$src1, i8imm:$src2),
1376                    "shl{w} {$src2, $dst|$dst, $src2}",
1377                    [(set R16:$dst, (shl R16:$src1, (i8 imm:$src2)))]>, OpSize;
1378 def SHL32ri  : Ii8<0xC1, MRM4r, (ops R32:$dst, R32:$src1, i8imm:$src2),
1379                    "shl{l} {$src2, $dst|$dst, $src2}",
1380                    [(set R32:$dst, (shl R32:$src1, (i8 imm:$src2)))]>;
1381 }
1382
1383 let isTwoAddress = 0 in {
1384   def SHL8mCL  : I<0xD2, MRM4m, (ops i8mem :$dst),
1385                    "shl{b} {%cl, $dst|$dst, %CL}",
1386                    [(store (shl (loadi8 addr:$dst), CL), addr:$dst)]>,
1387                    Imp<[CL],[]>;
1388   def SHL16mCL : I<0xD3, MRM4m, (ops i16mem:$dst),
1389                    "shl{w} {%cl, $dst|$dst, %CL}",
1390                    [(store (shl (loadi16 addr:$dst), CL), addr:$dst)]>,
1391                    Imp<[CL],[]>, OpSize;
1392   def SHL32mCL : I<0xD3, MRM4m, (ops i32mem:$dst),
1393                    "shl{l} {%cl, $dst|$dst, %CL}",
1394                    [(store (shl (loadi32 addr:$dst), CL), addr:$dst)]>,
1395                    Imp<[CL],[]>;
1396   def SHL8mi   : Ii8<0xC0, MRM4m, (ops i8mem :$dst, i8imm:$src),
1397                      "shl{b} {$src, $dst|$dst, $src}",
1398                   [(store (shl (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1399   def SHL16mi  : Ii8<0xC1, MRM4m, (ops i16mem:$dst, i8imm:$src),
1400                      "shl{w} {$src, $dst|$dst, $src}",
1401                  [(store (shl (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>,
1402                      OpSize;
1403   def SHL32mi  : Ii8<0xC1, MRM4m, (ops i32mem:$dst, i8imm:$src),
1404                      "shl{l} {$src, $dst|$dst, $src}",
1405                  [(store (shl (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1406 }
1407
1408 def SHR8rCL  : I<0xD2, MRM5r, (ops R8 :$dst, R8 :$src),
1409                  "shr{b} {%cl, $dst|$dst, %CL}",
1410                  [(set R8:$dst, (srl R8:$src, CL))]>, Imp<[CL],[]>;
1411 def SHR16rCL : I<0xD3, MRM5r, (ops R16:$dst, R16:$src),
1412                  "shr{w} {%cl, $dst|$dst, %CL}",
1413                  [(set R16:$dst, (srl R16:$src, CL))]>, Imp<[CL],[]>, OpSize;
1414 def SHR32rCL : I<0xD3, MRM5r, (ops R32:$dst, R32:$src),
1415                  "shr{l} {%cl, $dst|$dst, %CL}",
1416                  [(set R32:$dst, (srl R32:$src, CL))]>, Imp<[CL],[]>;
1417
1418 def SHR8ri   : Ii8<0xC0, MRM5r, (ops R8:$dst, R8:$src1, i8imm:$src2),
1419                    "shr{b} {$src2, $dst|$dst, $src2}",
1420                    [(set R8:$dst, (srl R8:$src1, (i8 imm:$src2)))]>;
1421 def SHR16ri  : Ii8<0xC1, MRM5r, (ops R16:$dst, R16:$src1, i8imm:$src2),
1422                    "shr{w} {$src2, $dst|$dst, $src2}",
1423                    [(set R16:$dst, (srl R16:$src1, (i8 imm:$src2)))]>, OpSize;
1424 def SHR32ri  : Ii8<0xC1, MRM5r, (ops R32:$dst, R32:$src1, i8imm:$src2),
1425                    "shr{l} {$src2, $dst|$dst, $src2}",
1426                    [(set R32:$dst, (srl R32:$src1, (i8 imm:$src2)))]>;
1427
1428 let isTwoAddress = 0 in {
1429   def SHR8mCL  : I<0xD2, MRM5m, (ops i8mem :$dst),
1430                    "shr{b} {%cl, $dst|$dst, %CL}",
1431                    [(store (srl (loadi8 addr:$dst), CL), addr:$dst)]>,
1432                    Imp<[CL],[]>;
1433   def SHR16mCL : I<0xD3, MRM5m, (ops i16mem:$dst),
1434                    "shr{w} {%cl, $dst|$dst, %CL}",
1435                    [(store (srl (loadi16 addr:$dst), CL), addr:$dst)]>,
1436                    Imp<[CL],[]>, OpSize;
1437   def SHR32mCL : I<0xD3, MRM5m, (ops i32mem:$dst),
1438                    "shr{l} {%cl, $dst|$dst, %CL}",
1439                    [(store (srl (loadi32 addr:$dst), CL), addr:$dst)]>,
1440                    Imp<[CL],[]>;
1441   def SHR8mi   : Ii8<0xC0, MRM5m, (ops i8mem :$dst, i8imm:$src),
1442                      "shr{b} {$src, $dst|$dst, $src}",
1443                   [(store (srl (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1444   def SHR16mi  : Ii8<0xC1, MRM5m, (ops i16mem:$dst, i8imm:$src),
1445                      "shr{w} {$src, $dst|$dst, $src}",
1446                  [(store (srl (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>,
1447                      OpSize;
1448   def SHR32mi  : Ii8<0xC1, MRM5m, (ops i32mem:$dst, i8imm:$src),
1449                      "shr{l} {$src, $dst|$dst, $src}",
1450                  [(store (srl (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1451 }
1452
1453 def SAR8rCL  : I<0xD2, MRM7r, (ops R8 :$dst, R8 :$src),
1454                  "sar{b} {%cl, $dst|$dst, %CL}",
1455                  [(set R8:$dst, (sra R8:$src, CL))]>, Imp<[CL],[]>;
1456 def SAR16rCL : I<0xD3, MRM7r, (ops R16:$dst, R16:$src),
1457                  "sar{w} {%cl, $dst|$dst, %CL}",
1458                  [(set R16:$dst, (sra R16:$src, CL))]>, Imp<[CL],[]>, OpSize;
1459 def SAR32rCL : I<0xD3, MRM7r, (ops R32:$dst, R32:$src),
1460                  "sar{l} {%cl, $dst|$dst, %CL}",
1461                  [(set R32:$dst, (sra R32:$src, CL))]>, Imp<[CL],[]>;
1462
1463 def SAR8ri   : Ii8<0xC0, MRM7r, (ops R8 :$dst, R8 :$src1, i8imm:$src2),
1464                    "sar{b} {$src2, $dst|$dst, $src2}",
1465                    [(set R8:$dst, (sra R8:$src1, (i8 imm:$src2)))]>;
1466 def SAR16ri  : Ii8<0xC1, MRM7r, (ops R16:$dst, R16:$src1, i8imm:$src2),
1467                    "sar{w} {$src2, $dst|$dst, $src2}",
1468                    [(set R16:$dst, (sra R16:$src1, (i8 imm:$src2)))]>,
1469                    OpSize;
1470 def SAR32ri  : Ii8<0xC1, MRM7r, (ops R32:$dst, R32:$src1, i8imm:$src2),
1471                    "sar{l} {$src2, $dst|$dst, $src2}",
1472                    [(set R32:$dst, (sra R32:$src1, (i8 imm:$src2)))]>;
1473 let isTwoAddress = 0 in {
1474   def SAR8mCL  : I<0xD2, MRM7m, (ops i8mem :$dst),
1475                    "sar{b} {%cl, $dst|$dst, %CL}",
1476                    [(store (sra (loadi8 addr:$dst), CL), addr:$dst)]>,
1477                    Imp<[CL],[]>;
1478   def SAR16mCL : I<0xD3, MRM7m, (ops i16mem:$dst),
1479                    "sar{w} {%cl, $dst|$dst, %CL}",
1480                    [(store (sra (loadi16 addr:$dst), CL), addr:$dst)]>,
1481                    Imp<[CL],[]>, OpSize;
1482   def SAR32mCL : I<0xD3, MRM7m, (ops i32mem:$dst), 
1483                    "sar{l} {%cl, $dst|$dst, %CL}",
1484                    [(store (sra (loadi32 addr:$dst), CL), addr:$dst)]>,
1485                    Imp<[CL],[]>;
1486   def SAR8mi   : Ii8<0xC0, MRM7m, (ops i8mem :$dst, i8imm:$src),
1487                      "sar{b} {$src, $dst|$dst, $src}",
1488                   [(store (sra (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1489   def SAR16mi  : Ii8<0xC1, MRM7m, (ops i16mem:$dst, i8imm:$src),
1490                      "sar{w} {$src, $dst|$dst, $src}",
1491                  [(store (sra (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>,
1492                      OpSize;
1493   def SAR32mi  : Ii8<0xC1, MRM7m, (ops i32mem:$dst, i8imm:$src),
1494                      "sar{l} {$src, $dst|$dst, $src}",
1495                  [(store (sra (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1496 }
1497
1498 // Rotate instructions
1499 // FIXME: provide shorter instructions when imm8 == 1
1500 def ROL8rCL  : I<0xD2, MRM0r, (ops R8 :$dst, R8 :$src),
1501                  "rol{b} {%cl, $dst|$dst, %CL}",
1502                  [(set R8:$dst, (rotl R8:$src, CL))]>, Imp<[CL],[]>;
1503 def ROL16rCL : I<0xD3, MRM0r, (ops R16:$dst, R16:$src),
1504                  "rol{w} {%cl, $dst|$dst, %CL}",
1505                  [(set R16:$dst, (rotl R16:$src, CL))]>, Imp<[CL],[]>, OpSize;
1506 def ROL32rCL : I<0xD3, MRM0r, (ops R32:$dst, R32:$src),
1507                  "rol{l} {%cl, $dst|$dst, %CL}",
1508                  [(set R32:$dst, (rotl R32:$src, CL))]>, Imp<[CL],[]>;
1509
1510 def ROL8ri   : Ii8<0xC0, MRM0r, (ops R8 :$dst, R8 :$src1, i8imm:$src2),
1511                    "rol{b} {$src2, $dst|$dst, $src2}",
1512                    [(set R8:$dst, (rotl R8:$src1, (i8 imm:$src2)))]>;
1513 def ROL16ri  : Ii8<0xC1, MRM0r, (ops R16:$dst, R16:$src1, i8imm:$src2),
1514                    "rol{w} {$src2, $dst|$dst, $src2}",
1515                    [(set R16:$dst, (rotl R16:$src1, (i8 imm:$src2)))]>, OpSize;
1516 def ROL32ri  : Ii8<0xC1, MRM0r, (ops R32:$dst, R32:$src1, i8imm:$src2),
1517                    "rol{l} {$src2, $dst|$dst, $src2}",
1518                    [(set R32:$dst, (rotl R32:$src1, (i8 imm:$src2)))]>;
1519
1520 let isTwoAddress = 0 in {
1521   def ROL8mCL  : I<0xD2, MRM0m, (ops i8mem :$dst),
1522                    "rol{b} {%cl, $dst|$dst, %CL}",
1523                    [(store (rotl (loadi8 addr:$dst), CL), addr:$dst)]>,
1524                    Imp<[CL],[]>;
1525   def ROL16mCL : I<0xD3, MRM0m, (ops i16mem:$dst),
1526                    "rol{w} {%cl, $dst|$dst, %CL}",
1527                    [(store (rotl (loadi16 addr:$dst), CL), addr:$dst)]>,
1528                    Imp<[CL],[]>, OpSize;
1529   def ROL32mCL : I<0xD3, MRM0m, (ops i32mem:$dst),
1530                    "rol{l} {%cl, $dst|$dst, %CL}",
1531                    [(store (rotl (loadi32 addr:$dst), CL), addr:$dst)]>,
1532                    Imp<[CL],[]>;
1533   def ROL8mi   : Ii8<0xC0, MRM0m, (ops i8mem :$dst, i8imm:$src),
1534                      "rol{b} {$src, $dst|$dst, $src}",
1535                  [(store (rotl (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1536   def ROL16mi  : Ii8<0xC1, MRM0m, (ops i16mem:$dst, i8imm:$src),
1537                      "rol{w} {$src, $dst|$dst, $src}",
1538                 [(store (rotl (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>,
1539                      OpSize;
1540   def ROL32mi  : Ii8<0xC1, MRM0m, (ops i32mem:$dst, i8imm:$src),
1541                      "rol{l} {$src, $dst|$dst, $src}",
1542                 [(store (rotl (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1543 }
1544
1545 def ROR8rCL  : I<0xD2, MRM1r, (ops R8 :$dst, R8 :$src),
1546                  "ror{b} {%cl, $dst|$dst, %CL}",
1547                  [(set R8:$dst, (rotr R8:$src, CL))]>, Imp<[CL],[]>;
1548 def ROR16rCL : I<0xD3, MRM1r, (ops R16:$dst, R16:$src),
1549                  "ror{w} {%cl, $dst|$dst, %CL}",
1550                  [(set R16:$dst, (rotr R16:$src, CL))]>, Imp<[CL],[]>, OpSize;
1551 def ROR32rCL : I<0xD3, MRM1r, (ops R32:$dst, R32:$src),
1552                  "ror{l} {%cl, $dst|$dst, %CL}",
1553                  [(set R32:$dst, (rotr R32:$src, CL))]>, Imp<[CL],[]>;
1554
1555 def ROR8ri   : Ii8<0xC0, MRM1r, (ops R8 :$dst, R8 :$src1, i8imm:$src2),
1556                    "ror{b} {$src2, $dst|$dst, $src2}",
1557                    [(set R8:$dst, (rotr R8:$src1, (i8 imm:$src2)))]>;
1558 def ROR16ri  : Ii8<0xC1, MRM1r, (ops R16:$dst, R16:$src1, i8imm:$src2),
1559                    "ror{w} {$src2, $dst|$dst, $src2}",
1560                    [(set R16:$dst, (rotr R16:$src1, (i8 imm:$src2)))]>, OpSize;
1561 def ROR32ri  : Ii8<0xC1, MRM1r, (ops R32:$dst, R32:$src1, i8imm:$src2),
1562                    "ror{l} {$src2, $dst|$dst, $src2}",
1563                    [(set R32:$dst, (rotr R32:$src1, (i8 imm:$src2)))]>;
1564 let isTwoAddress = 0 in {
1565   def ROR8mCL  : I<0xD2, MRM1m, (ops i8mem :$dst),
1566                    "ror{b} {%cl, $dst|$dst, %CL}",
1567                    [(store (rotr (loadi8 addr:$dst), CL), addr:$dst)]>,
1568                    Imp<[CL],[]>;
1569   def ROR16mCL : I<0xD3, MRM1m, (ops i16mem:$dst),
1570                    "ror{w} {%cl, $dst|$dst, %CL}",
1571                    [(store (rotr (loadi16 addr:$dst), CL), addr:$dst)]>,
1572                    Imp<[CL],[]>, OpSize;
1573   def ROR32mCL : I<0xD3, MRM1m, (ops i32mem:$dst), 
1574                    "ror{l} {%cl, $dst|$dst, %CL}",
1575                    [(store (rotr (loadi32 addr:$dst), CL), addr:$dst)]>,
1576                    Imp<[CL],[]>;
1577   def ROR8mi   : Ii8<0xC0, MRM1m, (ops i8mem :$dst, i8imm:$src),
1578                      "ror{b} {$src, $dst|$dst, $src}",
1579                  [(store (rotr (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1580   def ROR16mi  : Ii8<0xC1, MRM1m, (ops i16mem:$dst, i8imm:$src),
1581                      "ror{w} {$src, $dst|$dst, $src}",
1582                 [(store (rotr (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>,
1583                      OpSize;
1584   def ROR32mi  : Ii8<0xC1, MRM1m, (ops i32mem:$dst, i8imm:$src),
1585                      "ror{l} {$src, $dst|$dst, $src}",
1586                 [(store (rotr (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>;
1587 }
1588
1589
1590
1591 // Double shift instructions (generalizations of rotate)
1592 def SHLD32rrCL : I<0xA5, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1593                    "shld{l} {%cl, $src2, $dst|$dst, $src2, %CL}",
1594                    [(set R32:$dst, (X86shld R32:$src1, R32:$src2, CL))]>,
1595                    Imp<[CL],[]>, TB;
1596 def SHRD32rrCL : I<0xAD, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1597                    "shrd{l} {%cl, $src2, $dst|$dst, $src2, %CL}",
1598                    [(set R32:$dst, (X86shrd R32:$src1, R32:$src2, CL))]>,
1599                    Imp<[CL],[]>, TB;
1600 def SHLD16rrCL : I<0xA5, MRMDestReg, (ops R16:$dst, R16:$src1, R16:$src2),
1601                    "shld{w} {%cl, $src2, $dst|$dst, $src2, %CL}",
1602                    [(set R16:$dst, (X86shld R16:$src1, R16:$src2, CL))]>,
1603                    Imp<[CL],[]>, TB, OpSize;
1604 def SHRD16rrCL : I<0xAD, MRMDestReg, (ops R16:$dst, R16:$src1, R16:$src2),
1605                    "shrd{w} {%cl, $src2, $dst|$dst, $src2, %CL}",
1606                    [(set R16:$dst, (X86shrd R16:$src1, R16:$src2, CL))]>,
1607                    Imp<[CL],[]>, TB, OpSize;
1608
1609 let isCommutable = 1 in {  // These instructions commute to each other.
1610 def SHLD32rri8 : Ii8<0xA4, MRMDestReg,
1611                      (ops R32:$dst, R32:$src1, R32:$src2, i8imm:$src3),
1612                      "shld{l} {$src3, $src2, $dst|$dst, $src2, $src3}",
1613                      [(set R32:$dst, (X86shld R32:$src1, R32:$src2,
1614                                       (i8 imm:$src3)))]>,
1615                  TB;
1616 def SHRD32rri8 : Ii8<0xAC, MRMDestReg,
1617                      (ops R32:$dst, R32:$src1, R32:$src2, i8imm:$src3),
1618                      "shrd{l} {$src3, $src2, $dst|$dst, $src2, $src3}",
1619                      [(set R32:$dst, (X86shrd R32:$src1, R32:$src2,
1620                                       (i8 imm:$src3)))]>,
1621                  TB;
1622 def SHLD16rri8 : Ii8<0xA4, MRMDestReg,
1623                      (ops R16:$dst, R16:$src1, R16:$src2, i8imm:$src3),
1624                      "shld{w} {$src3, $src2, $dst|$dst, $src2, $src3}",
1625                      [(set R16:$dst, (X86shld R16:$src1, R16:$src2,
1626                                       (i8 imm:$src3)))]>,
1627                      TB, OpSize;
1628 def SHRD16rri8 : Ii8<0xAC, MRMDestReg,
1629                      (ops R16:$dst, R16:$src1, R16:$src2, i8imm:$src3),
1630                      "shrd{w} {$src3, $src2, $dst|$dst, $src2, $src3}",
1631                      [(set R16:$dst, (X86shrd R16:$src1, R16:$src2,
1632                                       (i8 imm:$src3)))]>,
1633                      TB, OpSize;
1634 }
1635
1636 let isTwoAddress = 0 in {
1637   def SHLD32mrCL : I<0xA5, MRMDestMem, (ops i32mem:$dst, R32:$src2),
1638                      "shld{l} {%cl, $src2, $dst|$dst, $src2, %CL}",
1639                      [(store (X86shld (loadi32 addr:$dst), R32:$src2, CL),
1640                        addr:$dst)]>,
1641                      Imp<[CL],[]>, TB;
1642   def SHRD32mrCL : I<0xAD, MRMDestMem, (ops i32mem:$dst, R32:$src2),
1643                     "shrd{l} {%cl, $src2, $dst|$dst, $src2, %CL}",
1644                     [(store (X86shrd (loadi32 addr:$dst), R32:$src2, CL),
1645                       addr:$dst)]>,
1646                     Imp<[CL],[]>, TB;
1647   def SHLD32mri8 : Ii8<0xA4, MRMDestMem,
1648                       (ops i32mem:$dst, R32:$src2, i8imm:$src3),
1649                       "shld{l} {$src3, $src2, $dst|$dst, $src2, $src3}",
1650                       [(store (X86shld (loadi32 addr:$dst), R32:$src2,
1651                                         (i8 imm:$src3)), addr:$dst)]>,
1652                       TB;
1653   def SHRD32mri8 : Ii8<0xAC, MRMDestMem, 
1654                        (ops i32mem:$dst, R32:$src2, i8imm:$src3),
1655                        "shrd{l} {$src3, $src2, $dst|$dst, $src2, $src3}",
1656                        [(store (X86shrd (loadi32 addr:$dst), R32:$src2,
1657                                          (i8 imm:$src3)), addr:$dst)]>,
1658                        TB;
1659
1660   def SHLD16mrCL : I<0xA5, MRMDestMem, (ops i16mem:$dst, R16:$src2),
1661                      "shld{w} {%cl, $src2, $dst|$dst, $src2, %CL}",
1662                      [(store (X86shld (loadi16 addr:$dst), R16:$src2, CL),
1663                        addr:$dst)]>,
1664                      Imp<[CL],[]>, TB, OpSize;
1665   def SHRD16mrCL : I<0xAD, MRMDestMem, (ops i16mem:$dst, R16:$src2),
1666                     "shrd{w} {%cl, $src2, $dst|$dst, $src2, %CL}",
1667                     [(store (X86shrd (loadi16 addr:$dst), R16:$src2, CL),
1668                       addr:$dst)]>,
1669                     Imp<[CL],[]>, TB, OpSize;
1670   def SHLD16mri8 : Ii8<0xA4, MRMDestMem,
1671                       (ops i16mem:$dst, R16:$src2, i8imm:$src3),
1672                       "shld{w} {$src3, $src2, $dst|$dst, $src2, $src3}",
1673                       [(store (X86shld (loadi16 addr:$dst), R16:$src2,
1674                                         (i8 imm:$src3)), addr:$dst)]>,
1675                       TB, OpSize;
1676   def SHRD16mri8 : Ii8<0xAC, MRMDestMem, 
1677                        (ops i16mem:$dst, R16:$src2, i8imm:$src3),
1678                        "shrd{w} {$src3, $src2, $dst|$dst, $src2, $src3}",
1679                       [(store (X86shrd (loadi16 addr:$dst), R16:$src2,
1680                                         (i8 imm:$src3)), addr:$dst)]>,
1681                        TB, OpSize;
1682 }
1683
1684
1685 // Arithmetic.
1686 let isCommutable = 1 in {   // X = ADD Y, Z   --> X = ADD Z, Y
1687 def ADD8rr   : I<0x00, MRMDestReg, (ops R8 :$dst, R8 :$src1, R8 :$src2),
1688                  "add{b} {$src2, $dst|$dst, $src2}",
1689                  [(set R8:$dst, (add R8:$src1, R8:$src2))]>;
1690 let isConvertibleToThreeAddress = 1 in {   // Can transform into LEA.
1691 def ADD16rr  : I<0x01, MRMDestReg, (ops R16:$dst, R16:$src1, R16:$src2),
1692                  "add{w} {$src2, $dst|$dst, $src2}",
1693                  [(set R16:$dst, (add R16:$src1, R16:$src2))]>, OpSize;
1694 def ADD32rr  : I<0x01, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1695                  "add{l} {$src2, $dst|$dst, $src2}",
1696                  [(set R32:$dst, (add R32:$src1, R32:$src2))]>;
1697 } // end isConvertibleToThreeAddress
1698 } // end isCommutable
1699 def ADD8rm   : I<0x02, MRMSrcMem, (ops R8 :$dst, R8 :$src1, i8mem :$src2),
1700                  "add{b} {$src2, $dst|$dst, $src2}",
1701                  [(set R8:$dst, (add R8:$src1, (load addr:$src2)))]>;
1702 def ADD16rm  : I<0x03, MRMSrcMem, (ops R16:$dst, R16:$src1, i16mem:$src2),
1703                  "add{w} {$src2, $dst|$dst, $src2}",
1704                  [(set R16:$dst, (add R16:$src1, (load addr:$src2)))]>, OpSize;
1705 def ADD32rm  : I<0x03, MRMSrcMem, (ops R32:$dst, R32:$src1, i32mem:$src2),
1706                  "add{l} {$src2, $dst|$dst, $src2}",
1707                  [(set R32:$dst, (add R32:$src1, (load addr:$src2)))]>;
1708
1709 def ADD8ri   : Ii8<0x80, MRM0r, (ops R8:$dst, R8:$src1, i8imm:$src2),
1710                    "add{b} {$src2, $dst|$dst, $src2}",
1711                    [(set R8:$dst, (add R8:$src1, imm:$src2))]>;
1712
1713 let isConvertibleToThreeAddress = 1 in {   // Can transform into LEA.
1714 def ADD16ri  : Ii16<0x81, MRM0r, (ops R16:$dst, R16:$src1, i16imm:$src2),
1715                     "add{w} {$src2, $dst|$dst, $src2}",
1716                     [(set R16:$dst, (add R16:$src1, imm:$src2))]>, OpSize;
1717 def ADD32ri  : Ii32<0x81, MRM0r, (ops R32:$dst, R32:$src1, i32imm:$src2),
1718                     "add{l} {$src2, $dst|$dst, $src2}",
1719                     [(set R32:$dst, (add R32:$src1, imm:$src2))]>;
1720 }
1721
1722 def ADD16ri8 : Ii8<0x83, MRM0r, (ops R16:$dst, R16:$src1, i16i8imm:$src2),
1723                    "add{w} {$src2, $dst|$dst, $src2}",
1724                    [(set R16:$dst, (add R16:$src1, i16immSExt8:$src2))]>,
1725                    OpSize;
1726 def ADD32ri8 : Ii8<0x83, MRM0r, (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1727                    "add{l} {$src2, $dst|$dst, $src2}",
1728                    [(set R32:$dst, (add R32:$src1, i32immSExt8:$src2))]>;
1729
1730 let isTwoAddress = 0 in {
1731   def ADD8mr   : I<0x00, MRMDestMem, (ops i8mem :$dst, R8 :$src2),
1732                    "add{b} {$src2, $dst|$dst, $src2}",
1733                    [(store (add (load addr:$dst), R8:$src2), addr:$dst)]>;
1734   def ADD16mr  : I<0x01, MRMDestMem, (ops i16mem:$dst, R16:$src2),
1735                    "add{w} {$src2, $dst|$dst, $src2}",
1736                    [(store (add (load addr:$dst), R16:$src2), addr:$dst)]>,
1737                    OpSize;
1738   def ADD32mr  : I<0x01, MRMDestMem, (ops i32mem:$dst, R32:$src2),
1739                    "add{l} {$src2, $dst|$dst, $src2}",
1740                    [(store (add (load addr:$dst), R32:$src2), addr:$dst)]>;
1741   def ADD8mi   : Ii8<0x80, MRM0m, (ops i8mem :$dst, i8imm :$src2),
1742                      "add{b} {$src2, $dst|$dst, $src2}",
1743                    [(store (add (loadi8 addr:$dst), imm:$src2), addr:$dst)]>;
1744   def ADD16mi  : Ii16<0x81, MRM0m, (ops i16mem:$dst, i16imm:$src2),
1745                       "add{w} {$src2, $dst|$dst, $src2}",
1746                   [(store (add (loadi16 addr:$dst), imm:$src2), addr:$dst)]>,
1747                    OpSize;
1748   def ADD32mi  : Ii32<0x81, MRM0m, (ops i32mem:$dst, i32imm:$src2),
1749                       "add{l} {$src2, $dst|$dst, $src2}",
1750                   [(store (add (loadi32 addr:$dst), imm:$src2), addr:$dst)]>;
1751   def ADD16mi8 : Ii8<0x83, MRM0m, (ops i16mem:$dst, i16i8imm :$src2),
1752                      "add{w} {$src2, $dst|$dst, $src2}",
1753                 [(store (add (load addr:$dst), i16immSExt8:$src2), addr:$dst)]>,
1754                    OpSize;
1755   def ADD32mi8 : Ii8<0x83, MRM0m, (ops i32mem:$dst, i32i8imm :$src2),
1756                      "add{l} {$src2, $dst|$dst, $src2}",
1757                 [(store (add (load addr:$dst), i32immSExt8:$src2), addr:$dst)]>;
1758 }
1759
1760 let isCommutable = 1 in {  // X = ADC Y, Z --> X = ADC Z, Y
1761 def ADC32rr  : I<0x11, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1762                  "adc{l} {$src2, $dst|$dst, $src2}",
1763                  [(set R32:$dst, (adde R32:$src1, R32:$src2))]>;
1764 }
1765 def ADC32rm  : I<0x13, MRMSrcMem , (ops R32:$dst, R32:$src1, i32mem:$src2),
1766                  "adc{l} {$src2, $dst|$dst, $src2}",
1767                  [(set R32:$dst, (adde R32:$src1, (load addr:$src2)))]>;
1768 def ADC32ri  : Ii32<0x81, MRM2r, (ops R32:$dst, R32:$src1, i32imm:$src2),
1769                     "adc{l} {$src2, $dst|$dst, $src2}",
1770                  [(set R32:$dst, (adde R32:$src1, imm:$src2))]>;
1771 def ADC32ri8 : Ii8<0x83, MRM2r, (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1772                    "adc{l} {$src2, $dst|$dst, $src2}",
1773                  [(set R32:$dst, (adde R32:$src1, i32immSExt8:$src2))]>;
1774
1775 let isTwoAddress = 0 in {
1776   def ADC32mr  : I<0x11, MRMDestMem, (ops i32mem:$dst, R32:$src2),
1777                    "adc{l} {$src2, $dst|$dst, $src2}",
1778                    [(store (adde (load addr:$dst), R32:$src2), addr:$dst)]>;
1779   def ADC32mi  : Ii32<0x81, MRM2m, (ops i32mem:$dst, i32imm:$src2),
1780                       "adc{l} {$src2, $dst|$dst, $src2}",
1781                   [(store (adde (loadi32 addr:$dst), imm:$src2), addr:$dst)]>;
1782   def ADC32mi8 : Ii8<0x83, MRM2m, (ops i32mem:$dst, i32i8imm :$src2),
1783                      "adc{l} {$src2, $dst|$dst, $src2}",
1784              [(store (adde (load addr:$dst), i32immSExt8:$src2), addr:$dst)]>;
1785 }
1786
1787 def SUB8rr   : I<0x28, MRMDestReg, (ops R8 :$dst, R8 :$src1, R8 :$src2),
1788                  "sub{b} {$src2, $dst|$dst, $src2}",
1789                  [(set R8:$dst, (sub R8:$src1, R8:$src2))]>;
1790 def SUB16rr  : I<0x29, MRMDestReg, (ops R16:$dst, R16:$src1, R16:$src2),
1791                  "sub{w} {$src2, $dst|$dst, $src2}",
1792                  [(set R16:$dst, (sub R16:$src1, R16:$src2))]>, OpSize;
1793 def SUB32rr  : I<0x29, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1794                  "sub{l} {$src2, $dst|$dst, $src2}",
1795                  [(set R32:$dst, (sub R32:$src1, R32:$src2))]>;
1796 def SUB8rm   : I<0x2A, MRMSrcMem, (ops R8 :$dst, R8 :$src1, i8mem :$src2),
1797                  "sub{b} {$src2, $dst|$dst, $src2}",
1798                  [(set R8:$dst, (sub R8:$src1, (load addr:$src2)))]>;
1799 def SUB16rm  : I<0x2B, MRMSrcMem, (ops R16:$dst, R16:$src1, i16mem:$src2),
1800                  "sub{w} {$src2, $dst|$dst, $src2}",
1801                  [(set R16:$dst, (sub R16:$src1, (load addr:$src2)))]>, OpSize;
1802 def SUB32rm  : I<0x2B, MRMSrcMem, (ops R32:$dst, R32:$src1, i32mem:$src2),
1803                  "sub{l} {$src2, $dst|$dst, $src2}",
1804                  [(set R32:$dst, (sub R32:$src1, (load addr:$src2)))]>;
1805
1806 def SUB8ri   : Ii8 <0x80, MRM5r, (ops R8:$dst, R8:$src1, i8imm:$src2),
1807                     "sub{b} {$src2, $dst|$dst, $src2}",
1808                     [(set R8:$dst, (sub R8:$src1, imm:$src2))]>;
1809 def SUB16ri  : Ii16<0x81, MRM5r, (ops R16:$dst, R16:$src1, i16imm:$src2),
1810                     "sub{w} {$src2, $dst|$dst, $src2}",
1811                     [(set R16:$dst, (sub R16:$src1, imm:$src2))]>, OpSize;
1812 def SUB32ri  : Ii32<0x81, MRM5r, (ops R32:$dst, R32:$src1, i32imm:$src2),
1813                     "sub{l} {$src2, $dst|$dst, $src2}",
1814                     [(set R32:$dst, (sub R32:$src1, imm:$src2))]>;
1815 def SUB16ri8 : Ii8<0x83, MRM5r, (ops R16:$dst, R16:$src1, i16i8imm:$src2),
1816                    "sub{w} {$src2, $dst|$dst, $src2}",
1817                    [(set R16:$dst, (sub R16:$src1, i16immSExt8:$src2))]>,
1818                    OpSize;
1819 def SUB32ri8 : Ii8<0x83, MRM5r, (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1820                    "sub{l} {$src2, $dst|$dst, $src2}",
1821                    [(set R32:$dst, (sub R32:$src1, i32immSExt8:$src2))]>;
1822 let isTwoAddress = 0 in {
1823   def SUB8mr   : I<0x28, MRMDestMem, (ops i8mem :$dst, R8 :$src2),
1824                    "sub{b} {$src2, $dst|$dst, $src2}",
1825                    [(store (sub (load addr:$dst), R8:$src2), addr:$dst)]>;
1826   def SUB16mr  : I<0x29, MRMDestMem, (ops i16mem:$dst, R16:$src2),
1827                    "sub{w} {$src2, $dst|$dst, $src2}",
1828                    [(store (sub (load addr:$dst), R16:$src2), addr:$dst)]>,
1829                    OpSize;
1830   def SUB32mr  : I<0x29, MRMDestMem, (ops i32mem:$dst, R32:$src2), 
1831                    "sub{l} {$src2, $dst|$dst, $src2}",
1832                    [(store (sub (load addr:$dst), R32:$src2), addr:$dst)]>;
1833   def SUB8mi   : Ii8<0x80, MRM5m, (ops i8mem :$dst, i8imm:$src2), 
1834                      "sub{b} {$src2, $dst|$dst, $src2}",
1835                    [(store (sub (loadi8 addr:$dst), imm:$src2), addr:$dst)]>;
1836   def SUB16mi  : Ii16<0x81, MRM5m, (ops i16mem:$dst, i16imm:$src2), 
1837                       "sub{w} {$src2, $dst|$dst, $src2}",
1838                   [(store (sub (loadi16 addr:$dst), imm:$src2), addr:$dst)]>,
1839                    OpSize;
1840   def SUB32mi  : Ii32<0x81, MRM5m, (ops i32mem:$dst, i32imm:$src2), 
1841                       "sub{l} {$src2, $dst|$dst, $src2}",
1842                   [(store (sub (loadi32 addr:$dst), imm:$src2), addr:$dst)]>;
1843   def SUB16mi8 : Ii8<0x83, MRM5m, (ops i16mem:$dst, i16i8imm :$src2), 
1844                      "sub{w} {$src2, $dst|$dst, $src2}",
1845                 [(store (sub (load addr:$dst), i16immSExt8:$src2), addr:$dst)]>,
1846                    OpSize;
1847   def SUB32mi8 : Ii8<0x83, MRM5m, (ops i32mem:$dst, i32i8imm :$src2), 
1848                      "sub{l} {$src2, $dst|$dst, $src2}",
1849                 [(store (sub (load addr:$dst), i32immSExt8:$src2), addr:$dst)]>;
1850 }
1851
1852 def SBB32rr    : I<0x19, MRMDestReg, (ops R32:$dst, R32:$src1, R32:$src2),
1853                   "sbb{l} {$src2, $dst|$dst, $src2}",
1854                   [(set R32:$dst, (sube R32:$src1, R32:$src2))]>;
1855
1856 let isTwoAddress = 0 in {
1857   def SBB32mr  : I<0x19, MRMDestMem, (ops i32mem:$dst, R32:$src2), 
1858                    "sbb{l} {$src2, $dst|$dst, $src2}",
1859                    [(store (sube (load addr:$dst), R32:$src2), addr:$dst)]>;
1860   def SBB8mi  : Ii32<0x80, MRM3m, (ops i8mem:$dst, i8imm:$src2), 
1861                       "sbb{b} {$src2, $dst|$dst, $src2}",
1862                    [(store (sube (loadi8 addr:$dst), imm:$src2), addr:$dst)]>;
1863   def SBB32mi  : Ii32<0x81, MRM3m, (ops i32mem:$dst, i32imm:$src2), 
1864                       "sbb{l} {$src2, $dst|$dst, $src2}",
1865                   [(store (sube (loadi32 addr:$dst), imm:$src2), addr:$dst)]>;
1866   def SBB32mi8 : Ii8<0x83, MRM3m, (ops i32mem:$dst, i32i8imm :$src2), 
1867                      "sbb{l} {$src2, $dst|$dst, $src2}",
1868              [(store (sube (load addr:$dst), i32immSExt8:$src2), addr:$dst)]>;
1869 }
1870 def SBB32rm  : I<0x1B, MRMSrcMem, (ops R32:$dst, R32:$src1, i32mem:$src2),
1871                     "sbb{l} {$src2, $dst|$dst, $src2}",
1872                     [(set R32:$dst, (sube R32:$src1, (load addr:$src2)))]>;
1873 def SBB32ri  : Ii32<0x81, MRM3r, (ops R32:$dst, R32:$src1, i32imm:$src2),
1874                     "sbb{l} {$src2, $dst|$dst, $src2}",
1875                     [(set R32:$dst, (sube R32:$src1, imm:$src2))]>;
1876 def SBB32ri8 : Ii8<0x83, MRM3r, (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1877                    "sbb{l} {$src2, $dst|$dst, $src2}",
1878                    [(set R32:$dst, (sube R32:$src1, i32immSExt8:$src2))]>;
1879
1880 let isCommutable = 1 in {  // X = IMUL Y, Z --> X = IMUL Z, Y
1881 def IMUL16rr : I<0xAF, MRMSrcReg, (ops R16:$dst, R16:$src1, R16:$src2),
1882                  "imul{w} {$src2, $dst|$dst, $src2}",
1883                  [(set R16:$dst, (mul R16:$src1, R16:$src2))]>, TB, OpSize;
1884 def IMUL32rr : I<0xAF, MRMSrcReg, (ops R32:$dst, R32:$src1, R32:$src2),
1885                  "imul{l} {$src2, $dst|$dst, $src2}",
1886                  [(set R32:$dst, (mul R32:$src1, R32:$src2))]>, TB;
1887 }
1888 def IMUL16rm : I<0xAF, MRMSrcMem, (ops R16:$dst, R16:$src1, i16mem:$src2),
1889                  "imul{w} {$src2, $dst|$dst, $src2}",
1890                  [(set R16:$dst, (mul R16:$src1, (load addr:$src2)))]>,
1891                  TB, OpSize;
1892 def IMUL32rm : I<0xAF, MRMSrcMem, (ops R32:$dst, R32:$src1, i32mem:$src2),
1893                  "imul{l} {$src2, $dst|$dst, $src2}",
1894                  [(set R32:$dst, (mul R32:$src1, (load addr:$src2)))]>, TB;
1895
1896 } // end Two Address instructions
1897
1898 // Suprisingly enough, these are not two address instructions!
1899 def IMUL16rri  : Ii16<0x69, MRMSrcReg,                      // R16 = R16*I16
1900                       (ops R16:$dst, R16:$src1, i16imm:$src2),
1901                       "imul{w} {$src2, $src1, $dst|$dst, $src1, $src2}",
1902                       [(set R16:$dst, (mul R16:$src1, imm:$src2))]>, OpSize;
1903 def IMUL32rri  : Ii32<0x69, MRMSrcReg,                      // R32 = R32*I32
1904                       (ops R32:$dst, R32:$src1, i32imm:$src2),
1905                       "imul{l} {$src2, $src1, $dst|$dst, $src1, $src2}",
1906                       [(set R32:$dst, (mul R32:$src1, imm:$src2))]>;
1907 def IMUL16rri8 : Ii8<0x6B, MRMSrcReg,                       // R16 = R16*I8
1908                      (ops R16:$dst, R16:$src1, i16i8imm:$src2),
1909                      "imul{w} {$src2, $src1, $dst|$dst, $src1, $src2}",
1910                      [(set R16:$dst, (mul R16:$src1, i16immSExt8:$src2))]>,
1911                      OpSize;
1912 def IMUL32rri8 : Ii8<0x6B, MRMSrcReg,                       // R32 = R32*I8
1913                      (ops R32:$dst, R32:$src1, i32i8imm:$src2),
1914                      "imul{l} {$src2, $src1, $dst|$dst, $src1, $src2}",
1915                      [(set R32:$dst, (mul R32:$src1, i32immSExt8:$src2))]>;
1916
1917 def IMUL16rmi  : Ii16<0x69, MRMSrcMem,                      // R16 = [mem16]*I16
1918                       (ops R16:$dst, i16mem:$src1, i16imm:$src2),
1919                       "imul{w} {$src2, $src1, $dst|$dst, $src1, $src2}",
1920                       [(set R16:$dst, (mul (load addr:$src1), imm:$src2))]>,
1921                       OpSize;
1922 def IMUL32rmi  : Ii32<0x69, MRMSrcMem,                      // R32 = [mem32]*I32
1923                       (ops R32:$dst, i32mem:$src1, i32imm:$src2),
1924                       "imul{l} {$src2, $src1, $dst|$dst, $src1, $src2}",
1925                       [(set R32:$dst, (mul (load addr:$src1), imm:$src2))]>;
1926 def IMUL16rmi8 : Ii8<0x6B, MRMSrcMem,                       // R16 = [mem16]*I8
1927                      (ops R16:$dst, i16mem:$src1, i16i8imm :$src2),
1928                      "imul{w} {$src2, $src1, $dst|$dst, $src1, $src2}",
1929                   [(set R16:$dst, (mul (load addr:$src1), i16immSExt8:$src2))]>,
1930                      OpSize;
1931 def IMUL32rmi8 : Ii8<0x6B, MRMSrcMem,                       // R32 = [mem32]*I8
1932                      (ops R32:$dst, i32mem:$src1, i32i8imm: $src2),
1933                      "imul{l} {$src2, $src1, $dst|$dst, $src1, $src2}",
1934                   [(set R32:$dst, (mul (load addr:$src1), i32immSExt8:$src2))]>;
1935
1936 //===----------------------------------------------------------------------===//
1937 // Test instructions are just like AND, except they don't generate a result.
1938 //
1939 let isCommutable = 1 in {   // TEST X, Y   --> TEST Y, X
1940 def TEST8rr  : I<0x84, MRMDestReg, (ops R8:$src1, R8:$src2),
1941                  "test{b} {$src2, $src1|$src1, $src2}",
1942                  [(X86test R8:$src1, R8:$src2)]>;
1943 def TEST16rr : I<0x85, MRMDestReg, (ops R16:$src1, R16:$src2),
1944                  "test{w} {$src2, $src1|$src1, $src2}",
1945                  [(X86test R16:$src1, R16:$src2)]>, OpSize;
1946 def TEST32rr : I<0x85, MRMDestReg, (ops R32:$src1, R32:$src2),
1947                  "test{l} {$src2, $src1|$src1, $src2}",
1948                  [(X86test R32:$src1, R32:$src2)]>;
1949 }
1950 def TEST8mr  : I<0x84, MRMDestMem, (ops i8mem :$src1, R8 :$src2),
1951                  "test{b} {$src2, $src1|$src1, $src2}",
1952                  [(X86test (loadi8 addr:$src1), R8:$src2)]>;
1953 def TEST16mr : I<0x85, MRMDestMem, (ops i16mem:$src1, R16:$src2),
1954                  "test{w} {$src2, $src1|$src1, $src2}",
1955                  [(X86test (loadi16 addr:$src1), R16:$src2)]>,
1956                OpSize;
1957 def TEST32mr : I<0x85, MRMDestMem, (ops i32mem:$src1, R32:$src2),
1958                  "test{l} {$src2, $src1|$src1, $src2}",
1959                  [(X86test (loadi32 addr:$src1), R32:$src2)]>;
1960 def TEST8rm  : I<0x84, MRMSrcMem, (ops R8 :$src1, i8mem :$src2),
1961                  "test{b} {$src2, $src1|$src1, $src2}",
1962                  [(X86test R8:$src1, (loadi8 addr:$src2))]>;
1963 def TEST16rm : I<0x85, MRMSrcMem, (ops R16:$src1, i16mem:$src2),
1964                  "test{w} {$src2, $src1|$src1, $src2}",
1965                  [(X86test R16:$src1, (loadi16 addr:$src2))]>,
1966                OpSize;
1967 def TEST32rm : I<0x85, MRMSrcMem, (ops R32:$src1, i32mem:$src2),
1968                  "test{l} {$src2, $src1|$src1, $src2}",
1969                  [(X86test R32:$src1, (loadi32 addr:$src2))]>;
1970
1971 def TEST8ri  : Ii8 <0xF6, MRM0r,                     // flags = R8  & imm8
1972                     (ops R8:$src1, i8imm:$src2),
1973                     "test{b} {$src2, $src1|$src1, $src2}",
1974                     [(X86test R8:$src1, imm:$src2)]>;
1975 def TEST16ri : Ii16<0xF7, MRM0r,                     // flags = R16 & imm16
1976                     (ops R16:$src1, i16imm:$src2),
1977                     "test{w} {$src2, $src1|$src1, $src2}",
1978                     [(X86test R16:$src1, imm:$src2)]>, OpSize;
1979 def TEST32ri : Ii32<0xF7, MRM0r,                     // flags = R32 & imm32
1980                     (ops R32:$src1, i32imm:$src2),
1981                     "test{l} {$src2, $src1|$src1, $src2}",
1982                     [(X86test R32:$src1, imm:$src2)]>;
1983 def TEST8mi  : Ii8 <0xF6, MRM0m,                     // flags = [mem8]  & imm8
1984                     (ops i8mem:$src1, i8imm:$src2),
1985                     "test{b} {$src2, $src1|$src1, $src2}",
1986                     [(X86test (loadi8 addr:$src1), imm:$src2)]>;
1987 def TEST16mi : Ii16<0xF7, MRM0m,                     // flags = [mem16] & imm16
1988                     (ops i16mem:$src1, i16imm:$src2),
1989                     "test{w} {$src2, $src1|$src1, $src2}",
1990                     [(X86test (loadi16 addr:$src1), imm:$src2)]>,
1991                OpSize;
1992 def TEST32mi : Ii32<0xF7, MRM0m,                     // flags = [mem32] & imm32
1993                     (ops i32mem:$src1, i32imm:$src2),
1994                     "test{l} {$src2, $src1|$src1, $src2}",
1995                     [(X86test (loadi32 addr:$src1), imm:$src2)]>;
1996
1997
1998 // Condition code ops, incl. set if equal/not equal/...
1999 def SAHF     : I<0x9E, RawFrm, (ops), "sahf", []>, Imp<[AH],[]>;  // flags = AH
2000 def LAHF     : I<0x9F, RawFrm, (ops), "lahf", []>, Imp<[],[AH]>;  // AH = flags
2001
2002 def SETEr    : I<0x94, MRM0r, 
2003                  (ops R8   :$dst),
2004                  "sete $dst",
2005                  [(set R8:$dst, (X86setcc X86_COND_E))]>,
2006                TB;                        // R8 = ==
2007 def SETEm    : I<0x94, MRM0m, 
2008                  (ops i8mem:$dst),
2009                  "sete $dst",
2010                  [(store (X86setcc X86_COND_E), addr:$dst)]>,
2011                TB;                        // [mem8] = ==
2012 def SETNEr   : I<0x95, MRM0r, 
2013                  (ops R8   :$dst),
2014                  "setne $dst",
2015                  [(set R8:$dst, (X86setcc X86_COND_NE))]>,
2016                TB;                        // R8 = !=
2017 def SETNEm   : I<0x95, MRM0m, 
2018                  (ops i8mem:$dst),
2019                  "setne $dst",
2020                  [(store (X86setcc X86_COND_NE), addr:$dst)]>,
2021                TB;                        // [mem8] = !=
2022 def SETLr    : I<0x9C, MRM0r, 
2023                  (ops R8   :$dst),
2024                  "setl $dst",
2025                  [(set R8:$dst, (X86setcc X86_COND_L))]>,
2026                TB;                        // R8 = <  signed
2027 def SETLm    : I<0x9C, MRM0m, 
2028                  (ops i8mem:$dst),
2029                  "setl $dst",
2030                  [(store (X86setcc X86_COND_L), addr:$dst)]>,
2031                TB;                        // [mem8] = <  signed
2032 def SETGEr   : I<0x9D, MRM0r, 
2033                  (ops R8   :$dst),
2034                  "setge $dst",
2035                  [(set R8:$dst, (X86setcc X86_COND_GE))]>,
2036                TB;                        // R8 = >= signed
2037 def SETGEm   : I<0x9D, MRM0m, 
2038                  (ops i8mem:$dst),
2039                  "setge $dst",
2040                  [(store (X86setcc X86_COND_GE), addr:$dst)]>,
2041                TB;                        // [mem8] = >= signed
2042 def SETLEr   : I<0x9E, MRM0r, 
2043                  (ops R8   :$dst),
2044                  "setle $dst",
2045                  [(set R8:$dst, (X86setcc X86_COND_LE))]>,
2046                TB;                        // R8 = <= signed
2047 def SETLEm   : I<0x9E, MRM0m, 
2048                  (ops i8mem:$dst),
2049                  "setle $dst",
2050                  [(store (X86setcc X86_COND_LE), addr:$dst)]>,
2051                TB;                        // [mem8] = <= signed
2052 def SETGr    : I<0x9F, MRM0r, 
2053                  (ops R8   :$dst),
2054                  "setg $dst",
2055                  [(set R8:$dst, (X86setcc X86_COND_G))]>,
2056                TB;                        // R8 = >  signed
2057 def SETGm    : I<0x9F, MRM0m, 
2058                  (ops i8mem:$dst),
2059                  "setg $dst",
2060                  [(store (X86setcc X86_COND_G), addr:$dst)]>,
2061                TB;                        // [mem8] = >  signed
2062
2063 def SETBr    : I<0x92, MRM0r,
2064                  (ops R8   :$dst),
2065                  "setb $dst",
2066                  [(set R8:$dst, (X86setcc X86_COND_B))]>,
2067                TB;                        // R8 = <  unsign
2068 def SETBm    : I<0x92, MRM0m,
2069                  (ops i8mem:$dst),
2070                  "setb $dst",
2071                  [(store (X86setcc X86_COND_B), addr:$dst)]>,
2072                TB;                        // [mem8] = <  unsign
2073 def SETAEr   : I<0x93, MRM0r, 
2074                  (ops R8   :$dst),
2075                  "setae $dst",
2076                  [(set R8:$dst, (X86setcc X86_COND_AE))]>,
2077                TB;                        // R8 = >= unsign
2078 def SETAEm   : I<0x93, MRM0m, 
2079                  (ops i8mem:$dst),
2080                  "setae $dst",
2081                  [(store (X86setcc X86_COND_AE), addr:$dst)]>,
2082                TB;                        // [mem8] = >= unsign
2083 def SETBEr   : I<0x96, MRM0r, 
2084                  (ops R8   :$dst),
2085                  "setbe $dst",
2086                  [(set R8:$dst, (X86setcc X86_COND_BE))]>,
2087                TB;                        // R8 = <= unsign
2088 def SETBEm   : I<0x96, MRM0m, 
2089                  (ops i8mem:$dst),
2090                  "setbe $dst",
2091                  [(store (X86setcc X86_COND_BE), addr:$dst)]>,
2092                TB;                        // [mem8] = <= unsign
2093 def SETAr    : I<0x97, MRM0r, 
2094                  (ops R8   :$dst),
2095                  "seta $dst",
2096                  [(set R8:$dst, (X86setcc X86_COND_A))]>,
2097                TB;                        // R8 = >  signed
2098 def SETAm    : I<0x97, MRM0m, 
2099                  (ops i8mem:$dst),
2100                  "seta $dst",
2101                  [(store (X86setcc X86_COND_A), addr:$dst)]>,
2102                TB;                        // [mem8] = >  signed
2103
2104 def SETSr    : I<0x98, MRM0r, 
2105                  (ops R8   :$dst),
2106                  "sets $dst",
2107                  [(set R8:$dst, (X86setcc X86_COND_S))]>,
2108                TB;                        // R8 = <sign bit>
2109 def SETSm    : I<0x98, MRM0m, 
2110                  (ops i8mem:$dst),
2111                  "sets $dst",
2112                  [(store (X86setcc X86_COND_S), addr:$dst)]>,
2113                TB;                        // [mem8] = <sign bit>
2114 def SETNSr   : I<0x99, MRM0r, 
2115                  (ops R8   :$dst),
2116                  "setns $dst",
2117                  [(set R8:$dst, (X86setcc X86_COND_NS))]>,
2118                TB;                        // R8 = !<sign bit>
2119 def SETNSm   : I<0x99, MRM0m, 
2120                  (ops i8mem:$dst),
2121                  "setns $dst",
2122                  [(store (X86setcc X86_COND_NS), addr:$dst)]>,
2123                TB;                        // [mem8] = !<sign bit>
2124 def SETPr    : I<0x9A, MRM0r, 
2125                  (ops R8   :$dst),
2126                  "setp $dst",
2127                  [(set R8:$dst, (X86setcc X86_COND_P))]>,
2128                TB;                        // R8 = parity
2129 def SETPm    : I<0x9A, MRM0m, 
2130                  (ops i8mem:$dst),
2131                  "setp $dst",
2132                  [(store (X86setcc X86_COND_P), addr:$dst)]>,
2133                TB;                        // [mem8] = parity
2134 def SETNPr   : I<0x9B, MRM0r, 
2135                  (ops R8   :$dst),
2136                  "setnp $dst",
2137                  [(set R8:$dst, (X86setcc X86_COND_NP))]>,
2138                TB;                        // R8 = not parity
2139 def SETNPm   : I<0x9B, MRM0m, 
2140                  (ops i8mem:$dst),
2141                  "setnp $dst",
2142                  [(store (X86setcc X86_COND_NP), addr:$dst)]>,
2143                TB;                        // [mem8] = not parity
2144
2145 // Integer comparisons
2146 def CMP8rr  : I<0x38, MRMDestReg,
2147                 (ops R8 :$src1, R8 :$src2),
2148                 "cmp{b} {$src2, $src1|$src1, $src2}",
2149                 [(X86cmp R8:$src1, R8:$src2)]>;
2150 def CMP16rr : I<0x39, MRMDestReg,
2151                 (ops R16:$src1, R16:$src2),
2152                 "cmp{w} {$src2, $src1|$src1, $src2}",
2153                 [(X86cmp R16:$src1, R16:$src2)]>, OpSize;
2154 def CMP32rr : I<0x39, MRMDestReg,
2155                 (ops R32:$src1, R32:$src2),
2156                 "cmp{l} {$src2, $src1|$src1, $src2}",
2157                 [(X86cmp R32:$src1, R32:$src2)]>;
2158 def CMP8mr  : I<0x38, MRMDestMem,
2159                 (ops i8mem :$src1, R8 :$src2),
2160                 "cmp{b} {$src2, $src1|$src1, $src2}",
2161                 [(X86cmp (loadi8 addr:$src1), R8:$src2)]>;
2162 def CMP16mr : I<0x39, MRMDestMem,
2163                 (ops i16mem:$src1, R16:$src2),
2164                 "cmp{w} {$src2, $src1|$src1, $src2}",
2165                 [(X86cmp (loadi16 addr:$src1), R16:$src2)]>, OpSize;
2166 def CMP32mr : I<0x39, MRMDestMem,
2167                 (ops i32mem:$src1, R32:$src2),
2168                 "cmp{l} {$src2, $src1|$src1, $src2}",
2169                 [(X86cmp (loadi32 addr:$src1), R32:$src2)]>;
2170 def CMP8rm  : I<0x3A, MRMSrcMem,
2171                 (ops R8 :$src1, i8mem :$src2),
2172                 "cmp{b} {$src2, $src1|$src1, $src2}",
2173                 [(X86cmp R8:$src1, (loadi8 addr:$src2))]>;
2174 def CMP16rm : I<0x3B, MRMSrcMem,
2175                 (ops R16:$src1, i16mem:$src2),
2176                 "cmp{w} {$src2, $src1|$src1, $src2}",
2177                 [(X86cmp R16:$src1, (loadi16 addr:$src2))]>, OpSize;
2178 def CMP32rm : I<0x3B, MRMSrcMem,
2179                 (ops R32:$src1, i32mem:$src2),
2180                 "cmp{l} {$src2, $src1|$src1, $src2}",
2181                 [(X86cmp R32:$src1, (loadi32 addr:$src2))]>;
2182 def CMP8ri  : Ii8<0x80, MRM7r,
2183                   (ops R8:$src1, i8imm:$src2),
2184                   "cmp{b} {$src2, $src1|$src1, $src2}",
2185                   [(X86cmp R8:$src1, imm:$src2)]>;
2186 def CMP16ri : Ii16<0x81, MRM7r,
2187                    (ops R16:$src1, i16imm:$src2),
2188                    "cmp{w} {$src2, $src1|$src1, $src2}",
2189                    [(X86cmp R16:$src1, imm:$src2)]>, OpSize;
2190 def CMP32ri : Ii32<0x81, MRM7r,
2191                    (ops R32:$src1, i32imm:$src2),
2192                    "cmp{l} {$src2, $src1|$src1, $src2}",
2193                    [(X86cmp R32:$src1, imm:$src2)]>;
2194 def CMP8mi  : Ii8 <0x80, MRM7m,
2195                    (ops i8mem :$src1, i8imm :$src2),
2196                    "cmp{b} {$src2, $src1|$src1, $src2}",
2197                    [(X86cmp (loadi8 addr:$src1), imm:$src2)]>;
2198 def CMP16mi : Ii16<0x81, MRM7m,
2199                    (ops i16mem:$src1, i16imm:$src2),
2200                    "cmp{w} {$src2, $src1|$src1, $src2}",
2201                    [(X86cmp (loadi16 addr:$src1), imm:$src2)]>, OpSize;
2202 def CMP32mi : Ii32<0x81, MRM7m,
2203                    (ops i32mem:$src1, i32imm:$src2),
2204                    "cmp{l} {$src2, $src1|$src1, $src2}",
2205                    [(X86cmp (loadi32 addr:$src1), imm:$src2)]>;
2206 def CMP16ri8 : Ii8<0x83, MRM7r,
2207                    (ops R16:$src1, i16i8imm:$src2),
2208                    "cmp{w} {$src2, $src1|$src1, $src2}",
2209                    [(X86cmp R16:$src1, i16immSExt8:$src2)]>, OpSize;
2210 def CMP16mi8 : Ii8<0x83, MRM7m,
2211                    (ops i16mem:$src1, i16i8imm:$src2),
2212                    "cmp{w} {$src2, $src1|$src1, $src2}",
2213                    [(X86cmp (loadi16 addr:$src1), i16immSExt8:$src2)]>, OpSize;
2214 def CMP32mi8 : Ii8<0x83, MRM7m,
2215                    (ops i32mem:$src1, i32i8imm:$src2),
2216                    "cmp{l} {$src2, $src1|$src1, $src2}",
2217                    [(X86cmp (loadi32 addr:$src1), i32immSExt8:$src2)]>;
2218 def CMP32ri8 : Ii8<0x83, MRM7r,
2219                    (ops R32:$src1, i32i8imm:$src2),
2220                    "cmp{l} {$src2, $src1|$src1, $src2}",
2221                    [(X86cmp R32:$src1, i32immSExt8:$src2)]>;
2222
2223 // Sign/Zero extenders
2224 def MOVSX16rr8 : I<0xBE, MRMSrcReg, (ops R16:$dst, R8 :$src),
2225                    "movs{bw|x} {$src, $dst|$dst, $src}",
2226                    [(set R16:$dst, (sext R8:$src))]>, TB, OpSize;
2227 def MOVSX16rm8 : I<0xBE, MRMSrcMem, (ops R16:$dst, i8mem :$src),
2228                    "movs{bw|x} {$src, $dst|$dst, $src}",
2229                    [(set R16:$dst, (sextloadi16i8 addr:$src))]>, TB, OpSize;
2230 def MOVSX32rr8 : I<0xBE, MRMSrcReg, (ops R32:$dst, R8 :$src),
2231                    "movs{bl|x} {$src, $dst|$dst, $src}",
2232                    [(set R32:$dst, (sext R8:$src))]>, TB;
2233 def MOVSX32rm8 : I<0xBE, MRMSrcMem, (ops R32:$dst, i8mem :$src),
2234                    "movs{bl|x} {$src, $dst|$dst, $src}",
2235                    [(set R32:$dst, (sextloadi32i8 addr:$src))]>, TB;
2236 def MOVSX32rr16: I<0xBF, MRMSrcReg, (ops R32:$dst, R16:$src),
2237                    "movs{wl|x} {$src, $dst|$dst, $src}",
2238                    [(set R32:$dst, (sext R16:$src))]>, TB;
2239 def MOVSX32rm16: I<0xBF, MRMSrcMem, (ops R32:$dst, i16mem:$src),
2240                    "movs{wl|x} {$src, $dst|$dst, $src}",
2241                    [(set R32:$dst, (sextloadi32i16 addr:$src))]>, TB;
2242
2243 def MOVZX16rr8 : I<0xB6, MRMSrcReg, (ops R16:$dst, R8 :$src),
2244                    "movz{bw|x} {$src, $dst|$dst, $src}",
2245                    [(set R16:$dst, (zext R8:$src))]>, TB, OpSize;
2246 def MOVZX16rm8 : I<0xB6, MRMSrcMem, (ops R16:$dst, i8mem :$src),
2247                    "movz{bw|x} {$src, $dst|$dst, $src}",
2248                    [(set R16:$dst, (zextloadi16i8 addr:$src))]>, TB, OpSize;
2249 def MOVZX32rr8 : I<0xB6, MRMSrcReg, (ops R32:$dst, R8 :$src),
2250                    "movz{bl|x} {$src, $dst|$dst, $src}",
2251                    [(set R32:$dst, (zext R8:$src))]>, TB;
2252 def MOVZX32rm8 : I<0xB6, MRMSrcMem, (ops R32:$dst, i8mem :$src),
2253                    "movz{bl|x} {$src, $dst|$dst, $src}",
2254                    [(set R32:$dst, (zextloadi32i8 addr:$src))]>, TB;
2255 def MOVZX32rr16: I<0xB7, MRMSrcReg, (ops R32:$dst, R16:$src),
2256                    "movz{wl|x} {$src, $dst|$dst, $src}",
2257                    [(set R32:$dst, (zext R16:$src))]>, TB;
2258 def MOVZX32rm16: I<0xB7, MRMSrcMem, (ops R32:$dst, i16mem:$src),
2259                    "movz{wl|x} {$src, $dst|$dst, $src}",
2260                    [(set R32:$dst, (zextloadi32i16 addr:$src))]>, TB;
2261
2262 //===----------------------------------------------------------------------===//
2263 // Miscellaneous Instructions
2264 //===----------------------------------------------------------------------===//
2265
2266 def RDTSC : I<0x31, RawFrm, (ops), "rdtsc", [(X86rdtsc)]>,
2267             TB, Imp<[],[EAX,EDX]>;
2268
2269 //===----------------------------------------------------------------------===//
2270 // Alias Instructions
2271 //===----------------------------------------------------------------------===//
2272
2273 // Alias instructions that map movr0 to xor.
2274 // FIXME: remove when we can teach regalloc that xor reg, reg is ok.
2275 def MOV8r0   : I<0x30, MRMInitReg, (ops R8 :$dst),
2276                  "xor{b} $dst, $dst",
2277                  [(set R8:$dst, 0)]>;
2278 def MOV16r0  : I<0x31, MRMInitReg,  (ops R16:$dst), 
2279                  "xor{w} $dst, $dst",
2280                  [(set R16:$dst, 0)]>, OpSize;
2281 def MOV32r0  : I<0x31, MRMInitReg,  (ops R32:$dst), 
2282                  "xor{l} $dst, $dst",
2283                  [(set R32:$dst, 0)]>;
2284
2285 //===----------------------------------------------------------------------===//
2286 // DWARF Pseudo Instructions
2287 //
2288
2289 def DWARF_LOC   : I<0, Pseudo, (ops i32imm:$line, i32imm:$col, i32imm:$file),
2290                     "; .loc $file, $line, $col",
2291                     [(dwarf_loc (i32 imm:$line), (i32 imm:$col),
2292                       (i32 imm:$file))]>;
2293
2294 def DWARF_LABEL : I<0, Pseudo, (ops i32imm:$id),
2295                    "\nLdebug_loc${id:debug}:",
2296                    [(dwarf_label (i32 imm:$id))]>;
2297
2298 //===----------------------------------------------------------------------===//
2299 // Non-Instruction Patterns
2300 //===----------------------------------------------------------------------===//
2301
2302 // ConstantPool GlobalAddress, ExternalSymbol
2303 def : Pat<(i32 (X86Wrapper tconstpool  :$dst)), (MOV32ri tconstpool  :$dst)>;
2304 def : Pat<(i32 (X86Wrapper tglobaladdr :$dst)), (MOV32ri tglobaladdr :$dst)>;
2305 def : Pat<(i32 (X86Wrapper texternalsym:$dst)), (MOV32ri texternalsym:$dst)>;
2306
2307 def : Pat<(add R32:$src1, (X86Wrapper tconstpool:$src2)),
2308           (ADD32ri R32:$src1, tconstpool:$src2)>;
2309 def : Pat<(add R32:$src1, (X86Wrapper tglobaladdr :$src2)),
2310           (ADD32ri R32:$src1, tglobaladdr:$src2)>;
2311 def : Pat<(add R32:$src1, (X86Wrapper texternalsym:$src2)),
2312           (ADD32ri R32:$src1, texternalsym:$src2)>;
2313
2314 def : Pat<(store (X86Wrapper tconstpool:$src), addr:$dst),
2315           (MOV32mi addr:$dst, tconstpool:$src)>;
2316 def : Pat<(store (X86Wrapper tglobaladdr:$src), addr:$dst),
2317           (MOV32mi addr:$dst, tglobaladdr:$src)>;
2318 def : Pat<(store (X86Wrapper texternalsym:$src), addr:$dst),
2319           (MOV32mi addr:$dst, texternalsym:$src)>;
2320
2321 // Calls
2322 def : Pat<(X86call tglobaladdr:$dst),
2323           (CALLpcrel32 tglobaladdr:$dst)>;
2324 def : Pat<(X86call texternalsym:$dst),
2325           (CALLpcrel32 texternalsym:$dst)>;
2326
2327 // X86 specific add which produces a flag.
2328 def : Pat<(addc R32:$src1, R32:$src2),
2329           (ADD32rr R32:$src1, R32:$src2)>;
2330 def : Pat<(addc R32:$src1, (load addr:$src2)),
2331           (ADD32rm R32:$src1, addr:$src2)>;
2332 def : Pat<(addc R32:$src1, imm:$src2),
2333           (ADD32ri R32:$src1, imm:$src2)>;
2334 def : Pat<(addc R32:$src1, i32immSExt8:$src2),
2335           (ADD32ri8 R32:$src1, i32immSExt8:$src2)>;
2336
2337 def : Pat<(subc R32:$src1, R32:$src2),
2338           (SUB32rr R32:$src1, R32:$src2)>;
2339 def : Pat<(subc R32:$src1, (load addr:$src2)),
2340           (SUB32rm R32:$src1, addr:$src2)>;
2341 def : Pat<(subc R32:$src1, imm:$src2),
2342           (SUB32ri R32:$src1, imm:$src2)>;
2343 def : Pat<(subc R32:$src1, i32immSExt8:$src2),
2344           (SUB32ri8 R32:$src1, i32immSExt8:$src2)>;
2345
2346 def : Pat<(truncstore (i8 imm:$src), addr:$dst, i1), 
2347           (MOV8mi addr:$dst, imm:$src)>;
2348 def : Pat<(truncstore R8:$src, addr:$dst, i1), 
2349           (MOV8mr addr:$dst, R8:$src)>;
2350
2351 // {s|z}extload bool -> {s|z}extload byte
2352 def : Pat<(sextloadi16i1 addr:$src), (MOVSX16rm8 addr:$src)>;
2353 def : Pat<(sextloadi32i1 addr:$src), (MOVSX32rm8 addr:$src)>;
2354 def : Pat<(zextloadi8i1  addr:$src), (MOV8rm     addr:$src)>;
2355 def : Pat<(zextloadi16i1 addr:$src), (MOVZX16rm8 addr:$src)>;
2356 def : Pat<(zextloadi32i1 addr:$src), (MOVZX32rm8 addr:$src)>;
2357
2358 // extload bool -> extload byte
2359 def : Pat<(extloadi8i1 addr:$src), (MOV8rm addr:$src)>;
2360
2361 // anyext -> zext
2362 def : Pat<(i16 (anyext R8 :$src)), (MOVZX16rr8  R8 :$src)>;
2363 def : Pat<(i32 (anyext R8 :$src)), (MOVZX32rr8  R8 :$src)>;
2364 def : Pat<(i32 (anyext R16:$src)), (MOVZX32rr16 R16:$src)>;
2365
2366 //===----------------------------------------------------------------------===//
2367 // Some peepholes
2368 //===----------------------------------------------------------------------===//
2369
2370 // (shl x, 1) ==> (add x, x)
2371 def : Pat<(shl R8 :$src1, (i8 1)), (ADD8rr  R8 :$src1, R8 :$src1)>;
2372 def : Pat<(shl R16:$src1, (i8 1)), (ADD16rr R16:$src1, R16:$src1)>;
2373 def : Pat<(shl R32:$src1, (i8 1)), (ADD32rr R32:$src1, R32:$src1)>;
2374
2375 // (or (x >> c) | (y << (32 - c))) ==> (shrd32 x, y, c)
2376 def : Pat<(or (srl R32:$src1, CL:$amt),
2377               (shl R32:$src2, (sub 32, CL:$amt))),
2378           (SHRD32rrCL R32:$src1, R32:$src2)>;
2379
2380 def : Pat<(store (or (srl (loadi32 addr:$dst), CL:$amt),
2381                      (shl R32:$src2, (sub 32, CL:$amt))), addr:$dst),
2382           (SHRD32mrCL addr:$dst, R32:$src2)>;
2383
2384 // (or (x << c) | (y >> (32 - c))) ==> (shld32 x, y, c)
2385 def : Pat<(or (shl R32:$src1, CL:$amt),
2386               (srl R32:$src2, (sub 32, CL:$amt))),
2387           (SHLD32rrCL R32:$src1, R32:$src2)>;
2388
2389 def : Pat<(store (or (shl (loadi32 addr:$dst), CL:$amt),
2390                      (srl R32:$src2, (sub 32, CL:$amt))), addr:$dst),
2391           (SHLD32mrCL addr:$dst, R32:$src2)>;
2392
2393 // (or (x >> c) | (y << (16 - c))) ==> (shrd16 x, y, c)
2394 def : Pat<(or (srl R16:$src1, CL:$amt),
2395               (shl R16:$src2, (sub 16, CL:$amt))),
2396           (SHRD16rrCL R16:$src1, R16:$src2)>;
2397
2398 def : Pat<(store (or (srl (loadi16 addr:$dst), CL:$amt),
2399                      (shl R16:$src2, (sub 16, CL:$amt))), addr:$dst),
2400           (SHRD16mrCL addr:$dst, R16:$src2)>;
2401
2402 // (or (x << c) | (y >> (16 - c))) ==> (shld16 x, y, c)
2403 def : Pat<(or (shl R16:$src1, CL:$amt),
2404               (srl R16:$src2, (sub 16, CL:$amt))),
2405           (SHLD16rrCL R16:$src1, R16:$src2)>;
2406
2407 def : Pat<(store (or (shl (loadi16 addr:$dst), CL:$amt),
2408                      (srl R16:$src2, (sub 16, CL:$amt))), addr:$dst),
2409           (SHLD16mrCL addr:$dst, R16:$src2)>;
2410
2411
2412 //===----------------------------------------------------------------------===//
2413 // Floating Point Stack Support
2414 //===----------------------------------------------------------------------===//
2415
2416 include "X86InstrFPStack.td"
2417
2418 //===----------------------------------------------------------------------===//
2419 // MMX and XMM Packed Integer support (requires MMX, SSE, and SSE2)
2420 //===----------------------------------------------------------------------===//
2421
2422 include "X86InstrMMX.td"
2423
2424 //===----------------------------------------------------------------------===//
2425 // XMM Floating point support (requires SSE / SSE2)
2426 //===----------------------------------------------------------------------===//
2427
2428 include "X86InstrSSE.td"