10b57cec5SDimitry Andric//===-- X86InstrShiftRotate.td - Shift and Rotate Instrs ---*- tablegen -*-===// 20b57cec5SDimitry Andric// 30b57cec5SDimitry Andric// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 40b57cec5SDimitry Andric// See https://llvm.org/LICENSE.txt for license information. 50b57cec5SDimitry Andric// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 60b57cec5SDimitry Andric// 70b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 80b57cec5SDimitry Andric// 90b57cec5SDimitry Andric// This file describes the shift and rotate instructions. 100b57cec5SDimitry Andric// 110b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 120b57cec5SDimitry Andric 130b57cec5SDimitry Andric// FIXME: Someone needs to smear multipattern goodness all over this file. 140b57cec5SDimitry Andric 150b57cec5SDimitry Andriclet Defs = [EFLAGS] in { 160b57cec5SDimitry Andric 170b57cec5SDimitry Andriclet Constraints = "$src1 = $dst", SchedRW = [WriteShift] in { 180b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteShiftCL] in { 190b57cec5SDimitry Andricdef SHL8rCL : I<0xD2, MRM4r, (outs GR8 :$dst), (ins GR8 :$src1), 200b57cec5SDimitry Andric "shl{b}\t{%cl, $dst|$dst, cl}", 210b57cec5SDimitry Andric [(set GR8:$dst, (shl GR8:$src1, CL))]>; 220b57cec5SDimitry Andricdef SHL16rCL : I<0xD3, MRM4r, (outs GR16:$dst), (ins GR16:$src1), 230b57cec5SDimitry Andric "shl{w}\t{%cl, $dst|$dst, cl}", 240b57cec5SDimitry Andric [(set GR16:$dst, (shl GR16:$src1, CL))]>, OpSize16; 250b57cec5SDimitry Andricdef SHL32rCL : I<0xD3, MRM4r, (outs GR32:$dst), (ins GR32:$src1), 260b57cec5SDimitry Andric "shl{l}\t{%cl, $dst|$dst, cl}", 270b57cec5SDimitry Andric [(set GR32:$dst, (shl GR32:$src1, CL))]>, OpSize32; 280b57cec5SDimitry Andricdef SHL64rCL : RI<0xD3, MRM4r, (outs GR64:$dst), (ins GR64:$src1), 290b57cec5SDimitry Andric "shl{q}\t{%cl, $dst|$dst, cl}", 300b57cec5SDimitry Andric [(set GR64:$dst, (shl GR64:$src1, CL))]>; 310b57cec5SDimitry Andric} // Uses = [CL], SchedRW 320b57cec5SDimitry Andric 330b57cec5SDimitry Andriclet isConvertibleToThreeAddress = 1 in { // Can transform into LEA. 340b57cec5SDimitry Andricdef SHL8ri : Ii8<0xC0, MRM4r, (outs GR8 :$dst), (ins GR8 :$src1, u8imm:$src2), 350b57cec5SDimitry Andric "shl{b}\t{$src2, $dst|$dst, $src2}", 360b57cec5SDimitry Andric [(set GR8:$dst, (shl GR8:$src1, (i8 imm:$src2)))]>; 370b57cec5SDimitry Andric 380b57cec5SDimitry Andricdef SHL16ri : Ii8<0xC1, MRM4r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$src2), 390b57cec5SDimitry Andric "shl{w}\t{$src2, $dst|$dst, $src2}", 400b57cec5SDimitry Andric [(set GR16:$dst, (shl GR16:$src1, (i8 imm:$src2)))]>, 410b57cec5SDimitry Andric OpSize16; 420b57cec5SDimitry Andricdef SHL32ri : Ii8<0xC1, MRM4r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$src2), 430b57cec5SDimitry Andric "shl{l}\t{$src2, $dst|$dst, $src2}", 440b57cec5SDimitry Andric [(set GR32:$dst, (shl GR32:$src1, (i8 imm:$src2)))]>, 450b57cec5SDimitry Andric OpSize32; 460b57cec5SDimitry Andricdef SHL64ri : RIi8<0xC1, MRM4r, (outs GR64:$dst), 470b57cec5SDimitry Andric (ins GR64:$src1, u8imm:$src2), 480b57cec5SDimitry Andric "shl{q}\t{$src2, $dst|$dst, $src2}", 490b57cec5SDimitry Andric [(set GR64:$dst, (shl GR64:$src1, (i8 imm:$src2)))]>; 500b57cec5SDimitry Andric} // isConvertibleToThreeAddress = 1 510b57cec5SDimitry Andric 520b57cec5SDimitry Andric// NOTE: We don't include patterns for shifts of a register by one, because 530b57cec5SDimitry Andric// 'add reg,reg' is cheaper (and we have a Pat pattern for shift-by-one). 540b57cec5SDimitry Andriclet hasSideEffects = 0 in { 550b57cec5SDimitry Andricdef SHL8r1 : I<0xD0, MRM4r, (outs GR8:$dst), (ins GR8:$src1), 560b57cec5SDimitry Andric "shl{b}\t$dst", []>; 570b57cec5SDimitry Andricdef SHL16r1 : I<0xD1, MRM4r, (outs GR16:$dst), (ins GR16:$src1), 580b57cec5SDimitry Andric "shl{w}\t$dst", []>, OpSize16; 590b57cec5SDimitry Andricdef SHL32r1 : I<0xD1, MRM4r, (outs GR32:$dst), (ins GR32:$src1), 600b57cec5SDimitry Andric "shl{l}\t$dst", []>, OpSize32; 610b57cec5SDimitry Andricdef SHL64r1 : RI<0xD1, MRM4r, (outs GR64:$dst), (ins GR64:$src1), 620b57cec5SDimitry Andric "shl{q}\t$dst", []>; 630b57cec5SDimitry Andric} // hasSideEffects = 0 640b57cec5SDimitry Andric} // Constraints = "$src = $dst", SchedRW 650b57cec5SDimitry Andric 660b57cec5SDimitry Andric// FIXME: Why do we need an explicit "Uses = [CL]" when the instr has a pattern 670b57cec5SDimitry Andric// using CL? 680b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteShiftCLLd, WriteRMW] in { 690b57cec5SDimitry Andricdef SHL8mCL : I<0xD2, MRM4m, (outs), (ins i8mem :$dst), 700b57cec5SDimitry Andric "shl{b}\t{%cl, $dst|$dst, cl}", 710b57cec5SDimitry Andric [(store (shl (loadi8 addr:$dst), CL), addr:$dst)]>; 720b57cec5SDimitry Andricdef SHL16mCL : I<0xD3, MRM4m, (outs), (ins i16mem:$dst), 730b57cec5SDimitry Andric "shl{w}\t{%cl, $dst|$dst, cl}", 740b57cec5SDimitry Andric [(store (shl (loadi16 addr:$dst), CL), addr:$dst)]>, 750b57cec5SDimitry Andric OpSize16; 760b57cec5SDimitry Andricdef SHL32mCL : I<0xD3, MRM4m, (outs), (ins i32mem:$dst), 770b57cec5SDimitry Andric "shl{l}\t{%cl, $dst|$dst, cl}", 780b57cec5SDimitry Andric [(store (shl (loadi32 addr:$dst), CL), addr:$dst)]>, 790b57cec5SDimitry Andric OpSize32; 800b57cec5SDimitry Andricdef SHL64mCL : RI<0xD3, MRM4m, (outs), (ins i64mem:$dst), 810b57cec5SDimitry Andric "shl{q}\t{%cl, $dst|$dst, cl}", 820b57cec5SDimitry Andric [(store (shl (loadi64 addr:$dst), CL), addr:$dst)]>, 830b57cec5SDimitry Andric Requires<[In64BitMode]>; 840b57cec5SDimitry Andric} 850b57cec5SDimitry Andric 860b57cec5SDimitry Andriclet SchedRW = [WriteShiftLd, WriteRMW] in { 870b57cec5SDimitry Andricdef SHL8mi : Ii8<0xC0, MRM4m, (outs), (ins i8mem :$dst, u8imm:$src), 880b57cec5SDimitry Andric "shl{b}\t{$src, $dst|$dst, $src}", 890b57cec5SDimitry Andric [(store (shl (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>; 900b57cec5SDimitry Andricdef SHL16mi : Ii8<0xC1, MRM4m, (outs), (ins i16mem:$dst, u8imm:$src), 910b57cec5SDimitry Andric "shl{w}\t{$src, $dst|$dst, $src}", 920b57cec5SDimitry Andric [(store (shl (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 930b57cec5SDimitry Andric OpSize16; 940b57cec5SDimitry Andricdef SHL32mi : Ii8<0xC1, MRM4m, (outs), (ins i32mem:$dst, u8imm:$src), 950b57cec5SDimitry Andric "shl{l}\t{$src, $dst|$dst, $src}", 960b57cec5SDimitry Andric [(store (shl (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 970b57cec5SDimitry Andric OpSize32; 980b57cec5SDimitry Andricdef SHL64mi : RIi8<0xC1, MRM4m, (outs), (ins i64mem:$dst, u8imm:$src), 990b57cec5SDimitry Andric "shl{q}\t{$src, $dst|$dst, $src}", 1000b57cec5SDimitry Andric [(store (shl (loadi64 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 1010b57cec5SDimitry Andric Requires<[In64BitMode]>; 1020b57cec5SDimitry Andric 1030b57cec5SDimitry Andric// Shift by 1 1040b57cec5SDimitry Andricdef SHL8m1 : I<0xD0, MRM4m, (outs), (ins i8mem :$dst), 1050b57cec5SDimitry Andric "shl{b}\t$dst", 1060b57cec5SDimitry Andric [(store (shl (loadi8 addr:$dst), (i8 1)), addr:$dst)]>; 1070b57cec5SDimitry Andricdef SHL16m1 : I<0xD1, MRM4m, (outs), (ins i16mem:$dst), 1080b57cec5SDimitry Andric "shl{w}\t$dst", 1090b57cec5SDimitry Andric [(store (shl (loadi16 addr:$dst), (i8 1)), addr:$dst)]>, 1100b57cec5SDimitry Andric OpSize16; 1110b57cec5SDimitry Andricdef SHL32m1 : I<0xD1, MRM4m, (outs), (ins i32mem:$dst), 1120b57cec5SDimitry Andric "shl{l}\t$dst", 1130b57cec5SDimitry Andric [(store (shl (loadi32 addr:$dst), (i8 1)), addr:$dst)]>, 1140b57cec5SDimitry Andric OpSize32; 1150b57cec5SDimitry Andricdef SHL64m1 : RI<0xD1, MRM4m, (outs), (ins i64mem:$dst), 1160b57cec5SDimitry Andric "shl{q}\t$dst", 1170b57cec5SDimitry Andric [(store (shl (loadi64 addr:$dst), (i8 1)), addr:$dst)]>, 1180b57cec5SDimitry Andric Requires<[In64BitMode]>; 1190b57cec5SDimitry Andric} // SchedRW 1200b57cec5SDimitry Andric 1210b57cec5SDimitry Andriclet Constraints = "$src1 = $dst", SchedRW = [WriteShift] in { 1220b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteShiftCL] in { 1230b57cec5SDimitry Andricdef SHR8rCL : I<0xD2, MRM5r, (outs GR8 :$dst), (ins GR8 :$src1), 1240b57cec5SDimitry Andric "shr{b}\t{%cl, $dst|$dst, cl}", 1250b57cec5SDimitry Andric [(set GR8:$dst, (srl GR8:$src1, CL))]>; 1260b57cec5SDimitry Andricdef SHR16rCL : I<0xD3, MRM5r, (outs GR16:$dst), (ins GR16:$src1), 1270b57cec5SDimitry Andric "shr{w}\t{%cl, $dst|$dst, cl}", 1280b57cec5SDimitry Andric [(set GR16:$dst, (srl GR16:$src1, CL))]>, OpSize16; 1290b57cec5SDimitry Andricdef SHR32rCL : I<0xD3, MRM5r, (outs GR32:$dst), (ins GR32:$src1), 1300b57cec5SDimitry Andric "shr{l}\t{%cl, $dst|$dst, cl}", 1310b57cec5SDimitry Andric [(set GR32:$dst, (srl GR32:$src1, CL))]>, OpSize32; 1320b57cec5SDimitry Andricdef SHR64rCL : RI<0xD3, MRM5r, (outs GR64:$dst), (ins GR64:$src1), 1330b57cec5SDimitry Andric "shr{q}\t{%cl, $dst|$dst, cl}", 1340b57cec5SDimitry Andric [(set GR64:$dst, (srl GR64:$src1, CL))]>; 1350b57cec5SDimitry Andric} 1360b57cec5SDimitry Andric 1370b57cec5SDimitry Andricdef SHR8ri : Ii8<0xC0, MRM5r, (outs GR8:$dst), (ins GR8:$src1, u8imm:$src2), 1380b57cec5SDimitry Andric "shr{b}\t{$src2, $dst|$dst, $src2}", 1390b57cec5SDimitry Andric [(set GR8:$dst, (srl GR8:$src1, (i8 imm:$src2)))]>; 1400b57cec5SDimitry Andricdef SHR16ri : Ii8<0xC1, MRM5r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$src2), 1410b57cec5SDimitry Andric "shr{w}\t{$src2, $dst|$dst, $src2}", 1420b57cec5SDimitry Andric [(set GR16:$dst, (srl GR16:$src1, (i8 imm:$src2)))]>, 1430b57cec5SDimitry Andric OpSize16; 1440b57cec5SDimitry Andricdef SHR32ri : Ii8<0xC1, MRM5r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$src2), 1450b57cec5SDimitry Andric "shr{l}\t{$src2, $dst|$dst, $src2}", 1460b57cec5SDimitry Andric [(set GR32:$dst, (srl GR32:$src1, (i8 imm:$src2)))]>, 1470b57cec5SDimitry Andric OpSize32; 1480b57cec5SDimitry Andricdef SHR64ri : RIi8<0xC1, MRM5r, (outs GR64:$dst), (ins GR64:$src1, u8imm:$src2), 1490b57cec5SDimitry Andric "shr{q}\t{$src2, $dst|$dst, $src2}", 1500b57cec5SDimitry Andric [(set GR64:$dst, (srl GR64:$src1, (i8 imm:$src2)))]>; 1510b57cec5SDimitry Andric 1520b57cec5SDimitry Andric// Shift right by 1 1530b57cec5SDimitry Andricdef SHR8r1 : I<0xD0, MRM5r, (outs GR8:$dst), (ins GR8:$src1), 1540b57cec5SDimitry Andric "shr{b}\t$dst", 1550b57cec5SDimitry Andric [(set GR8:$dst, (srl GR8:$src1, (i8 1)))]>; 1560b57cec5SDimitry Andricdef SHR16r1 : I<0xD1, MRM5r, (outs GR16:$dst), (ins GR16:$src1), 1570b57cec5SDimitry Andric "shr{w}\t$dst", 1580b57cec5SDimitry Andric [(set GR16:$dst, (srl GR16:$src1, (i8 1)))]>, OpSize16; 1590b57cec5SDimitry Andricdef SHR32r1 : I<0xD1, MRM5r, (outs GR32:$dst), (ins GR32:$src1), 1600b57cec5SDimitry Andric "shr{l}\t$dst", 1610b57cec5SDimitry Andric [(set GR32:$dst, (srl GR32:$src1, (i8 1)))]>, OpSize32; 1620b57cec5SDimitry Andricdef SHR64r1 : RI<0xD1, MRM5r, (outs GR64:$dst), (ins GR64:$src1), 1630b57cec5SDimitry Andric "shr{q}\t$dst", 1640b57cec5SDimitry Andric [(set GR64:$dst, (srl GR64:$src1, (i8 1)))]>; 1650b57cec5SDimitry Andric} // Constraints = "$src = $dst", SchedRW 1660b57cec5SDimitry Andric 1670b57cec5SDimitry Andric 1680b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteShiftCLLd, WriteRMW] in { 1690b57cec5SDimitry Andricdef SHR8mCL : I<0xD2, MRM5m, (outs), (ins i8mem :$dst), 1700b57cec5SDimitry Andric "shr{b}\t{%cl, $dst|$dst, cl}", 1710b57cec5SDimitry Andric [(store (srl (loadi8 addr:$dst), CL), addr:$dst)]>; 1720b57cec5SDimitry Andricdef SHR16mCL : I<0xD3, MRM5m, (outs), (ins i16mem:$dst), 1730b57cec5SDimitry Andric "shr{w}\t{%cl, $dst|$dst, cl}", 1740b57cec5SDimitry Andric [(store (srl (loadi16 addr:$dst), CL), addr:$dst)]>, 1750b57cec5SDimitry Andric OpSize16; 1760b57cec5SDimitry Andricdef SHR32mCL : I<0xD3, MRM5m, (outs), (ins i32mem:$dst), 1770b57cec5SDimitry Andric "shr{l}\t{%cl, $dst|$dst, cl}", 1780b57cec5SDimitry Andric [(store (srl (loadi32 addr:$dst), CL), addr:$dst)]>, 1790b57cec5SDimitry Andric OpSize32; 1800b57cec5SDimitry Andricdef SHR64mCL : RI<0xD3, MRM5m, (outs), (ins i64mem:$dst), 1810b57cec5SDimitry Andric "shr{q}\t{%cl, $dst|$dst, cl}", 1820b57cec5SDimitry Andric [(store (srl (loadi64 addr:$dst), CL), addr:$dst)]>, 1830b57cec5SDimitry Andric Requires<[In64BitMode]>; 1840b57cec5SDimitry Andric} 1850b57cec5SDimitry Andric 1860b57cec5SDimitry Andriclet SchedRW = [WriteShiftLd, WriteRMW] in { 1870b57cec5SDimitry Andricdef SHR8mi : Ii8<0xC0, MRM5m, (outs), (ins i8mem :$dst, u8imm:$src), 1880b57cec5SDimitry Andric "shr{b}\t{$src, $dst|$dst, $src}", 1890b57cec5SDimitry Andric [(store (srl (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>; 1900b57cec5SDimitry Andricdef SHR16mi : Ii8<0xC1, MRM5m, (outs), (ins i16mem:$dst, u8imm:$src), 1910b57cec5SDimitry Andric "shr{w}\t{$src, $dst|$dst, $src}", 1920b57cec5SDimitry Andric [(store (srl (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 1930b57cec5SDimitry Andric OpSize16; 1940b57cec5SDimitry Andricdef SHR32mi : Ii8<0xC1, MRM5m, (outs), (ins i32mem:$dst, u8imm:$src), 1950b57cec5SDimitry Andric "shr{l}\t{$src, $dst|$dst, $src}", 1960b57cec5SDimitry Andric [(store (srl (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 1970b57cec5SDimitry Andric OpSize32; 1980b57cec5SDimitry Andricdef SHR64mi : RIi8<0xC1, MRM5m, (outs), (ins i64mem:$dst, u8imm:$src), 1990b57cec5SDimitry Andric "shr{q}\t{$src, $dst|$dst, $src}", 2000b57cec5SDimitry Andric [(store (srl (loadi64 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 2010b57cec5SDimitry Andric Requires<[In64BitMode]>; 2020b57cec5SDimitry Andric 2030b57cec5SDimitry Andric// Shift by 1 2040b57cec5SDimitry Andricdef SHR8m1 : I<0xD0, MRM5m, (outs), (ins i8mem :$dst), 2050b57cec5SDimitry Andric "shr{b}\t$dst", 2060b57cec5SDimitry Andric [(store (srl (loadi8 addr:$dst), (i8 1)), addr:$dst)]>; 2070b57cec5SDimitry Andricdef SHR16m1 : I<0xD1, MRM5m, (outs), (ins i16mem:$dst), 2080b57cec5SDimitry Andric "shr{w}\t$dst", 2090b57cec5SDimitry Andric [(store (srl (loadi16 addr:$dst), (i8 1)), addr:$dst)]>, 2100b57cec5SDimitry Andric OpSize16; 2110b57cec5SDimitry Andricdef SHR32m1 : I<0xD1, MRM5m, (outs), (ins i32mem:$dst), 2120b57cec5SDimitry Andric "shr{l}\t$dst", 2130b57cec5SDimitry Andric [(store (srl (loadi32 addr:$dst), (i8 1)), addr:$dst)]>, 2140b57cec5SDimitry Andric OpSize32; 2150b57cec5SDimitry Andricdef SHR64m1 : RI<0xD1, MRM5m, (outs), (ins i64mem:$dst), 2160b57cec5SDimitry Andric "shr{q}\t$dst", 2170b57cec5SDimitry Andric [(store (srl (loadi64 addr:$dst), (i8 1)), addr:$dst)]>, 2180b57cec5SDimitry Andric Requires<[In64BitMode]>; 2190b57cec5SDimitry Andric} // SchedRW 2200b57cec5SDimitry Andric 2210b57cec5SDimitry Andriclet Constraints = "$src1 = $dst", SchedRW = [WriteShift] in { 2220b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteShiftCL] in { 2230b57cec5SDimitry Andricdef SAR8rCL : I<0xD2, MRM7r, (outs GR8 :$dst), (ins GR8 :$src1), 2240b57cec5SDimitry Andric "sar{b}\t{%cl, $dst|$dst, cl}", 2250b57cec5SDimitry Andric [(set GR8:$dst, (sra GR8:$src1, CL))]>; 2260b57cec5SDimitry Andricdef SAR16rCL : I<0xD3, MRM7r, (outs GR16:$dst), (ins GR16:$src1), 2270b57cec5SDimitry Andric "sar{w}\t{%cl, $dst|$dst, cl}", 2280b57cec5SDimitry Andric [(set GR16:$dst, (sra GR16:$src1, CL))]>, 2290b57cec5SDimitry Andric OpSize16; 2300b57cec5SDimitry Andricdef SAR32rCL : I<0xD3, MRM7r, (outs GR32:$dst), (ins GR32:$src1), 2310b57cec5SDimitry Andric "sar{l}\t{%cl, $dst|$dst, cl}", 2320b57cec5SDimitry Andric [(set GR32:$dst, (sra GR32:$src1, CL))]>, 2330b57cec5SDimitry Andric OpSize32; 2340b57cec5SDimitry Andricdef SAR64rCL : RI<0xD3, MRM7r, (outs GR64:$dst), (ins GR64:$src1), 2350b57cec5SDimitry Andric "sar{q}\t{%cl, $dst|$dst, cl}", 2360b57cec5SDimitry Andric [(set GR64:$dst, (sra GR64:$src1, CL))]>; 2370b57cec5SDimitry Andric} 2380b57cec5SDimitry Andric 2390b57cec5SDimitry Andricdef SAR8ri : Ii8<0xC0, MRM7r, (outs GR8 :$dst), (ins GR8 :$src1, u8imm:$src2), 2400b57cec5SDimitry Andric "sar{b}\t{$src2, $dst|$dst, $src2}", 2410b57cec5SDimitry Andric [(set GR8:$dst, (sra GR8:$src1, (i8 imm:$src2)))]>; 2420b57cec5SDimitry Andricdef SAR16ri : Ii8<0xC1, MRM7r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$src2), 2430b57cec5SDimitry Andric "sar{w}\t{$src2, $dst|$dst, $src2}", 2440b57cec5SDimitry Andric [(set GR16:$dst, (sra GR16:$src1, (i8 imm:$src2)))]>, 2450b57cec5SDimitry Andric OpSize16; 2460b57cec5SDimitry Andricdef SAR32ri : Ii8<0xC1, MRM7r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$src2), 2470b57cec5SDimitry Andric "sar{l}\t{$src2, $dst|$dst, $src2}", 2480b57cec5SDimitry Andric [(set GR32:$dst, (sra GR32:$src1, (i8 imm:$src2)))]>, 2490b57cec5SDimitry Andric OpSize32; 2500b57cec5SDimitry Andricdef SAR64ri : RIi8<0xC1, MRM7r, (outs GR64:$dst), 2510b57cec5SDimitry Andric (ins GR64:$src1, u8imm:$src2), 2520b57cec5SDimitry Andric "sar{q}\t{$src2, $dst|$dst, $src2}", 2530b57cec5SDimitry Andric [(set GR64:$dst, (sra GR64:$src1, (i8 imm:$src2)))]>; 2540b57cec5SDimitry Andric 2550b57cec5SDimitry Andric// Shift by 1 2560b57cec5SDimitry Andricdef SAR8r1 : I<0xD0, MRM7r, (outs GR8 :$dst), (ins GR8 :$src1), 2570b57cec5SDimitry Andric "sar{b}\t$dst", 2580b57cec5SDimitry Andric [(set GR8:$dst, (sra GR8:$src1, (i8 1)))]>; 2590b57cec5SDimitry Andricdef SAR16r1 : I<0xD1, MRM7r, (outs GR16:$dst), (ins GR16:$src1), 2600b57cec5SDimitry Andric "sar{w}\t$dst", 2610b57cec5SDimitry Andric [(set GR16:$dst, (sra GR16:$src1, (i8 1)))]>, OpSize16; 2620b57cec5SDimitry Andricdef SAR32r1 : I<0xD1, MRM7r, (outs GR32:$dst), (ins GR32:$src1), 2630b57cec5SDimitry Andric "sar{l}\t$dst", 2640b57cec5SDimitry Andric [(set GR32:$dst, (sra GR32:$src1, (i8 1)))]>, OpSize32; 2650b57cec5SDimitry Andricdef SAR64r1 : RI<0xD1, MRM7r, (outs GR64:$dst), (ins GR64:$src1), 2660b57cec5SDimitry Andric "sar{q}\t$dst", 2670b57cec5SDimitry Andric [(set GR64:$dst, (sra GR64:$src1, (i8 1)))]>; 2680b57cec5SDimitry Andric} // Constraints = "$src = $dst", SchedRW 2690b57cec5SDimitry Andric 2700b57cec5SDimitry Andric 2710b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteShiftCLLd, WriteRMW] in { 2720b57cec5SDimitry Andricdef SAR8mCL : I<0xD2, MRM7m, (outs), (ins i8mem :$dst), 2730b57cec5SDimitry Andric "sar{b}\t{%cl, $dst|$dst, cl}", 2740b57cec5SDimitry Andric [(store (sra (loadi8 addr:$dst), CL), addr:$dst)]>; 2750b57cec5SDimitry Andricdef SAR16mCL : I<0xD3, MRM7m, (outs), (ins i16mem:$dst), 2760b57cec5SDimitry Andric "sar{w}\t{%cl, $dst|$dst, cl}", 2770b57cec5SDimitry Andric [(store (sra (loadi16 addr:$dst), CL), addr:$dst)]>, 2780b57cec5SDimitry Andric OpSize16; 2790b57cec5SDimitry Andricdef SAR32mCL : I<0xD3, MRM7m, (outs), (ins i32mem:$dst), 2800b57cec5SDimitry Andric "sar{l}\t{%cl, $dst|$dst, cl}", 2810b57cec5SDimitry Andric [(store (sra (loadi32 addr:$dst), CL), addr:$dst)]>, 2820b57cec5SDimitry Andric OpSize32; 2830b57cec5SDimitry Andricdef SAR64mCL : RI<0xD3, MRM7m, (outs), (ins i64mem:$dst), 2840b57cec5SDimitry Andric "sar{q}\t{%cl, $dst|$dst, cl}", 2850b57cec5SDimitry Andric [(store (sra (loadi64 addr:$dst), CL), addr:$dst)]>, 2860b57cec5SDimitry Andric Requires<[In64BitMode]>; 2870b57cec5SDimitry Andric} 2880b57cec5SDimitry Andric 2890b57cec5SDimitry Andriclet SchedRW = [WriteShiftLd, WriteRMW] in { 2900b57cec5SDimitry Andricdef SAR8mi : Ii8<0xC0, MRM7m, (outs), (ins i8mem :$dst, u8imm:$src), 2910b57cec5SDimitry Andric "sar{b}\t{$src, $dst|$dst, $src}", 2920b57cec5SDimitry Andric [(store (sra (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>; 2930b57cec5SDimitry Andricdef SAR16mi : Ii8<0xC1, MRM7m, (outs), (ins i16mem:$dst, u8imm:$src), 2940b57cec5SDimitry Andric "sar{w}\t{$src, $dst|$dst, $src}", 2950b57cec5SDimitry Andric [(store (sra (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 2960b57cec5SDimitry Andric OpSize16; 2970b57cec5SDimitry Andricdef SAR32mi : Ii8<0xC1, MRM7m, (outs), (ins i32mem:$dst, u8imm:$src), 2980b57cec5SDimitry Andric "sar{l}\t{$src, $dst|$dst, $src}", 2990b57cec5SDimitry Andric [(store (sra (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 3000b57cec5SDimitry Andric OpSize32; 3010b57cec5SDimitry Andricdef SAR64mi : RIi8<0xC1, MRM7m, (outs), (ins i64mem:$dst, u8imm:$src), 3020b57cec5SDimitry Andric "sar{q}\t{$src, $dst|$dst, $src}", 3030b57cec5SDimitry Andric [(store (sra (loadi64 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 3040b57cec5SDimitry Andric Requires<[In64BitMode]>; 3050b57cec5SDimitry Andric 3060b57cec5SDimitry Andric// Shift by 1 3070b57cec5SDimitry Andricdef SAR8m1 : I<0xD0, MRM7m, (outs), (ins i8mem :$dst), 3080b57cec5SDimitry Andric "sar{b}\t$dst", 3090b57cec5SDimitry Andric [(store (sra (loadi8 addr:$dst), (i8 1)), addr:$dst)]>; 3100b57cec5SDimitry Andricdef SAR16m1 : I<0xD1, MRM7m, (outs), (ins i16mem:$dst), 3110b57cec5SDimitry Andric "sar{w}\t$dst", 3120b57cec5SDimitry Andric [(store (sra (loadi16 addr:$dst), (i8 1)), addr:$dst)]>, 3130b57cec5SDimitry Andric OpSize16; 3140b57cec5SDimitry Andricdef SAR32m1 : I<0xD1, MRM7m, (outs), (ins i32mem:$dst), 3150b57cec5SDimitry Andric "sar{l}\t$dst", 3160b57cec5SDimitry Andric [(store (sra (loadi32 addr:$dst), (i8 1)), addr:$dst)]>, 3170b57cec5SDimitry Andric OpSize32; 3180b57cec5SDimitry Andricdef SAR64m1 : RI<0xD1, MRM7m, (outs), (ins i64mem:$dst), 3190b57cec5SDimitry Andric "sar{q}\t$dst", 3200b57cec5SDimitry Andric [(store (sra (loadi64 addr:$dst), (i8 1)), addr:$dst)]>, 3210b57cec5SDimitry Andric Requires<[In64BitMode]>; 3220b57cec5SDimitry Andric} // SchedRW 3230b57cec5SDimitry Andric 3240b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 3250b57cec5SDimitry Andric// Rotate instructions 3260b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 3270b57cec5SDimitry Andric 3280b57cec5SDimitry Andriclet hasSideEffects = 0 in { 3290b57cec5SDimitry Andriclet Constraints = "$src1 = $dst", SchedRW = [WriteRotate] in { 3300b57cec5SDimitry Andric 3310b57cec5SDimitry Andriclet Uses = [CL, EFLAGS], SchedRW = [WriteRotateCL] in { 3320b57cec5SDimitry Andricdef RCL8rCL : I<0xD2, MRM2r, (outs GR8:$dst), (ins GR8:$src1), 3330b57cec5SDimitry Andric "rcl{b}\t{%cl, $dst|$dst, cl}", []>; 3340b57cec5SDimitry Andricdef RCL16rCL : I<0xD3, MRM2r, (outs GR16:$dst), (ins GR16:$src1), 3350b57cec5SDimitry Andric "rcl{w}\t{%cl, $dst|$dst, cl}", []>, OpSize16; 3360b57cec5SDimitry Andricdef RCL32rCL : I<0xD3, MRM2r, (outs GR32:$dst), (ins GR32:$src1), 3370b57cec5SDimitry Andric "rcl{l}\t{%cl, $dst|$dst, cl}", []>, OpSize32; 3380b57cec5SDimitry Andricdef RCL64rCL : RI<0xD3, MRM2r, (outs GR64:$dst), (ins GR64:$src1), 3390b57cec5SDimitry Andric "rcl{q}\t{%cl, $dst|$dst, cl}", []>; 3400b57cec5SDimitry Andric} // Uses = [CL, EFLAGS] 3410b57cec5SDimitry Andric 3420b57cec5SDimitry Andriclet Uses = [EFLAGS] in { 3430b57cec5SDimitry Andricdef RCL8r1 : I<0xD0, MRM2r, (outs GR8:$dst), (ins GR8:$src1), 3440b57cec5SDimitry Andric "rcl{b}\t$dst", []>; 3450b57cec5SDimitry Andricdef RCL8ri : Ii8<0xC0, MRM2r, (outs GR8:$dst), (ins GR8:$src1, u8imm:$cnt), 3460b57cec5SDimitry Andric "rcl{b}\t{$cnt, $dst|$dst, $cnt}", []>; 3470b57cec5SDimitry Andricdef RCL16r1 : I<0xD1, MRM2r, (outs GR16:$dst), (ins GR16:$src1), 3480b57cec5SDimitry Andric "rcl{w}\t$dst", []>, OpSize16; 3490b57cec5SDimitry Andricdef RCL16ri : Ii8<0xC1, MRM2r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$cnt), 3500b57cec5SDimitry Andric "rcl{w}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize16; 3510b57cec5SDimitry Andricdef RCL32r1 : I<0xD1, MRM2r, (outs GR32:$dst), (ins GR32:$src1), 3520b57cec5SDimitry Andric "rcl{l}\t$dst", []>, OpSize32; 3530b57cec5SDimitry Andricdef RCL32ri : Ii8<0xC1, MRM2r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$cnt), 3540b57cec5SDimitry Andric "rcl{l}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize32; 3550b57cec5SDimitry Andricdef RCL64r1 : RI<0xD1, MRM2r, (outs GR64:$dst), (ins GR64:$src1), 3560b57cec5SDimitry Andric "rcl{q}\t$dst", []>; 3570b57cec5SDimitry Andricdef RCL64ri : RIi8<0xC1, MRM2r, (outs GR64:$dst), (ins GR64:$src1, u8imm:$cnt), 3580b57cec5SDimitry Andric "rcl{q}\t{$cnt, $dst|$dst, $cnt}", []>; 3590b57cec5SDimitry Andric} // Uses = [EFLAGS] 3600b57cec5SDimitry Andric 3610b57cec5SDimitry Andriclet Uses = [CL, EFLAGS], SchedRW = [WriteRotateCL] in { 3620b57cec5SDimitry Andricdef RCR8rCL : I<0xD2, MRM3r, (outs GR8:$dst), (ins GR8:$src1), 3630b57cec5SDimitry Andric "rcr{b}\t{%cl, $dst|$dst, cl}", []>; 3640b57cec5SDimitry Andricdef RCR16rCL : I<0xD3, MRM3r, (outs GR16:$dst), (ins GR16:$src1), 3650b57cec5SDimitry Andric "rcr{w}\t{%cl, $dst|$dst, cl}", []>, OpSize16; 3660b57cec5SDimitry Andricdef RCR32rCL : I<0xD3, MRM3r, (outs GR32:$dst), (ins GR32:$src1), 3670b57cec5SDimitry Andric "rcr{l}\t{%cl, $dst|$dst, cl}", []>, OpSize32; 3680b57cec5SDimitry Andricdef RCR64rCL : RI<0xD3, MRM3r, (outs GR64:$dst), (ins GR64:$src1), 3690b57cec5SDimitry Andric "rcr{q}\t{%cl, $dst|$dst, cl}", []>; 3700b57cec5SDimitry Andric} // Uses = [CL, EFLAGS] 3710b57cec5SDimitry Andric 3720b57cec5SDimitry Andriclet Uses = [EFLAGS] in { 3730b57cec5SDimitry Andricdef RCR8r1 : I<0xD0, MRM3r, (outs GR8:$dst), (ins GR8:$src1), 3740b57cec5SDimitry Andric "rcr{b}\t$dst", []>; 3750b57cec5SDimitry Andricdef RCR8ri : Ii8<0xC0, MRM3r, (outs GR8:$dst), (ins GR8:$src1, u8imm:$cnt), 3760b57cec5SDimitry Andric "rcr{b}\t{$cnt, $dst|$dst, $cnt}", []>; 3770b57cec5SDimitry Andricdef RCR16r1 : I<0xD1, MRM3r, (outs GR16:$dst), (ins GR16:$src1), 3780b57cec5SDimitry Andric "rcr{w}\t$dst", []>, OpSize16; 3790b57cec5SDimitry Andricdef RCR16ri : Ii8<0xC1, MRM3r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$cnt), 3800b57cec5SDimitry Andric "rcr{w}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize16; 3810b57cec5SDimitry Andricdef RCR32r1 : I<0xD1, MRM3r, (outs GR32:$dst), (ins GR32:$src1), 3820b57cec5SDimitry Andric "rcr{l}\t$dst", []>, OpSize32; 3830b57cec5SDimitry Andricdef RCR32ri : Ii8<0xC1, MRM3r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$cnt), 3840b57cec5SDimitry Andric "rcr{l}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize32; 3850b57cec5SDimitry Andricdef RCR64r1 : RI<0xD1, MRM3r, (outs GR64:$dst), (ins GR64:$src1), 3860b57cec5SDimitry Andric "rcr{q}\t$dst", []>; 3870b57cec5SDimitry Andricdef RCR64ri : RIi8<0xC1, MRM3r, (outs GR64:$dst), (ins GR64:$src1, u8imm:$cnt), 3880b57cec5SDimitry Andric "rcr{q}\t{$cnt, $dst|$dst, $cnt}", []>; 3890b57cec5SDimitry Andric} // Uses = [EFLAGS] 3900b57cec5SDimitry Andric 3910b57cec5SDimitry Andric} // Constraints = "$src = $dst" 3920b57cec5SDimitry Andric 3930b57cec5SDimitry Andriclet SchedRW = [WriteRotateLd, WriteRMW], mayStore = 1 in { 3940b57cec5SDimitry Andriclet Uses = [EFLAGS] in { 3950b57cec5SDimitry Andricdef RCL8m1 : I<0xD0, MRM2m, (outs), (ins i8mem:$dst), 3960b57cec5SDimitry Andric "rcl{b}\t$dst", []>; 3970b57cec5SDimitry Andricdef RCL8mi : Ii8<0xC0, MRM2m, (outs), (ins i8mem:$dst, u8imm:$cnt), 3980b57cec5SDimitry Andric "rcl{b}\t{$cnt, $dst|$dst, $cnt}", []>; 3990b57cec5SDimitry Andricdef RCL16m1 : I<0xD1, MRM2m, (outs), (ins i16mem:$dst), 4000b57cec5SDimitry Andric "rcl{w}\t$dst", []>, OpSize16; 4010b57cec5SDimitry Andricdef RCL16mi : Ii8<0xC1, MRM2m, (outs), (ins i16mem:$dst, u8imm:$cnt), 4020b57cec5SDimitry Andric "rcl{w}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize16; 4030b57cec5SDimitry Andricdef RCL32m1 : I<0xD1, MRM2m, (outs), (ins i32mem:$dst), 4040b57cec5SDimitry Andric "rcl{l}\t$dst", []>, OpSize32; 4050b57cec5SDimitry Andricdef RCL32mi : Ii8<0xC1, MRM2m, (outs), (ins i32mem:$dst, u8imm:$cnt), 4060b57cec5SDimitry Andric "rcl{l}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize32; 4070b57cec5SDimitry Andricdef RCL64m1 : RI<0xD1, MRM2m, (outs), (ins i64mem:$dst), 4080b57cec5SDimitry Andric "rcl{q}\t$dst", []>, Requires<[In64BitMode]>; 4090b57cec5SDimitry Andricdef RCL64mi : RIi8<0xC1, MRM2m, (outs), (ins i64mem:$dst, u8imm:$cnt), 4100b57cec5SDimitry Andric "rcl{q}\t{$cnt, $dst|$dst, $cnt}", []>, 4110b57cec5SDimitry Andric Requires<[In64BitMode]>; 4120b57cec5SDimitry Andric 4130b57cec5SDimitry Andricdef RCR8m1 : I<0xD0, MRM3m, (outs), (ins i8mem:$dst), 4140b57cec5SDimitry Andric "rcr{b}\t$dst", []>; 4150b57cec5SDimitry Andricdef RCR8mi : Ii8<0xC0, MRM3m, (outs), (ins i8mem:$dst, u8imm:$cnt), 4160b57cec5SDimitry Andric "rcr{b}\t{$cnt, $dst|$dst, $cnt}", []>; 4170b57cec5SDimitry Andricdef RCR16m1 : I<0xD1, MRM3m, (outs), (ins i16mem:$dst), 4180b57cec5SDimitry Andric "rcr{w}\t$dst", []>, OpSize16; 4190b57cec5SDimitry Andricdef RCR16mi : Ii8<0xC1, MRM3m, (outs), (ins i16mem:$dst, u8imm:$cnt), 4200b57cec5SDimitry Andric "rcr{w}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize16; 4210b57cec5SDimitry Andricdef RCR32m1 : I<0xD1, MRM3m, (outs), (ins i32mem:$dst), 4220b57cec5SDimitry Andric "rcr{l}\t$dst", []>, OpSize32; 4230b57cec5SDimitry Andricdef RCR32mi : Ii8<0xC1, MRM3m, (outs), (ins i32mem:$dst, u8imm:$cnt), 4240b57cec5SDimitry Andric "rcr{l}\t{$cnt, $dst|$dst, $cnt}", []>, OpSize32; 4250b57cec5SDimitry Andricdef RCR64m1 : RI<0xD1, MRM3m, (outs), (ins i64mem:$dst), 4260b57cec5SDimitry Andric "rcr{q}\t$dst", []>, Requires<[In64BitMode]>; 4270b57cec5SDimitry Andricdef RCR64mi : RIi8<0xC1, MRM3m, (outs), (ins i64mem:$dst, u8imm:$cnt), 4280b57cec5SDimitry Andric "rcr{q}\t{$cnt, $dst|$dst, $cnt}", []>, 4290b57cec5SDimitry Andric Requires<[In64BitMode]>; 4300b57cec5SDimitry Andric} // Uses = [EFLAGS] 4310b57cec5SDimitry Andric 4320b57cec5SDimitry Andriclet Uses = [CL, EFLAGS], SchedRW = [WriteRotateCLLd, WriteRMW] in { 4330b57cec5SDimitry Andricdef RCL8mCL : I<0xD2, MRM2m, (outs), (ins i8mem:$dst), 4340b57cec5SDimitry Andric "rcl{b}\t{%cl, $dst|$dst, cl}", []>; 4350b57cec5SDimitry Andricdef RCL16mCL : I<0xD3, MRM2m, (outs), (ins i16mem:$dst), 4360b57cec5SDimitry Andric "rcl{w}\t{%cl, $dst|$dst, cl}", []>, OpSize16; 4370b57cec5SDimitry Andricdef RCL32mCL : I<0xD3, MRM2m, (outs), (ins i32mem:$dst), 4380b57cec5SDimitry Andric "rcl{l}\t{%cl, $dst|$dst, cl}", []>, OpSize32; 4390b57cec5SDimitry Andricdef RCL64mCL : RI<0xD3, MRM2m, (outs), (ins i64mem:$dst), 4400b57cec5SDimitry Andric "rcl{q}\t{%cl, $dst|$dst, cl}", []>, 4410b57cec5SDimitry Andric Requires<[In64BitMode]>; 4420b57cec5SDimitry Andric 4430b57cec5SDimitry Andricdef RCR8mCL : I<0xD2, MRM3m, (outs), (ins i8mem:$dst), 4440b57cec5SDimitry Andric "rcr{b}\t{%cl, $dst|$dst, cl}", []>; 4450b57cec5SDimitry Andricdef RCR16mCL : I<0xD3, MRM3m, (outs), (ins i16mem:$dst), 4460b57cec5SDimitry Andric "rcr{w}\t{%cl, $dst|$dst, cl}", []>, OpSize16; 4470b57cec5SDimitry Andricdef RCR32mCL : I<0xD3, MRM3m, (outs), (ins i32mem:$dst), 4480b57cec5SDimitry Andric "rcr{l}\t{%cl, $dst|$dst, cl}", []>, OpSize32; 4490b57cec5SDimitry Andricdef RCR64mCL : RI<0xD3, MRM3m, (outs), (ins i64mem:$dst), 4500b57cec5SDimitry Andric "rcr{q}\t{%cl, $dst|$dst, cl}", []>, 4510b57cec5SDimitry Andric Requires<[In64BitMode]>; 4520b57cec5SDimitry Andric} // Uses = [CL, EFLAGS] 4530b57cec5SDimitry Andric} // SchedRW 4540b57cec5SDimitry Andric} // hasSideEffects = 0 4550b57cec5SDimitry Andric 4560b57cec5SDimitry Andriclet Constraints = "$src1 = $dst", SchedRW = [WriteRotate] in { 4570b57cec5SDimitry Andric// FIXME: provide shorter instructions when imm8 == 1 4580b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteRotateCL] in { 4590b57cec5SDimitry Andricdef ROL8rCL : I<0xD2, MRM0r, (outs GR8 :$dst), (ins GR8 :$src1), 4600b57cec5SDimitry Andric "rol{b}\t{%cl, $dst|$dst, cl}", 4610b57cec5SDimitry Andric [(set GR8:$dst, (rotl GR8:$src1, CL))]>; 4620b57cec5SDimitry Andricdef ROL16rCL : I<0xD3, MRM0r, (outs GR16:$dst), (ins GR16:$src1), 4630b57cec5SDimitry Andric "rol{w}\t{%cl, $dst|$dst, cl}", 4640b57cec5SDimitry Andric [(set GR16:$dst, (rotl GR16:$src1, CL))]>, OpSize16; 4650b57cec5SDimitry Andricdef ROL32rCL : I<0xD3, MRM0r, (outs GR32:$dst), (ins GR32:$src1), 4660b57cec5SDimitry Andric "rol{l}\t{%cl, $dst|$dst, cl}", 4670b57cec5SDimitry Andric [(set GR32:$dst, (rotl GR32:$src1, CL))]>, OpSize32; 4680b57cec5SDimitry Andricdef ROL64rCL : RI<0xD3, MRM0r, (outs GR64:$dst), (ins GR64:$src1), 4690b57cec5SDimitry Andric "rol{q}\t{%cl, $dst|$dst, cl}", 4700b57cec5SDimitry Andric [(set GR64:$dst, (rotl GR64:$src1, CL))]>; 4710b57cec5SDimitry Andric} 4720b57cec5SDimitry Andric 4730b57cec5SDimitry Andricdef ROL8ri : Ii8<0xC0, MRM0r, (outs GR8 :$dst), (ins GR8 :$src1, u8imm:$src2), 4740b57cec5SDimitry Andric "rol{b}\t{$src2, $dst|$dst, $src2}", 475*5ffd83dbSDimitry Andric [(set GR8:$dst, (rotl GR8:$src1, (i8 imm:$src2)))]>; 4760b57cec5SDimitry Andricdef ROL16ri : Ii8<0xC1, MRM0r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$src2), 4770b57cec5SDimitry Andric "rol{w}\t{$src2, $dst|$dst, $src2}", 478*5ffd83dbSDimitry Andric [(set GR16:$dst, (rotl GR16:$src1, (i8 imm:$src2)))]>, 4790b57cec5SDimitry Andric OpSize16; 4800b57cec5SDimitry Andricdef ROL32ri : Ii8<0xC1, MRM0r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$src2), 4810b57cec5SDimitry Andric "rol{l}\t{$src2, $dst|$dst, $src2}", 482*5ffd83dbSDimitry Andric [(set GR32:$dst, (rotl GR32:$src1, (i8 imm:$src2)))]>, 4830b57cec5SDimitry Andric OpSize32; 4840b57cec5SDimitry Andricdef ROL64ri : RIi8<0xC1, MRM0r, (outs GR64:$dst), 4850b57cec5SDimitry Andric (ins GR64:$src1, u8imm:$src2), 4860b57cec5SDimitry Andric "rol{q}\t{$src2, $dst|$dst, $src2}", 487*5ffd83dbSDimitry Andric [(set GR64:$dst, (rotl GR64:$src1, (i8 imm:$src2)))]>; 4880b57cec5SDimitry Andric 4890b57cec5SDimitry Andric// Rotate by 1 4900b57cec5SDimitry Andricdef ROL8r1 : I<0xD0, MRM0r, (outs GR8 :$dst), (ins GR8 :$src1), 4910b57cec5SDimitry Andric "rol{b}\t$dst", 4920b57cec5SDimitry Andric [(set GR8:$dst, (rotl GR8:$src1, (i8 1)))]>; 4930b57cec5SDimitry Andricdef ROL16r1 : I<0xD1, MRM0r, (outs GR16:$dst), (ins GR16:$src1), 4940b57cec5SDimitry Andric "rol{w}\t$dst", 4950b57cec5SDimitry Andric [(set GR16:$dst, (rotl GR16:$src1, (i8 1)))]>, OpSize16; 4960b57cec5SDimitry Andricdef ROL32r1 : I<0xD1, MRM0r, (outs GR32:$dst), (ins GR32:$src1), 4970b57cec5SDimitry Andric "rol{l}\t$dst", 4980b57cec5SDimitry Andric [(set GR32:$dst, (rotl GR32:$src1, (i8 1)))]>, OpSize32; 4990b57cec5SDimitry Andricdef ROL64r1 : RI<0xD1, MRM0r, (outs GR64:$dst), (ins GR64:$src1), 5000b57cec5SDimitry Andric "rol{q}\t$dst", 5010b57cec5SDimitry Andric [(set GR64:$dst, (rotl GR64:$src1, (i8 1)))]>; 5020b57cec5SDimitry Andric} // Constraints = "$src = $dst", SchedRW 5030b57cec5SDimitry Andric 5040b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteRotateCLLd, WriteRMW] in { 5050b57cec5SDimitry Andricdef ROL8mCL : I<0xD2, MRM0m, (outs), (ins i8mem :$dst), 5060b57cec5SDimitry Andric "rol{b}\t{%cl, $dst|$dst, cl}", 5070b57cec5SDimitry Andric [(store (rotl (loadi8 addr:$dst), CL), addr:$dst)]>; 5080b57cec5SDimitry Andricdef ROL16mCL : I<0xD3, MRM0m, (outs), (ins i16mem:$dst), 5090b57cec5SDimitry Andric "rol{w}\t{%cl, $dst|$dst, cl}", 5100b57cec5SDimitry Andric [(store (rotl (loadi16 addr:$dst), CL), addr:$dst)]>, OpSize16; 5110b57cec5SDimitry Andricdef ROL32mCL : I<0xD3, MRM0m, (outs), (ins i32mem:$dst), 5120b57cec5SDimitry Andric "rol{l}\t{%cl, $dst|$dst, cl}", 5130b57cec5SDimitry Andric [(store (rotl (loadi32 addr:$dst), CL), addr:$dst)]>, OpSize32; 5140b57cec5SDimitry Andricdef ROL64mCL : RI<0xD3, MRM0m, (outs), (ins i64mem:$dst), 5150b57cec5SDimitry Andric "rol{q}\t{%cl, $dst|$dst, cl}", 5160b57cec5SDimitry Andric [(store (rotl (loadi64 addr:$dst), CL), addr:$dst)]>, 5170b57cec5SDimitry Andric Requires<[In64BitMode]>; 5180b57cec5SDimitry Andric} 5190b57cec5SDimitry Andric 5200b57cec5SDimitry Andriclet SchedRW = [WriteRotateLd, WriteRMW] in { 5210b57cec5SDimitry Andricdef ROL8mi : Ii8<0xC0, MRM0m, (outs), (ins i8mem :$dst, u8imm:$src1), 5220b57cec5SDimitry Andric "rol{b}\t{$src1, $dst|$dst, $src1}", 5230b57cec5SDimitry Andric [(store (rotl (loadi8 addr:$dst), (i8 imm:$src1)), addr:$dst)]>; 5240b57cec5SDimitry Andricdef ROL16mi : Ii8<0xC1, MRM0m, (outs), (ins i16mem:$dst, u8imm:$src1), 5250b57cec5SDimitry Andric "rol{w}\t{$src1, $dst|$dst, $src1}", 5260b57cec5SDimitry Andric [(store (rotl (loadi16 addr:$dst), (i8 imm:$src1)), addr:$dst)]>, 5270b57cec5SDimitry Andric OpSize16; 5280b57cec5SDimitry Andricdef ROL32mi : Ii8<0xC1, MRM0m, (outs), (ins i32mem:$dst, u8imm:$src1), 5290b57cec5SDimitry Andric "rol{l}\t{$src1, $dst|$dst, $src1}", 5300b57cec5SDimitry Andric [(store (rotl (loadi32 addr:$dst), (i8 imm:$src1)), addr:$dst)]>, 5310b57cec5SDimitry Andric OpSize32; 5320b57cec5SDimitry Andricdef ROL64mi : RIi8<0xC1, MRM0m, (outs), (ins i64mem:$dst, u8imm:$src1), 5330b57cec5SDimitry Andric "rol{q}\t{$src1, $dst|$dst, $src1}", 5340b57cec5SDimitry Andric [(store (rotl (loadi64 addr:$dst), (i8 imm:$src1)), addr:$dst)]>, 5350b57cec5SDimitry Andric Requires<[In64BitMode]>; 5360b57cec5SDimitry Andric 5370b57cec5SDimitry Andric// Rotate by 1 5380b57cec5SDimitry Andricdef ROL8m1 : I<0xD0, MRM0m, (outs), (ins i8mem :$dst), 5390b57cec5SDimitry Andric "rol{b}\t$dst", 5400b57cec5SDimitry Andric [(store (rotl (loadi8 addr:$dst), (i8 1)), addr:$dst)]>; 5410b57cec5SDimitry Andricdef ROL16m1 : I<0xD1, MRM0m, (outs), (ins i16mem:$dst), 5420b57cec5SDimitry Andric "rol{w}\t$dst", 5430b57cec5SDimitry Andric [(store (rotl (loadi16 addr:$dst), (i8 1)), addr:$dst)]>, 5440b57cec5SDimitry Andric OpSize16; 5450b57cec5SDimitry Andricdef ROL32m1 : I<0xD1, MRM0m, (outs), (ins i32mem:$dst), 5460b57cec5SDimitry Andric "rol{l}\t$dst", 5470b57cec5SDimitry Andric [(store (rotl (loadi32 addr:$dst), (i8 1)), addr:$dst)]>, 5480b57cec5SDimitry Andric OpSize32; 5490b57cec5SDimitry Andricdef ROL64m1 : RI<0xD1, MRM0m, (outs), (ins i64mem:$dst), 5500b57cec5SDimitry Andric "rol{q}\t$dst", 5510b57cec5SDimitry Andric [(store (rotl (loadi64 addr:$dst), (i8 1)), addr:$dst)]>, 5520b57cec5SDimitry Andric Requires<[In64BitMode]>; 5530b57cec5SDimitry Andric} // SchedRW 5540b57cec5SDimitry Andric 5550b57cec5SDimitry Andriclet Constraints = "$src1 = $dst", SchedRW = [WriteRotate] in { 5560b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteRotateCL] in { 5570b57cec5SDimitry Andricdef ROR8rCL : I<0xD2, MRM1r, (outs GR8 :$dst), (ins GR8 :$src1), 5580b57cec5SDimitry Andric "ror{b}\t{%cl, $dst|$dst, cl}", 5590b57cec5SDimitry Andric [(set GR8:$dst, (rotr GR8:$src1, CL))]>; 5600b57cec5SDimitry Andricdef ROR16rCL : I<0xD3, MRM1r, (outs GR16:$dst), (ins GR16:$src1), 5610b57cec5SDimitry Andric "ror{w}\t{%cl, $dst|$dst, cl}", 5620b57cec5SDimitry Andric [(set GR16:$dst, (rotr GR16:$src1, CL))]>, OpSize16; 5630b57cec5SDimitry Andricdef ROR32rCL : I<0xD3, MRM1r, (outs GR32:$dst), (ins GR32:$src1), 5640b57cec5SDimitry Andric "ror{l}\t{%cl, $dst|$dst, cl}", 5650b57cec5SDimitry Andric [(set GR32:$dst, (rotr GR32:$src1, CL))]>, OpSize32; 5660b57cec5SDimitry Andricdef ROR64rCL : RI<0xD3, MRM1r, (outs GR64:$dst), (ins GR64:$src1), 5670b57cec5SDimitry Andric "ror{q}\t{%cl, $dst|$dst, cl}", 5680b57cec5SDimitry Andric [(set GR64:$dst, (rotr GR64:$src1, CL))]>; 5690b57cec5SDimitry Andric} 5700b57cec5SDimitry Andric 5710b57cec5SDimitry Andricdef ROR8ri : Ii8<0xC0, MRM1r, (outs GR8 :$dst), (ins GR8 :$src1, u8imm:$src2), 5720b57cec5SDimitry Andric "ror{b}\t{$src2, $dst|$dst, $src2}", 573*5ffd83dbSDimitry Andric [(set GR8:$dst, (rotr GR8:$src1, (i8 imm:$src2)))]>; 5740b57cec5SDimitry Andricdef ROR16ri : Ii8<0xC1, MRM1r, (outs GR16:$dst), (ins GR16:$src1, u8imm:$src2), 5750b57cec5SDimitry Andric "ror{w}\t{$src2, $dst|$dst, $src2}", 576*5ffd83dbSDimitry Andric [(set GR16:$dst, (rotr GR16:$src1, (i8 imm:$src2)))]>, 5770b57cec5SDimitry Andric OpSize16; 5780b57cec5SDimitry Andricdef ROR32ri : Ii8<0xC1, MRM1r, (outs GR32:$dst), (ins GR32:$src1, u8imm:$src2), 5790b57cec5SDimitry Andric "ror{l}\t{$src2, $dst|$dst, $src2}", 580*5ffd83dbSDimitry Andric [(set GR32:$dst, (rotr GR32:$src1, (i8 imm:$src2)))]>, 5810b57cec5SDimitry Andric OpSize32; 5820b57cec5SDimitry Andricdef ROR64ri : RIi8<0xC1, MRM1r, (outs GR64:$dst), 5830b57cec5SDimitry Andric (ins GR64:$src1, u8imm:$src2), 5840b57cec5SDimitry Andric "ror{q}\t{$src2, $dst|$dst, $src2}", 585*5ffd83dbSDimitry Andric [(set GR64:$dst, (rotr GR64:$src1, (i8 imm:$src2)))]>; 5860b57cec5SDimitry Andric 5870b57cec5SDimitry Andric// Rotate by 1 5880b57cec5SDimitry Andricdef ROR8r1 : I<0xD0, MRM1r, (outs GR8 :$dst), (ins GR8 :$src1), 5890b57cec5SDimitry Andric "ror{b}\t$dst", 5900b57cec5SDimitry Andric [(set GR8:$dst, (rotr GR8:$src1, (i8 1)))]>; 5910b57cec5SDimitry Andricdef ROR16r1 : I<0xD1, MRM1r, (outs GR16:$dst), (ins GR16:$src1), 5920b57cec5SDimitry Andric "ror{w}\t$dst", 5930b57cec5SDimitry Andric [(set GR16:$dst, (rotr GR16:$src1, (i8 1)))]>, OpSize16; 5940b57cec5SDimitry Andricdef ROR32r1 : I<0xD1, MRM1r, (outs GR32:$dst), (ins GR32:$src1), 5950b57cec5SDimitry Andric "ror{l}\t$dst", 5960b57cec5SDimitry Andric [(set GR32:$dst, (rotr GR32:$src1, (i8 1)))]>, OpSize32; 5970b57cec5SDimitry Andricdef ROR64r1 : RI<0xD1, MRM1r, (outs GR64:$dst), (ins GR64:$src1), 5980b57cec5SDimitry Andric "ror{q}\t$dst", 5990b57cec5SDimitry Andric [(set GR64:$dst, (rotr GR64:$src1, (i8 1)))]>; 6000b57cec5SDimitry Andric} // Constraints = "$src = $dst", SchedRW 6010b57cec5SDimitry Andric 6020b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteRotateCLLd, WriteRMW] in { 6030b57cec5SDimitry Andricdef ROR8mCL : I<0xD2, MRM1m, (outs), (ins i8mem :$dst), 6040b57cec5SDimitry Andric "ror{b}\t{%cl, $dst|$dst, cl}", 6050b57cec5SDimitry Andric [(store (rotr (loadi8 addr:$dst), CL), addr:$dst)]>; 6060b57cec5SDimitry Andricdef ROR16mCL : I<0xD3, MRM1m, (outs), (ins i16mem:$dst), 6070b57cec5SDimitry Andric "ror{w}\t{%cl, $dst|$dst, cl}", 6080b57cec5SDimitry Andric [(store (rotr (loadi16 addr:$dst), CL), addr:$dst)]>, OpSize16; 6090b57cec5SDimitry Andricdef ROR32mCL : I<0xD3, MRM1m, (outs), (ins i32mem:$dst), 6100b57cec5SDimitry Andric "ror{l}\t{%cl, $dst|$dst, cl}", 6110b57cec5SDimitry Andric [(store (rotr (loadi32 addr:$dst), CL), addr:$dst)]>, OpSize32; 6120b57cec5SDimitry Andricdef ROR64mCL : RI<0xD3, MRM1m, (outs), (ins i64mem:$dst), 6130b57cec5SDimitry Andric "ror{q}\t{%cl, $dst|$dst, cl}", 6140b57cec5SDimitry Andric [(store (rotr (loadi64 addr:$dst), CL), addr:$dst)]>, 6150b57cec5SDimitry Andric Requires<[In64BitMode]>; 6160b57cec5SDimitry Andric} 6170b57cec5SDimitry Andric 6180b57cec5SDimitry Andriclet SchedRW = [WriteRotateLd, WriteRMW] in { 6190b57cec5SDimitry Andricdef ROR8mi : Ii8<0xC0, MRM1m, (outs), (ins i8mem :$dst, u8imm:$src), 6200b57cec5SDimitry Andric "ror{b}\t{$src, $dst|$dst, $src}", 6210b57cec5SDimitry Andric [(store (rotr (loadi8 addr:$dst), (i8 imm:$src)), addr:$dst)]>; 6220b57cec5SDimitry Andricdef ROR16mi : Ii8<0xC1, MRM1m, (outs), (ins i16mem:$dst, u8imm:$src), 6230b57cec5SDimitry Andric "ror{w}\t{$src, $dst|$dst, $src}", 6240b57cec5SDimitry Andric [(store (rotr (loadi16 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 6250b57cec5SDimitry Andric OpSize16; 6260b57cec5SDimitry Andricdef ROR32mi : Ii8<0xC1, MRM1m, (outs), (ins i32mem:$dst, u8imm:$src), 6270b57cec5SDimitry Andric "ror{l}\t{$src, $dst|$dst, $src}", 6280b57cec5SDimitry Andric [(store (rotr (loadi32 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 6290b57cec5SDimitry Andric OpSize32; 6300b57cec5SDimitry Andricdef ROR64mi : RIi8<0xC1, MRM1m, (outs), (ins i64mem:$dst, u8imm:$src), 6310b57cec5SDimitry Andric "ror{q}\t{$src, $dst|$dst, $src}", 6320b57cec5SDimitry Andric [(store (rotr (loadi64 addr:$dst), (i8 imm:$src)), addr:$dst)]>, 6330b57cec5SDimitry Andric Requires<[In64BitMode]>; 6340b57cec5SDimitry Andric 6350b57cec5SDimitry Andric// Rotate by 1 6360b57cec5SDimitry Andricdef ROR8m1 : I<0xD0, MRM1m, (outs), (ins i8mem :$dst), 6370b57cec5SDimitry Andric "ror{b}\t$dst", 6380b57cec5SDimitry Andric [(store (rotr (loadi8 addr:$dst), (i8 1)), addr:$dst)]>; 6390b57cec5SDimitry Andricdef ROR16m1 : I<0xD1, MRM1m, (outs), (ins i16mem:$dst), 6400b57cec5SDimitry Andric "ror{w}\t$dst", 6410b57cec5SDimitry Andric [(store (rotr (loadi16 addr:$dst), (i8 1)), addr:$dst)]>, 6420b57cec5SDimitry Andric OpSize16; 6430b57cec5SDimitry Andricdef ROR32m1 : I<0xD1, MRM1m, (outs), (ins i32mem:$dst), 6440b57cec5SDimitry Andric "ror{l}\t$dst", 6450b57cec5SDimitry Andric [(store (rotr (loadi32 addr:$dst), (i8 1)), addr:$dst)]>, 6460b57cec5SDimitry Andric OpSize32; 6470b57cec5SDimitry Andricdef ROR64m1 : RI<0xD1, MRM1m, (outs), (ins i64mem:$dst), 6480b57cec5SDimitry Andric "ror{q}\t$dst", 6490b57cec5SDimitry Andric [(store (rotr (loadi64 addr:$dst), (i8 1)), addr:$dst)]>, 6500b57cec5SDimitry Andric Requires<[In64BitMode]>; 6510b57cec5SDimitry Andric} // SchedRW 6520b57cec5SDimitry Andric 6530b57cec5SDimitry Andric 6540b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 6550b57cec5SDimitry Andric// Double shift instructions (generalizations of rotate) 6560b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 6570b57cec5SDimitry Andric 6580b57cec5SDimitry Andriclet Constraints = "$src1 = $dst" in { 6590b57cec5SDimitry Andric 6600b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteSHDrrcl] in { 6610b57cec5SDimitry Andricdef SHLD16rrCL : I<0xA5, MRMDestReg, (outs GR16:$dst), 6620b57cec5SDimitry Andric (ins GR16:$src1, GR16:$src2), 6630b57cec5SDimitry Andric "shld{w}\t{%cl, $src2, $dst|$dst, $src2, cl}", 664*5ffd83dbSDimitry Andric [(set GR16:$dst, (X86fshl GR16:$src1, GR16:$src2, CL))]>, 6650b57cec5SDimitry Andric TB, OpSize16; 6660b57cec5SDimitry Andricdef SHRD16rrCL : I<0xAD, MRMDestReg, (outs GR16:$dst), 6670b57cec5SDimitry Andric (ins GR16:$src1, GR16:$src2), 6680b57cec5SDimitry Andric "shrd{w}\t{%cl, $src2, $dst|$dst, $src2, cl}", 669*5ffd83dbSDimitry Andric [(set GR16:$dst, (X86fshr GR16:$src2, GR16:$src1, CL))]>, 6700b57cec5SDimitry Andric TB, OpSize16; 6710b57cec5SDimitry Andricdef SHLD32rrCL : I<0xA5, MRMDestReg, (outs GR32:$dst), 6720b57cec5SDimitry Andric (ins GR32:$src1, GR32:$src2), 6730b57cec5SDimitry Andric "shld{l}\t{%cl, $src2, $dst|$dst, $src2, cl}", 674*5ffd83dbSDimitry Andric [(set GR32:$dst, (fshl GR32:$src1, GR32:$src2, CL))]>, 6750b57cec5SDimitry Andric TB, OpSize32; 6760b57cec5SDimitry Andricdef SHRD32rrCL : I<0xAD, MRMDestReg, (outs GR32:$dst), 6770b57cec5SDimitry Andric (ins GR32:$src1, GR32:$src2), 6780b57cec5SDimitry Andric "shrd{l}\t{%cl, $src2, $dst|$dst, $src2, cl}", 679*5ffd83dbSDimitry Andric [(set GR32:$dst, (fshr GR32:$src2, GR32:$src1, CL))]>, 6800b57cec5SDimitry Andric TB, OpSize32; 6810b57cec5SDimitry Andricdef SHLD64rrCL : RI<0xA5, MRMDestReg, (outs GR64:$dst), 6820b57cec5SDimitry Andric (ins GR64:$src1, GR64:$src2), 6830b57cec5SDimitry Andric "shld{q}\t{%cl, $src2, $dst|$dst, $src2, cl}", 684*5ffd83dbSDimitry Andric [(set GR64:$dst, (fshl GR64:$src1, GR64:$src2, CL))]>, 6850b57cec5SDimitry Andric TB; 6860b57cec5SDimitry Andricdef SHRD64rrCL : RI<0xAD, MRMDestReg, (outs GR64:$dst), 6870b57cec5SDimitry Andric (ins GR64:$src1, GR64:$src2), 6880b57cec5SDimitry Andric "shrd{q}\t{%cl, $src2, $dst|$dst, $src2, cl}", 689*5ffd83dbSDimitry Andric [(set GR64:$dst, (fshr GR64:$src2, GR64:$src1, CL))]>, 6900b57cec5SDimitry Andric TB; 6910b57cec5SDimitry Andric} // SchedRW 6920b57cec5SDimitry Andric 6930b57cec5SDimitry Andriclet isCommutable = 1, SchedRW = [WriteSHDrri] in { // These instructions commute to each other. 6940b57cec5SDimitry Andricdef SHLD16rri8 : Ii8<0xA4, MRMDestReg, 6950b57cec5SDimitry Andric (outs GR16:$dst), 6960b57cec5SDimitry Andric (ins GR16:$src1, GR16:$src2, u8imm:$src3), 6970b57cec5SDimitry Andric "shld{w}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 698*5ffd83dbSDimitry Andric [(set GR16:$dst, (X86fshl GR16:$src1, GR16:$src2, 6990b57cec5SDimitry Andric (i8 imm:$src3)))]>, 7000b57cec5SDimitry Andric TB, OpSize16; 7010b57cec5SDimitry Andricdef SHRD16rri8 : Ii8<0xAC, MRMDestReg, 7020b57cec5SDimitry Andric (outs GR16:$dst), 7030b57cec5SDimitry Andric (ins GR16:$src1, GR16:$src2, u8imm:$src3), 7040b57cec5SDimitry Andric "shrd{w}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 705*5ffd83dbSDimitry Andric [(set GR16:$dst, (X86fshr GR16:$src2, GR16:$src1, 7060b57cec5SDimitry Andric (i8 imm:$src3)))]>, 7070b57cec5SDimitry Andric TB, OpSize16; 7080b57cec5SDimitry Andricdef SHLD32rri8 : Ii8<0xA4, MRMDestReg, 7090b57cec5SDimitry Andric (outs GR32:$dst), 7100b57cec5SDimitry Andric (ins GR32:$src1, GR32:$src2, u8imm:$src3), 7110b57cec5SDimitry Andric "shld{l}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 712*5ffd83dbSDimitry Andric [(set GR32:$dst, (fshl GR32:$src1, GR32:$src2, 7130b57cec5SDimitry Andric (i8 imm:$src3)))]>, 7140b57cec5SDimitry Andric TB, OpSize32; 7150b57cec5SDimitry Andricdef SHRD32rri8 : Ii8<0xAC, MRMDestReg, 7160b57cec5SDimitry Andric (outs GR32:$dst), 7170b57cec5SDimitry Andric (ins GR32:$src1, GR32:$src2, u8imm:$src3), 7180b57cec5SDimitry Andric "shrd{l}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 719*5ffd83dbSDimitry Andric [(set GR32:$dst, (fshr GR32:$src2, GR32:$src1, 7200b57cec5SDimitry Andric (i8 imm:$src3)))]>, 7210b57cec5SDimitry Andric TB, OpSize32; 7220b57cec5SDimitry Andricdef SHLD64rri8 : RIi8<0xA4, MRMDestReg, 7230b57cec5SDimitry Andric (outs GR64:$dst), 7240b57cec5SDimitry Andric (ins GR64:$src1, GR64:$src2, u8imm:$src3), 7250b57cec5SDimitry Andric "shld{q}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 726*5ffd83dbSDimitry Andric [(set GR64:$dst, (fshl GR64:$src1, GR64:$src2, 7270b57cec5SDimitry Andric (i8 imm:$src3)))]>, 7280b57cec5SDimitry Andric TB; 7290b57cec5SDimitry Andricdef SHRD64rri8 : RIi8<0xAC, MRMDestReg, 7300b57cec5SDimitry Andric (outs GR64:$dst), 7310b57cec5SDimitry Andric (ins GR64:$src1, GR64:$src2, u8imm:$src3), 7320b57cec5SDimitry Andric "shrd{q}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 733*5ffd83dbSDimitry Andric [(set GR64:$dst, (fshr GR64:$src2, GR64:$src1, 7340b57cec5SDimitry Andric (i8 imm:$src3)))]>, 7350b57cec5SDimitry Andric TB; 7360b57cec5SDimitry Andric} // SchedRW 7370b57cec5SDimitry Andric} // Constraints = "$src = $dst" 7380b57cec5SDimitry Andric 7390b57cec5SDimitry Andriclet Uses = [CL], SchedRW = [WriteSHDmrcl] in { 7400b57cec5SDimitry Andricdef SHLD16mrCL : I<0xA5, MRMDestMem, (outs), (ins i16mem:$dst, GR16:$src2), 7410b57cec5SDimitry Andric "shld{w}\t{%cl, $src2, $dst|$dst, $src2, cl}", 742*5ffd83dbSDimitry Andric [(store (X86fshl (loadi16 addr:$dst), GR16:$src2, CL), 7430b57cec5SDimitry Andric addr:$dst)]>, TB, OpSize16; 7440b57cec5SDimitry Andricdef SHRD16mrCL : I<0xAD, MRMDestMem, (outs), (ins i16mem:$dst, GR16:$src2), 7450b57cec5SDimitry Andric "shrd{w}\t{%cl, $src2, $dst|$dst, $src2, cl}", 746*5ffd83dbSDimitry Andric [(store (X86fshr GR16:$src2, (loadi16 addr:$dst), CL), 7470b57cec5SDimitry Andric addr:$dst)]>, TB, OpSize16; 7480b57cec5SDimitry Andric 7490b57cec5SDimitry Andricdef SHLD32mrCL : I<0xA5, MRMDestMem, (outs), (ins i32mem:$dst, GR32:$src2), 7500b57cec5SDimitry Andric "shld{l}\t{%cl, $src2, $dst|$dst, $src2, cl}", 751*5ffd83dbSDimitry Andric [(store (fshl (loadi32 addr:$dst), GR32:$src2, CL), 7520b57cec5SDimitry Andric addr:$dst)]>, TB, OpSize32; 7530b57cec5SDimitry Andricdef SHRD32mrCL : I<0xAD, MRMDestMem, (outs), (ins i32mem:$dst, GR32:$src2), 7540b57cec5SDimitry Andric "shrd{l}\t{%cl, $src2, $dst|$dst, $src2, cl}", 755*5ffd83dbSDimitry Andric [(store (fshr GR32:$src2, (loadi32 addr:$dst), CL), 7560b57cec5SDimitry Andric addr:$dst)]>, TB, OpSize32; 7570b57cec5SDimitry Andric 7580b57cec5SDimitry Andricdef SHLD64mrCL : RI<0xA5, MRMDestMem, (outs), (ins i64mem:$dst, GR64:$src2), 7590b57cec5SDimitry Andric "shld{q}\t{%cl, $src2, $dst|$dst, $src2, cl}", 760*5ffd83dbSDimitry Andric [(store (fshl (loadi64 addr:$dst), GR64:$src2, CL), 7610b57cec5SDimitry Andric addr:$dst)]>, TB; 7620b57cec5SDimitry Andricdef SHRD64mrCL : RI<0xAD, MRMDestMem, (outs), (ins i64mem:$dst, GR64:$src2), 7630b57cec5SDimitry Andric "shrd{q}\t{%cl, $src2, $dst|$dst, $src2, cl}", 764*5ffd83dbSDimitry Andric [(store (fshr GR64:$src2, (loadi64 addr:$dst), CL), 7650b57cec5SDimitry Andric addr:$dst)]>, TB; 7660b57cec5SDimitry Andric} // SchedRW 7670b57cec5SDimitry Andric 7680b57cec5SDimitry Andriclet SchedRW = [WriteSHDmri] in { 7690b57cec5SDimitry Andricdef SHLD16mri8 : Ii8<0xA4, MRMDestMem, 7700b57cec5SDimitry Andric (outs), (ins i16mem:$dst, GR16:$src2, u8imm:$src3), 7710b57cec5SDimitry Andric "shld{w}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 772*5ffd83dbSDimitry Andric [(store (X86fshl (loadi16 addr:$dst), GR16:$src2, 7730b57cec5SDimitry Andric (i8 imm:$src3)), addr:$dst)]>, 7740b57cec5SDimitry Andric TB, OpSize16; 7750b57cec5SDimitry Andricdef SHRD16mri8 : Ii8<0xAC, MRMDestMem, 7760b57cec5SDimitry Andric (outs), (ins i16mem:$dst, GR16:$src2, u8imm:$src3), 7770b57cec5SDimitry Andric "shrd{w}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 778*5ffd83dbSDimitry Andric [(store (X86fshr GR16:$src2, (loadi16 addr:$dst), 7790b57cec5SDimitry Andric (i8 imm:$src3)), addr:$dst)]>, 7800b57cec5SDimitry Andric TB, OpSize16; 7810b57cec5SDimitry Andric 7820b57cec5SDimitry Andricdef SHLD32mri8 : Ii8<0xA4, MRMDestMem, 7830b57cec5SDimitry Andric (outs), (ins i32mem:$dst, GR32:$src2, u8imm:$src3), 7840b57cec5SDimitry Andric "shld{l}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 785*5ffd83dbSDimitry Andric [(store (fshl (loadi32 addr:$dst), GR32:$src2, 7860b57cec5SDimitry Andric (i8 imm:$src3)), addr:$dst)]>, 7870b57cec5SDimitry Andric TB, OpSize32; 7880b57cec5SDimitry Andricdef SHRD32mri8 : Ii8<0xAC, MRMDestMem, 7890b57cec5SDimitry Andric (outs), (ins i32mem:$dst, GR32:$src2, u8imm:$src3), 7900b57cec5SDimitry Andric "shrd{l}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 791*5ffd83dbSDimitry Andric [(store (fshr GR32:$src2, (loadi32 addr:$dst), 7920b57cec5SDimitry Andric (i8 imm:$src3)), addr:$dst)]>, 7930b57cec5SDimitry Andric TB, OpSize32; 7940b57cec5SDimitry Andric 7950b57cec5SDimitry Andricdef SHLD64mri8 : RIi8<0xA4, MRMDestMem, 7960b57cec5SDimitry Andric (outs), (ins i64mem:$dst, GR64:$src2, u8imm:$src3), 7970b57cec5SDimitry Andric "shld{q}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 798*5ffd83dbSDimitry Andric [(store (fshl (loadi64 addr:$dst), GR64:$src2, 7990b57cec5SDimitry Andric (i8 imm:$src3)), addr:$dst)]>, 8000b57cec5SDimitry Andric TB; 8010b57cec5SDimitry Andricdef SHRD64mri8 : RIi8<0xAC, MRMDestMem, 8020b57cec5SDimitry Andric (outs), (ins i64mem:$dst, GR64:$src2, u8imm:$src3), 8030b57cec5SDimitry Andric "shrd{q}\t{$src3, $src2, $dst|$dst, $src2, $src3}", 804*5ffd83dbSDimitry Andric [(store (fshr GR64:$src2, (loadi64 addr:$dst), 8050b57cec5SDimitry Andric (i8 imm:$src3)), addr:$dst)]>, 8060b57cec5SDimitry Andric TB; 8070b57cec5SDimitry Andric} // SchedRW 8080b57cec5SDimitry Andric 8090b57cec5SDimitry Andric} // Defs = [EFLAGS] 8100b57cec5SDimitry Andric 8110b57cec5SDimitry Andric// Use the opposite rotate if allows us to use the rotate by 1 instruction. 8120b57cec5SDimitry Andricdef : Pat<(rotl GR8:$src1, (i8 7)), (ROR8r1 GR8:$src1)>; 8130b57cec5SDimitry Andricdef : Pat<(rotl GR16:$src1, (i8 15)), (ROR16r1 GR16:$src1)>; 8140b57cec5SDimitry Andricdef : Pat<(rotl GR32:$src1, (i8 31)), (ROR32r1 GR32:$src1)>; 8150b57cec5SDimitry Andricdef : Pat<(rotl GR64:$src1, (i8 63)), (ROR64r1 GR64:$src1)>; 8160b57cec5SDimitry Andricdef : Pat<(rotr GR8:$src1, (i8 7)), (ROL8r1 GR8:$src1)>; 8170b57cec5SDimitry Andricdef : Pat<(rotr GR16:$src1, (i8 15)), (ROL16r1 GR16:$src1)>; 8180b57cec5SDimitry Andricdef : Pat<(rotr GR32:$src1, (i8 31)), (ROL32r1 GR32:$src1)>; 8190b57cec5SDimitry Andricdef : Pat<(rotr GR64:$src1, (i8 63)), (ROL64r1 GR64:$src1)>; 8200b57cec5SDimitry Andric 8210b57cec5SDimitry Andricdef : Pat<(store (rotl (loadi8 addr:$dst), (i8 7)), addr:$dst), 8220b57cec5SDimitry Andric (ROR8m1 addr:$dst)>; 8230b57cec5SDimitry Andricdef : Pat<(store (rotl (loadi16 addr:$dst), (i8 15)), addr:$dst), 8240b57cec5SDimitry Andric (ROR16m1 addr:$dst)>; 8250b57cec5SDimitry Andricdef : Pat<(store (rotl (loadi32 addr:$dst), (i8 31)), addr:$dst), 8260b57cec5SDimitry Andric (ROR32m1 addr:$dst)>; 8270b57cec5SDimitry Andricdef : Pat<(store (rotl (loadi64 addr:$dst), (i8 63)), addr:$dst), 8280b57cec5SDimitry Andric (ROR64m1 addr:$dst)>, Requires<[In64BitMode]>; 8290b57cec5SDimitry Andric 8300b57cec5SDimitry Andricdef : Pat<(store (rotr (loadi8 addr:$dst), (i8 7)), addr:$dst), 8310b57cec5SDimitry Andric (ROL8m1 addr:$dst)>; 8320b57cec5SDimitry Andricdef : Pat<(store (rotr (loadi16 addr:$dst), (i8 15)), addr:$dst), 8330b57cec5SDimitry Andric (ROL16m1 addr:$dst)>; 8340b57cec5SDimitry Andricdef : Pat<(store (rotr (loadi32 addr:$dst), (i8 31)), addr:$dst), 8350b57cec5SDimitry Andric (ROL32m1 addr:$dst)>; 8360b57cec5SDimitry Andricdef : Pat<(store (rotr (loadi64 addr:$dst), (i8 63)), addr:$dst), 8370b57cec5SDimitry Andric (ROL64m1 addr:$dst)>, Requires<[In64BitMode]>; 8380b57cec5SDimitry Andric 8390b57cec5SDimitry Andric// Sandy Bridge and newer Intel processors support faster rotates using 8400b57cec5SDimitry Andric// SHLD to avoid a partial flag update on the normal rotate instructions. 8410b57cec5SDimitry Andric// Use a pseudo so that TwoInstructionPass and register allocation will see 8420b57cec5SDimitry Andric// this as unary instruction. 8430b57cec5SDimitry Andriclet Predicates = [HasFastSHLDRotate], AddedComplexity = 5, 8440b57cec5SDimitry Andric Defs = [EFLAGS], isPseudo = 1, SchedRW = [WriteSHDrri], 8450b57cec5SDimitry Andric Constraints = "$src1 = $dst" in { 8460b57cec5SDimitry Andric def SHLDROT32ri : I<0, Pseudo, (outs GR32:$dst), 8470b57cec5SDimitry Andric (ins GR32:$src1, u8imm:$shamt), "", 8480b57cec5SDimitry Andric [(set GR32:$dst, (rotl GR32:$src1, (i8 imm:$shamt)))]>; 8490b57cec5SDimitry Andric def SHLDROT64ri : I<0, Pseudo, (outs GR64:$dst), 8500b57cec5SDimitry Andric (ins GR64:$src1, u8imm:$shamt), "", 8510b57cec5SDimitry Andric [(set GR64:$dst, (rotl GR64:$src1, (i8 imm:$shamt)))]>; 8520b57cec5SDimitry Andric 8530b57cec5SDimitry Andric def SHRDROT32ri : I<0, Pseudo, (outs GR32:$dst), 8540b57cec5SDimitry Andric (ins GR32:$src1, u8imm:$shamt), "", 8550b57cec5SDimitry Andric [(set GR32:$dst, (rotr GR32:$src1, (i8 imm:$shamt)))]>; 8560b57cec5SDimitry Andric def SHRDROT64ri : I<0, Pseudo, (outs GR64:$dst), 8570b57cec5SDimitry Andric (ins GR64:$src1, u8imm:$shamt), "", 8580b57cec5SDimitry Andric [(set GR64:$dst, (rotr GR64:$src1, (i8 imm:$shamt)))]>; 8590b57cec5SDimitry Andric} 8600b57cec5SDimitry Andric 8610b57cec5SDimitry Andricdef ROT32L2R_imm8 : SDNodeXForm<imm, [{ 8620b57cec5SDimitry Andric // Convert a ROTL shamt to a ROTR shamt on 32-bit integer. 8630b57cec5SDimitry Andric return getI8Imm(32 - N->getZExtValue(), SDLoc(N)); 8640b57cec5SDimitry Andric}]>; 8650b57cec5SDimitry Andric 8660b57cec5SDimitry Andricdef ROT64L2R_imm8 : SDNodeXForm<imm, [{ 8670b57cec5SDimitry Andric // Convert a ROTL shamt to a ROTR shamt on 64-bit integer. 8680b57cec5SDimitry Andric return getI8Imm(64 - N->getZExtValue(), SDLoc(N)); 8690b57cec5SDimitry Andric}]>; 8700b57cec5SDimitry Andric 8710b57cec5SDimitry Andric// NOTE: We use WriteShift for these rotates as they avoid the stalls 8720b57cec5SDimitry Andric// of many of the older x86 rotate instructions. 8730b57cec5SDimitry Andricmulticlass bmi_rotate<string asm, RegisterClass RC, X86MemOperand x86memop> { 8740b57cec5SDimitry Andriclet hasSideEffects = 0 in { 8750b57cec5SDimitry Andric def ri : Ii8<0xF0, MRMSrcReg, (outs RC:$dst), (ins RC:$src1, u8imm:$src2), 8760b57cec5SDimitry Andric !strconcat(asm, "\t{$src2, $src1, $dst|$dst, $src1, $src2}"), 8770b57cec5SDimitry Andric []>, TAXD, VEX, Sched<[WriteShift]>; 8780b57cec5SDimitry Andric let mayLoad = 1 in 8790b57cec5SDimitry Andric def mi : Ii8<0xF0, MRMSrcMem, (outs RC:$dst), 8800b57cec5SDimitry Andric (ins x86memop:$src1, u8imm:$src2), 8810b57cec5SDimitry Andric !strconcat(asm, "\t{$src2, $src1, $dst|$dst, $src1, $src2}"), 8820b57cec5SDimitry Andric []>, TAXD, VEX, Sched<[WriteShiftLd]>; 8830b57cec5SDimitry Andric} 8840b57cec5SDimitry Andric} 8850b57cec5SDimitry Andric 8860b57cec5SDimitry Andricmulticlass bmi_shift<string asm, RegisterClass RC, X86MemOperand x86memop> { 8870b57cec5SDimitry Andriclet hasSideEffects = 0 in { 8880b57cec5SDimitry Andric def rr : I<0xF7, MRMSrcReg4VOp3, (outs RC:$dst), (ins RC:$src1, RC:$src2), 8890b57cec5SDimitry Andric !strconcat(asm, "\t{$src2, $src1, $dst|$dst, $src1, $src2}"), []>, 8900b57cec5SDimitry Andric VEX, Sched<[WriteShift]>; 8910b57cec5SDimitry Andric let mayLoad = 1 in 8920b57cec5SDimitry Andric def rm : I<0xF7, MRMSrcMem4VOp3, 8930b57cec5SDimitry Andric (outs RC:$dst), (ins x86memop:$src1, RC:$src2), 8940b57cec5SDimitry Andric !strconcat(asm, "\t{$src2, $src1, $dst|$dst, $src1, $src2}"), []>, 8950b57cec5SDimitry Andric VEX, Sched<[WriteShift.Folded, 8960b57cec5SDimitry Andric // x86memop:$src1 8970b57cec5SDimitry Andric ReadDefault, ReadDefault, ReadDefault, ReadDefault, 8980b57cec5SDimitry Andric ReadDefault, 8990b57cec5SDimitry Andric // RC:$src2 9000b57cec5SDimitry Andric WriteShift.ReadAfterFold]>; 9010b57cec5SDimitry Andric} 9020b57cec5SDimitry Andric} 9030b57cec5SDimitry Andric 9040b57cec5SDimitry Andriclet Predicates = [HasBMI2] in { 9050b57cec5SDimitry Andric defm RORX32 : bmi_rotate<"rorx{l}", GR32, i32mem>; 9060b57cec5SDimitry Andric defm RORX64 : bmi_rotate<"rorx{q}", GR64, i64mem>, VEX_W; 9070b57cec5SDimitry Andric defm SARX32 : bmi_shift<"sarx{l}", GR32, i32mem>, T8XS; 9080b57cec5SDimitry Andric defm SARX64 : bmi_shift<"sarx{q}", GR64, i64mem>, T8XS, VEX_W; 9090b57cec5SDimitry Andric defm SHRX32 : bmi_shift<"shrx{l}", GR32, i32mem>, T8XD; 9100b57cec5SDimitry Andric defm SHRX64 : bmi_shift<"shrx{q}", GR64, i64mem>, T8XD, VEX_W; 9110b57cec5SDimitry Andric defm SHLX32 : bmi_shift<"shlx{l}", GR32, i32mem>, T8PD; 9120b57cec5SDimitry Andric defm SHLX64 : bmi_shift<"shlx{q}", GR64, i64mem>, T8PD, VEX_W; 9130b57cec5SDimitry Andric 9140b57cec5SDimitry Andric // Prefer RORX which is non-destructive and doesn't update EFLAGS. 9150b57cec5SDimitry Andric let AddedComplexity = 10 in { 9160b57cec5SDimitry Andric def : Pat<(rotr GR32:$src, (i8 imm:$shamt)), 9170b57cec5SDimitry Andric (RORX32ri GR32:$src, imm:$shamt)>; 9180b57cec5SDimitry Andric def : Pat<(rotr GR64:$src, (i8 imm:$shamt)), 9190b57cec5SDimitry Andric (RORX64ri GR64:$src, imm:$shamt)>; 9200b57cec5SDimitry Andric 9210b57cec5SDimitry Andric def : Pat<(rotl GR32:$src, (i8 imm:$shamt)), 9220b57cec5SDimitry Andric (RORX32ri GR32:$src, (ROT32L2R_imm8 imm:$shamt))>; 9230b57cec5SDimitry Andric def : Pat<(rotl GR64:$src, (i8 imm:$shamt)), 9240b57cec5SDimitry Andric (RORX64ri GR64:$src, (ROT64L2R_imm8 imm:$shamt))>; 9250b57cec5SDimitry Andric } 9260b57cec5SDimitry Andric 9270b57cec5SDimitry Andric def : Pat<(rotr (loadi32 addr:$src), (i8 imm:$shamt)), 9280b57cec5SDimitry Andric (RORX32mi addr:$src, imm:$shamt)>; 9290b57cec5SDimitry Andric def : Pat<(rotr (loadi64 addr:$src), (i8 imm:$shamt)), 9300b57cec5SDimitry Andric (RORX64mi addr:$src, imm:$shamt)>; 9310b57cec5SDimitry Andric 9320b57cec5SDimitry Andric def : Pat<(rotl (loadi32 addr:$src), (i8 imm:$shamt)), 9330b57cec5SDimitry Andric (RORX32mi addr:$src, (ROT32L2R_imm8 imm:$shamt))>; 9340b57cec5SDimitry Andric def : Pat<(rotl (loadi64 addr:$src), (i8 imm:$shamt)), 9350b57cec5SDimitry Andric (RORX64mi addr:$src, (ROT64L2R_imm8 imm:$shamt))>; 9360b57cec5SDimitry Andric 9370b57cec5SDimitry Andric // Prefer SARX/SHRX/SHLX over SAR/SHR/SHL with variable shift BUT not 9380b57cec5SDimitry Andric // immediate shift, i.e. the following code is considered better 9390b57cec5SDimitry Andric // 9400b57cec5SDimitry Andric // mov %edi, %esi 9410b57cec5SDimitry Andric // shl $imm, %esi 9420b57cec5SDimitry Andric // ... %edi, ... 9430b57cec5SDimitry Andric // 9440b57cec5SDimitry Andric // than 9450b57cec5SDimitry Andric // 9460b57cec5SDimitry Andric // movb $imm, %sil 9470b57cec5SDimitry Andric // shlx %sil, %edi, %esi 9480b57cec5SDimitry Andric // ... %edi, ... 9490b57cec5SDimitry Andric // 9500b57cec5SDimitry Andric let AddedComplexity = 1 in { 9510b57cec5SDimitry Andric def : Pat<(sra GR32:$src1, GR8:$src2), 9520b57cec5SDimitry Andric (SARX32rr GR32:$src1, 9530b57cec5SDimitry Andric (INSERT_SUBREG 9540b57cec5SDimitry Andric (i32 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9550b57cec5SDimitry Andric def : Pat<(sra GR64:$src1, GR8:$src2), 9560b57cec5SDimitry Andric (SARX64rr GR64:$src1, 9570b57cec5SDimitry Andric (INSERT_SUBREG 9580b57cec5SDimitry Andric (i64 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9590b57cec5SDimitry Andric 9600b57cec5SDimitry Andric def : Pat<(srl GR32:$src1, GR8:$src2), 9610b57cec5SDimitry Andric (SHRX32rr GR32:$src1, 9620b57cec5SDimitry Andric (INSERT_SUBREG 9630b57cec5SDimitry Andric (i32 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9640b57cec5SDimitry Andric def : Pat<(srl GR64:$src1, GR8:$src2), 9650b57cec5SDimitry Andric (SHRX64rr GR64:$src1, 9660b57cec5SDimitry Andric (INSERT_SUBREG 9670b57cec5SDimitry Andric (i64 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9680b57cec5SDimitry Andric 9690b57cec5SDimitry Andric def : Pat<(shl GR32:$src1, GR8:$src2), 9700b57cec5SDimitry Andric (SHLX32rr GR32:$src1, 9710b57cec5SDimitry Andric (INSERT_SUBREG 9720b57cec5SDimitry Andric (i32 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9730b57cec5SDimitry Andric def : Pat<(shl GR64:$src1, GR8:$src2), 9740b57cec5SDimitry Andric (SHLX64rr GR64:$src1, 9750b57cec5SDimitry Andric (INSERT_SUBREG 9760b57cec5SDimitry Andric (i64 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9770b57cec5SDimitry Andric } 9780b57cec5SDimitry Andric 9790b57cec5SDimitry Andric // We prefer to use 9800b57cec5SDimitry Andric // mov (%ecx), %esi 9810b57cec5SDimitry Andric // shl $imm, $esi 9820b57cec5SDimitry Andric // 9830b57cec5SDimitry Andric // over 9840b57cec5SDimitry Andric // 9850b57cec5SDimitry Andric // movb $imm, %al 9860b57cec5SDimitry Andric // shlx %al, (%ecx), %esi 9870b57cec5SDimitry Andric // 9880b57cec5SDimitry Andric // This priority is enforced by IsProfitableToFoldLoad. 9890b57cec5SDimitry Andric def : Pat<(sra (loadi32 addr:$src1), GR8:$src2), 9900b57cec5SDimitry Andric (SARX32rm addr:$src1, 9910b57cec5SDimitry Andric (INSERT_SUBREG 9920b57cec5SDimitry Andric (i32 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9930b57cec5SDimitry Andric def : Pat<(sra (loadi64 addr:$src1), GR8:$src2), 9940b57cec5SDimitry Andric (SARX64rm addr:$src1, 9950b57cec5SDimitry Andric (INSERT_SUBREG 9960b57cec5SDimitry Andric (i64 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 9970b57cec5SDimitry Andric 9980b57cec5SDimitry Andric def : Pat<(srl (loadi32 addr:$src1), GR8:$src2), 9990b57cec5SDimitry Andric (SHRX32rm addr:$src1, 10000b57cec5SDimitry Andric (INSERT_SUBREG 10010b57cec5SDimitry Andric (i32 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 10020b57cec5SDimitry Andric def : Pat<(srl (loadi64 addr:$src1), GR8:$src2), 10030b57cec5SDimitry Andric (SHRX64rm addr:$src1, 10040b57cec5SDimitry Andric (INSERT_SUBREG 10050b57cec5SDimitry Andric (i64 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 10060b57cec5SDimitry Andric 10070b57cec5SDimitry Andric def : Pat<(shl (loadi32 addr:$src1), GR8:$src2), 10080b57cec5SDimitry Andric (SHLX32rm addr:$src1, 10090b57cec5SDimitry Andric (INSERT_SUBREG 10100b57cec5SDimitry Andric (i32 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 10110b57cec5SDimitry Andric def : Pat<(shl (loadi64 addr:$src1), GR8:$src2), 10120b57cec5SDimitry Andric (SHLX64rm addr:$src1, 10130b57cec5SDimitry Andric (INSERT_SUBREG 10140b57cec5SDimitry Andric (i64 (IMPLICIT_DEF)), GR8:$src2, sub_8bit))>; 10150b57cec5SDimitry Andric} 1016*5ffd83dbSDimitry Andric 1017*5ffd83dbSDimitry Andricdef : Pat<(rotl GR8:$src1, (i8 relocImm:$src2)), 1018*5ffd83dbSDimitry Andric (ROL8ri GR8:$src1, relocImm:$src2)>; 1019*5ffd83dbSDimitry Andricdef : Pat<(rotl GR16:$src1, (i8 relocImm:$src2)), 1020*5ffd83dbSDimitry Andric (ROL16ri GR16:$src1, relocImm:$src2)>; 1021*5ffd83dbSDimitry Andricdef : Pat<(rotl GR32:$src1, (i8 relocImm:$src2)), 1022*5ffd83dbSDimitry Andric (ROL32ri GR32:$src1, relocImm:$src2)>; 1023*5ffd83dbSDimitry Andricdef : Pat<(rotl GR64:$src1, (i8 relocImm:$src2)), 1024*5ffd83dbSDimitry Andric (ROL64ri GR64:$src1, relocImm:$src2)>; 1025*5ffd83dbSDimitry Andric 1026*5ffd83dbSDimitry Andricdef : Pat<(rotr GR8:$src1, (i8 relocImm:$src2)), 1027*5ffd83dbSDimitry Andric (ROR8ri GR8:$src1, relocImm:$src2)>; 1028*5ffd83dbSDimitry Andricdef : Pat<(rotr GR16:$src1, (i8 relocImm:$src2)), 1029*5ffd83dbSDimitry Andric (ROR16ri GR16:$src1, relocImm:$src2)>; 1030*5ffd83dbSDimitry Andricdef : Pat<(rotr GR32:$src1, (i8 relocImm:$src2)), 1031*5ffd83dbSDimitry Andric (ROR32ri GR32:$src1, relocImm:$src2)>; 1032*5ffd83dbSDimitry Andricdef : Pat<(rotr GR64:$src1, (i8 relocImm:$src2)), 1033*5ffd83dbSDimitry Andric (ROR64ri GR64:$src1, relocImm:$src2)>; 1034