diff --git a/llvm/lib/Target/LoongArch/AsmParser/LoongArchAsmParser.cpp b/llvm/lib/Target/LoongArch/AsmParser/LoongArchAsmParser.cpp --- a/llvm/lib/Target/LoongArch/AsmParser/LoongArchAsmParser.cpp +++ b/llvm/lib/Target/LoongArch/AsmParser/LoongArchAsmParser.cpp @@ -236,12 +236,24 @@ VK == LoongArchMCExpr::VK_LoongArch_None; } + bool isUImm1() const { return isUImm<1>(); } bool isUImm2() const { return isUImm<2>(); } bool isUImm2plus1() const { return isUImm<2, 1>(); } bool isUImm3() const { return isUImm<3>(); } + bool isUImm4() const { return isUImm<4>(); } + bool isSImm5() const { return isSImm<5>(); } bool isUImm5() const { return isUImm<5>(); } bool isUImm6() const { return isUImm<6>(); } + bool isUImm7() const { return isUImm<7>(); } + bool isSImm8() const { return isSImm<8>(); } + bool isSImm8lsl1() const { return isSImm<8, 1>(); } + bool isSImm8lsl2() const { return isSImm<8, 2>(); } + bool isSImm8lsl3() const { return isSImm<8, 3>(); } bool isUImm8() const { return isUImm<8>(); } + bool isSImm9lsl3() const { return isSImm<9, 3>(); } + bool isSImm10() const { return isSImm<10>(); } + bool isSImm10lsl2() const { return isSImm<10, 2>(); } + bool isSImm11lsl1() const { return isSImm<11, 1>(); } bool isSImm12() const { return isSImm<12>(); } bool isSImm12addlike() const { @@ -305,6 +317,7 @@ IsValidKind; } + bool isSImm13() const { return isSImm<13>(); } bool isUImm14() const { return isUImm<14>(); } bool isUImm15() const { return isUImm<15>(); } @@ -1316,6 +1329,9 @@ "$rd must be different from both $rk and $rj"); case Match_RequiresLAORdDifferRj: return Error(Operands[1]->getStartLoc(), "$rd must be different from $rj"); + case Match_InvalidUImm1: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, + /*Upper=*/(1 << 1) - 1); case Match_InvalidUImm2: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, /*Upper=*/(1 << 2) - 1); @@ -1325,12 +1341,18 @@ case Match_InvalidUImm3: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, /*Upper=*/(1 << 3) - 1); + case Match_InvalidUImm4: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, + /*Upper=*/(1 << 4) - 1); case Match_InvalidUImm5: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, /*Upper=*/(1 << 5) - 1); case Match_InvalidUImm6: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, /*Upper=*/(1 << 6) - 1); + case Match_InvalidUImm7: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, + /*Upper=*/(1 << 7) - 1); case Match_InvalidUImm8: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, /*Upper=*/(1 << 8) - 1); @@ -1346,6 +1368,39 @@ case Match_InvalidUImm15: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/0, /*Upper=*/(1 << 15) - 1); + case Match_InvalidSImm5: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/-(1 << 4), + /*Upper=*/(1 << 4) - 1); + case Match_InvalidSImm8: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/-(1 << 7), + /*Upper=*/(1 << 7) - 1); + case Match_InvalidSImm8lsl1: + return generateImmOutOfRangeError( + Operands, ErrorInfo, /*Lower=*/-(1 << 8), /*Upper=*/(1 << 8) - 2, + "immediate must be a multiple of 2 in the range"); + case Match_InvalidSImm8lsl2: + return generateImmOutOfRangeError( + Operands, ErrorInfo, /*Lower=*/-(1 << 9), /*Upper=*/(1 << 9) - 4, + "immediate must be a multiple of 4 in the range"); + case Match_InvalidSImm10: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/-(1 << 9), + /*Upper=*/(1 << 9) - 1); + case Match_InvalidSImm8lsl3: + return generateImmOutOfRangeError( + Operands, ErrorInfo, /*Lower=*/-(1 << 10), /*Upper=*/(1 << 10) - 8, + "immediate must be a multiple of 8 in the range"); + case Match_InvalidSImm9lsl3: + return generateImmOutOfRangeError( + Operands, ErrorInfo, /*Lower=*/-(1 << 11), /*Upper=*/(1 << 11) - 8, + "immediate must be a multiple of 8 in the range"); + case Match_InvalidSImm10lsl2: + return generateImmOutOfRangeError( + Operands, ErrorInfo, /*Lower=*/-(1 << 11), /*Upper=*/(1 << 11) - 4, + "immediate must be a multiple of 4 in the range"); + case Match_InvalidSImm11lsl1: + return generateImmOutOfRangeError( + Operands, ErrorInfo, /*Lower=*/-(1 << 11), /*Upper=*/(1 << 11) - 2, + "immediate must be a multiple of 2 in the range"); case Match_InvalidSImm12: return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/-(1 << 11), /*Upper=*/(1 << 11) - 1); @@ -1361,6 +1416,9 @@ /*Upper=*/(1 << 11) - 1, "operand must be a symbol with modifier (e.g. %pc64_hi12) or an " "integer in the range"); + case Match_InvalidSImm13: + return generateImmOutOfRangeError(Operands, ErrorInfo, /*Lower=*/-(1 << 12), + /*Upper=*/(1 << 12) - 1); case Match_InvalidSImm14lsl2: return generateImmOutOfRangeError( Operands, ErrorInfo, /*Lower=*/-(1 << 15), /*Upper=*/(1 << 15) - 4, diff --git a/llvm/lib/Target/LoongArch/Disassembler/LoongArchDisassembler.cpp b/llvm/lib/Target/LoongArch/Disassembler/LoongArchDisassembler.cpp --- a/llvm/lib/Target/LoongArch/Disassembler/LoongArchDisassembler.cpp +++ b/llvm/lib/Target/LoongArch/Disassembler/LoongArchDisassembler.cpp @@ -100,6 +100,15 @@ return MCDisassembler::Success; } +static DecodeStatus DecodeLSX128RegisterClass(MCInst &Inst, uint64_t RegNo, + uint64_t Address, + const MCDisassembler *Decoder) { + if (RegNo >= 32) + return MCDisassembler::Fail; + Inst.addOperand(MCOperand::createReg(LoongArch::VR0 + RegNo)); + return MCDisassembler::Success; +} + template static DecodeStatus decodeUImmOperand(MCInst &Inst, uint64_t Imm, int64_t Address, diff --git a/llvm/lib/Target/LoongArch/LoongArchInstrInfo.td b/llvm/lib/Target/LoongArch/LoongArchInstrInfo.td --- a/llvm/lib/Target/LoongArch/LoongArchInstrInfo.td +++ b/llvm/lib/Target/LoongArch/LoongArchInstrInfo.td @@ -182,6 +182,10 @@ let ParserMatchClass = ImmAsmOperand<"", 32, "">; } +def uimm1 : Operand { + let ParserMatchClass = UImmAsmOperand<1>; +} + def uimm2 : Operand, ImmLeaf(Imm);}]> { let ParserMatchClass = UImmAsmOperand<2>; } @@ -197,6 +201,10 @@ let ParserMatchClass = UImmAsmOperand<3>; } +def uimm4 : Operand { + let ParserMatchClass = UImmAsmOperand<4>; +} + def uimm5 : Operand, ImmLeaf(Imm);}]> { let ParserMatchClass = UImmAsmOperand<5>; } @@ -205,6 +213,10 @@ let ParserMatchClass = UImmAsmOperand<6>; } +def uimm7 : Operand { + let ParserMatchClass = UImmAsmOperand<7>; +} + def uimm8 : Operand, ImmLeaf(Imm);}]> { let ParserMatchClass = UImmAsmOperand<8>; } @@ -232,6 +244,46 @@ let ParserMatchClass = UImmAsmOperand<15>; } +def simm5 : Operand { + let ParserMatchClass = SImmAsmOperand<5>; + let DecoderMethod = "decodeSImmOperand<5>"; +} + +def simm8 : Operand { + let ParserMatchClass = SImmAsmOperand<8>; + let DecoderMethod = "decodeSImmOperand<8>"; +} + +foreach I = [1, 2, 3] in { +def simm8_lsl # I : Operand { + let ParserMatchClass = SImmAsmOperand<8, "lsl" # I>; + let EncoderMethod = "getImmOpValueAsr<" # I # ">"; + let DecoderMethod = "decodeSImmOperand<8," # I # ">"; +} +} + +def simm9_lsl3 : Operand { + let ParserMatchClass = SImmAsmOperand<9, "lsl3">; + let EncoderMethod = "getImmOpValueAsr<3>"; + let DecoderMethod = "decodeSImmOperand<9, 3>"; +} + +def simm10 : Operand { + let ParserMatchClass = SImmAsmOperand<10>; +} + +def simm10_lsl2 : Operand { + let ParserMatchClass = SImmAsmOperand<10, "lsl2">; + let EncoderMethod = "getImmOpValueAsr<2>"; + let DecoderMethod = "decodeSImmOperand<10, 2>"; +} + +def simm11_lsl1 : Operand { + let ParserMatchClass = SImmAsmOperand<11, "lsl1">; + let EncoderMethod = "getImmOpValueAsr<1>"; + let DecoderMethod = "decodeSImmOperand<11, 1>"; +} + class SImm12Operand : Operand, ImmLeaf (Imm);}]> { let DecoderMethod = "decodeSImmOperand<12>"; @@ -249,10 +301,15 @@ let ParserMatchClass = SImmAsmOperand<12, "lu52id">; } +def simm13 : Operand { + let ParserMatchClass = SImmAsmOperand<13>; + let DecoderMethod = "decodeSImmOperand<13>"; +} + def simm14_lsl2 : Operand, ImmLeaf(Imm);}]> { let ParserMatchClass = SImmAsmOperand<14, "lsl2">; - let EncoderMethod = "getImmOpValueAsr2"; + let EncoderMethod = "getImmOpValueAsr<2>"; let DecoderMethod = "decodeSImmOperand<14, 2>"; } @@ -264,13 +321,13 @@ def simm16_lsl2 : Operand, ImmLeaf(Imm>>2);}]> { let ParserMatchClass = SImmAsmOperand<16, "lsl2">; - let EncoderMethod = "getImmOpValueAsr2"; + let EncoderMethod = "getImmOpValueAsr<2>"; let DecoderMethod = "decodeSImmOperand<16, 2>"; } def simm16_lsl2_br : Operand { let ParserMatchClass = SImmAsmOperand<16, "lsl2">; - let EncoderMethod = "getImmOpValueAsr2"; + let EncoderMethod = "getImmOpValueAsr<2>"; let DecoderMethod = "decodeSImmOperand<16, 2>"; } @@ -296,7 +353,7 @@ def simm21_lsl2 : Operand { let ParserMatchClass = SImmAsmOperand<21, "lsl2">; - let EncoderMethod = "getImmOpValueAsr2"; + let EncoderMethod = "getImmOpValueAsr<2>"; let DecoderMethod = "decodeSImmOperand<21, 2>"; } @@ -311,7 +368,7 @@ // A symbol or an imm used in B/PseudoBR. def simm26_b : Operand { let ParserMatchClass = SImm26OperandB; - let EncoderMethod = "getImmOpValueAsr2"; + let EncoderMethod = "getImmOpValueAsr<2>"; let DecoderMethod = "decodeSImmOperand<26, 2>"; } @@ -326,7 +383,7 @@ // A symbol or an imm used in BL/PseudoCALL/PseudoTAIL. def simm26_symbol : Operand { let ParserMatchClass = SImm26OperandBL; - let EncoderMethod = "getImmOpValueAsr2"; + let EncoderMethod = "getImmOpValueAsr<2>"; let DecoderMethod = "decodeSImmOperand<26, 2>"; } @@ -468,6 +525,7 @@ include "LoongArchInstrFormats.td" include "LoongArchFloatInstrFormats.td" +include "LoongArchLSXInstrFormats.td" //===----------------------------------------------------------------------===// // Instruction Class Templates @@ -1950,3 +2008,8 @@ def : Pat<(int_loongarch_ldpte_d GPR:$rj, timm:$imm8), (LDPTE GPR:$rj, uimm8:$imm8)>; } // Predicates = [IsLA64] + +//===----------------------------------------------------------------------===// +// LSX Instructions +//===----------------------------------------------------------------------===// +include "LoongArchLSXInstrInfo.td" diff --git a/llvm/lib/Target/LoongArch/LoongArchLSXInstrFormats.td b/llvm/lib/Target/LoongArch/LoongArchLSXInstrFormats.td new file mode 100644 --- /dev/null +++ b/llvm/lib/Target/LoongArch/LoongArchLSXInstrFormats.td @@ -0,0 +1,486 @@ +// LoongArchLSXInstrFormats.td - LoongArch LSX Instr Formats -*- tablegen -*-=// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +//===----------------------------------------------------------------------===// +// Describe LoongArch LSX instructions format +// +// opcode - operation code. +// vd/rd/cd - destination register operand. +// {r/v}{j/k} - source register operand. +// immN - immediate data operand. +// +//===----------------------------------------------------------------------===// + +// 1RI13-type +// +class Fmt1RI13_VI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<13> imm13; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{17-5} = imm13; + let Inst{4-0} = vd; +} + +// 2R-type +// +class Fmt2R_VV op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt2R_VR op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// +class Fmt2R_CV op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> vj; + bits<3> cd; + + let Inst{31-0} = op; + let Inst{9-5} = vj; + let Inst{2-0} = cd; +} + +// 2RI1-type +// +class Fmt2RI1_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<1> imm1; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{10} = imm1; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI1_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<1> imm1; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{10} = imm1; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI1_RVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<1> imm1; + bits<5> vj; + bits<5> rd; + + let Inst{31-0} = op; + let Inst{10} = imm1; + let Inst{9-5} = vj; + let Inst{4-0} = rd; +} + +// 2RI2-type +// +class Fmt2RI2_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<2> imm2; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{11-10} = imm2; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI2_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<2> imm2; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{11-10} = imm2; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI2_RVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<2> imm2; + bits<5> vj; + bits<5> rd; + + let Inst{31-0} = op; + let Inst{11-10} = imm2; + let Inst{9-5} = vj; + let Inst{4-0} = rd; +} + +// 2RI3-type +// +class Fmt2RI3_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<3> imm3; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{12-10} = imm3; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI3_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<3> imm3; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{12-10} = imm3; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI3_RVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<3> imm3; + bits<5> vj; + bits<5> rd; + + let Inst{31-0} = op; + let Inst{12-10} = imm3; + let Inst{9-5} = vj; + let Inst{4-0} = rd; +} + +// 2RI4-type +// +class Fmt2RI4_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<4> imm4; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{13-10} = imm4; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI4_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<4> imm4; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{13-10} = imm4; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// +class Fmt2RI4_RVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<4> imm4; + bits<5> vj; + bits<5> rd; + + let Inst{31-0} = op; + let Inst{13-10} = imm4; + let Inst{9-5} = vj; + let Inst{4-0} = rd; +} + +// 2RI5-type +// +class Fmt2RI5_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> imm5; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{14-10} = imm5; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// 2RI6-type +// +class Fmt2RI6_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<6> imm6; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{15-10} = imm6; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// 2RI7-type +// +class Fmt2RI7_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<7> imm7; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{16-10} = imm7; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// 2RI8-type +// +class Fmt2RI8_VVI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<8> imm8; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{17-10} = imm8; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// 2RI8I1-type +// +class Fmt2RI8I1_VRII op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<1> imm1; + bits<8> imm8; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{18} = imm1; + let Inst{17-10} = imm8; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 2RI8I2-type +// +class Fmt2RI8I2_VRII op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<2> imm2; + bits<8> imm8; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{19-18} = imm2; + let Inst{17-10} = imm8; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 2RI8I3-type +// +class Fmt2RI8I3_VRII op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<3> imm3; + bits<8> imm8; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{20-18} = imm3; + let Inst{17-10} = imm8; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 2RI8I4-type +// +class Fmt2RI8I4_VRII op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<4> imm4; + bits<8> imm8; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{21-18} = imm4; + let Inst{17-10} = imm8; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} +// 2RI9-type +// +class Fmt2RI9_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<9> imm9; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{18-10} = imm9; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 2RI10-type +// +class Fmt2RI10_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<10> imm10; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{19-10} = imm10; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 2RI11-type +// +class Fmt2RI11_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<11> imm11; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{20-10} = imm11; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 2RI12-type +// +class Fmt2RI12_VRI op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<12> imm12; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{21-10} = imm12; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 3R-type +// +class Fmt3R_VVV op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> vk; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{14-10} = vk; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt3R_VVR op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> rk; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{14-10} = rk; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} + +// +class Fmt3R_VRR op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> rk; + bits<5> rj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{14-10} = rk; + let Inst{9-5} = rj; + let Inst{4-0} = vd; +} + +// 4R-type +// +class Fmt4R_VVVV op, dag outs, dag ins, string opcstr, string opnstr, + list pattern = []> + : LAInst { + bits<5> va; + bits<5> vk; + bits<5> vj; + bits<5> vd; + + let Inst{31-0} = op; + let Inst{19-15} = va; + let Inst{14-10} = vk; + let Inst{9-5} = vj; + let Inst{4-0} = vd; +} diff --git a/llvm/lib/Target/LoongArch/LoongArchLSXInstrInfo.td b/llvm/lib/Target/LoongArch/LoongArchLSXInstrInfo.td new file mode 100644 --- /dev/null +++ b/llvm/lib/Target/LoongArch/LoongArchLSXInstrInfo.td @@ -0,0 +1,1008 @@ +//===- LoongArchLSXInstrInfo.td - LoongArch LSX instructions -*- tablegen -*-=// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file describes the SIMD extension instructions. +// +//===----------------------------------------------------------------------===// + +//===----------------------------------------------------------------------===// +// Instruction class templates +//===----------------------------------------------------------------------===// + +class LSX1RI13_VI op, Operand ImmOpnd = simm13> + : Fmt1RI13_VI; + +class LSX2R_VV op> + : Fmt2R_VV; + +class LSX2R_VR op> + : Fmt2R_VR; + +class LSX2R_CV op> + : Fmt2R_CV; + +class LSX2RI1_VVI op, Operand ImmOpnd = uimm1> + : Fmt2RI1_VVI; + +class LSX2RI1_VRI op, Operand ImmOpnd = uimm1> + : Fmt2RI1_VRI; + +class LSX2RI1_RVI op, Operand ImmOpnd = uimm1> + : Fmt2RI1_RVI; + +class LSX2RI2_VVI op, Operand ImmOpnd = uimm2> + : Fmt2RI2_VVI; + +class LSX2RI2_VRI op, Operand ImmOpnd = uimm2> + : Fmt2RI2_VRI; + +class LSX2RI2_RVI op, Operand ImmOpnd = uimm2> + : Fmt2RI2_RVI; + +class LSX2RI3_VVI op, Operand ImmOpnd = uimm3> + : Fmt2RI3_VVI; + +class LSX2RI3_VRI op, Operand ImmOpnd = uimm3> + : Fmt2RI3_VRI; + +class LSX2RI3_RVI op, Operand ImmOpnd = uimm3> + : Fmt2RI3_RVI; + +class LSX2RI4_VVI op, Operand ImmOpnd = uimm4> + : Fmt2RI4_VVI; + +class LSX2RI4_VRI op, Operand ImmOpnd = uimm4> + : Fmt2RI4_VRI; + +class LSX2RI4_RVI op, Operand ImmOpnd = uimm4> + : Fmt2RI4_RVI; + +class LSX2RI5_VVI op, Operand ImmOpnd = uimm5> + : Fmt2RI5_VVI; + +class LSX2RI6_VVI op, Operand ImmOpnd = uimm6> + : Fmt2RI6_VVI; + +class LSX2RI8_VVI op, Operand ImmOpnd = uimm8> + : Fmt2RI8_VVI; + +class LSX2RI8I1_VRII op, Operand ImmOpnd = simm8, + Operand IdxOpnd = uimm1> + : Fmt2RI8I1_VRII; +class LSX2RI8I2_VRII op, Operand ImmOpnd = simm8, + Operand IdxOpnd = uimm2> + : Fmt2RI8I2_VRII; +class LSX2RI8I3_VRII op, Operand ImmOpnd = simm8, + Operand IdxOpnd = uimm3> + : Fmt2RI8I3_VRII; +class LSX2RI8I4_VRII op, Operand ImmOpnd = simm8, + Operand IdxOpnd = uimm4> + : Fmt2RI8I4_VRII; + +class LSX2RI9_VRI op, Operand ImmOpnd = simm9_lsl3> + : Fmt2RI9_VRI; + +class LSX2RI10_VRI op, Operand ImmOpnd = simm10_lsl2> + : Fmt2RI10_VRI; + +class LSX2RI11_VRI op, Operand ImmOpnd = simm11_lsl1> + : Fmt2RI11_VRI; + +class LSX2RI12_VRI op, Operand ImmOpnd = simm12> + : Fmt2RI12_VRI; + +class LSX3R_VVV op> + : Fmt3R_VVV; + +class LSX3R_VVR op> + : Fmt3R_VVR; + +class LSX3R_VRR op> + : Fmt3R_VRR; + +class LSX4R_VVVV op> + : Fmt4R_VVVV; + +let Constraints = "$vd = $dst" in { + +class LSX2RI4_VVVI op, Operand ImmOpnd = uimm4> + : Fmt2RI4_VVI; +class LSX2RI5_VVVI op, Operand ImmOpnd = uimm5> + : Fmt2RI5_VVI; +class LSX2RI6_VVVI op, Operand ImmOpnd = uimm6> + : Fmt2RI6_VVI; +class LSX2RI7_VVVI op, Operand ImmOpnd = uimm7> + : Fmt2RI7_VVI; + +class LSX2RI8_VVVI op, Operand ImmOpnd = uimm8> + : Fmt2RI8_VVI; + +class LSX3R_VVVV op> + : Fmt3R_VVV; + +} // Constraints = "$vd = $dst" + +//===----------------------------------------------------------------------===// +// Instructions +//===----------------------------------------------------------------------===// + +let Predicates = [HasExtLSX] in { + +def VADD_B : LSX3R_VVV<0x700a0000>; +def VADD_H : LSX3R_VVV<0x700a8000>; +def VADD_W : LSX3R_VVV<0x700b0000>; +def VADD_D : LSX3R_VVV<0x700b8000>; +def VADD_Q : LSX3R_VVV<0x712d0000>; + +def VSUB_B : LSX3R_VVV<0x700c0000>; +def VSUB_H : LSX3R_VVV<0x700c8000>; +def VSUB_W : LSX3R_VVV<0x700d0000>; +def VSUB_D : LSX3R_VVV<0x700d8000>; +def VSUB_Q : LSX3R_VVV<0x712d8000>; + +def VADDI_BU : LSX2RI5_VVI<0x728a0000>; +def VADDI_HU : LSX2RI5_VVI<0x728a8000>; +def VADDI_WU : LSX2RI5_VVI<0x728b0000>; +def VADDI_DU : LSX2RI5_VVI<0x728b8000>; + +def VSUBI_BU : LSX2RI5_VVI<0x728c0000>; +def VSUBI_HU : LSX2RI5_VVI<0x728c8000>; +def VSUBI_WU : LSX2RI5_VVI<0x728d0000>; +def VSUBI_DU : LSX2RI5_VVI<0x728d8000>; + +def VNEG_B : LSX2R_VV<0x729c3000>; +def VNEG_H : LSX2R_VV<0x729c3400>; +def VNEG_W : LSX2R_VV<0x729c3800>; +def VNEG_D : LSX2R_VV<0x729c3c00>; + +def VSADD_B : LSX3R_VVV<0x70460000>; +def VSADD_H : LSX3R_VVV<0x70468000>; +def VSADD_W : LSX3R_VVV<0x70470000>; +def VSADD_D : LSX3R_VVV<0x70478000>; +def VSADD_BU : LSX3R_VVV<0x704a0000>; +def VSADD_HU : LSX3R_VVV<0x704a8000>; +def VSADD_WU : LSX3R_VVV<0x704b0000>; +def VSADD_DU : LSX3R_VVV<0x704b8000>; + +def VSSUB_B : LSX3R_VVV<0x70480000>; +def VSSUB_H : LSX3R_VVV<0x70488000>; +def VSSUB_W : LSX3R_VVV<0x70490000>; +def VSSUB_D : LSX3R_VVV<0x70498000>; +def VSSUB_BU : LSX3R_VVV<0x704c0000>; +def VSSUB_HU : LSX3R_VVV<0x704c8000>; +def VSSUB_WU : LSX3R_VVV<0x704d0000>; +def VSSUB_DU : LSX3R_VVV<0x704d8000>; + +def VHADDW_H_B : LSX3R_VVV<0x70540000>; +def VHADDW_W_H : LSX3R_VVV<0x70548000>; +def VHADDW_D_W : LSX3R_VVV<0x70550000>; +def VHADDW_Q_D : LSX3R_VVV<0x70558000>; +def VHADDW_HU_BU : LSX3R_VVV<0x70580000>; +def VHADDW_WU_HU : LSX3R_VVV<0x70588000>; +def VHADDW_DU_WU : LSX3R_VVV<0x70590000>; +def VHADDW_QU_DU : LSX3R_VVV<0x70598000>; + +def VHSUBW_H_B : LSX3R_VVV<0x70560000>; +def VHSUBW_W_H : LSX3R_VVV<0x70568000>; +def VHSUBW_D_W : LSX3R_VVV<0x70570000>; +def VHSUBW_Q_D : LSX3R_VVV<0x70578000>; +def VHSUBW_HU_BU : LSX3R_VVV<0x705a0000>; +def VHSUBW_WU_HU : LSX3R_VVV<0x705a8000>; +def VHSUBW_DU_WU : LSX3R_VVV<0x705b0000>; +def VHSUBW_QU_DU : LSX3R_VVV<0x705b8000>; + +def VADDWEV_H_B : LSX3R_VVV<0x701e0000>; +def VADDWEV_W_H : LSX3R_VVV<0x701e8000>; +def VADDWEV_D_W : LSX3R_VVV<0x701f0000>; +def VADDWEV_Q_D : LSX3R_VVV<0x701f8000>; +def VADDWOD_H_B : LSX3R_VVV<0x70220000>; +def VADDWOD_W_H : LSX3R_VVV<0x70228000>; +def VADDWOD_D_W : LSX3R_VVV<0x70230000>; +def VADDWOD_Q_D : LSX3R_VVV<0x70238000>; + +def VSUBWEV_H_B : LSX3R_VVV<0x70200000>; +def VSUBWEV_W_H : LSX3R_VVV<0x70208000>; +def VSUBWEV_D_W : LSX3R_VVV<0x70210000>; +def VSUBWEV_Q_D : LSX3R_VVV<0x70218000>; +def VSUBWOD_H_B : LSX3R_VVV<0x70240000>; +def VSUBWOD_W_H : LSX3R_VVV<0x70248000>; +def VSUBWOD_D_W : LSX3R_VVV<0x70250000>; +def VSUBWOD_Q_D : LSX3R_VVV<0x70258000>; + +def VADDWEV_H_BU : LSX3R_VVV<0x702e0000>; +def VADDWEV_W_HU : LSX3R_VVV<0x702e8000>; +def VADDWEV_D_WU : LSX3R_VVV<0x702f0000>; +def VADDWEV_Q_DU : LSX3R_VVV<0x702f8000>; +def VADDWOD_H_BU : LSX3R_VVV<0x70320000>; +def VADDWOD_W_HU : LSX3R_VVV<0x70328000>; +def VADDWOD_D_WU : LSX3R_VVV<0x70330000>; +def VADDWOD_Q_DU : LSX3R_VVV<0x70338000>; + +def VSUBWEV_H_BU : LSX3R_VVV<0x70300000>; +def VSUBWEV_W_HU : LSX3R_VVV<0x70308000>; +def VSUBWEV_D_WU : LSX3R_VVV<0x70310000>; +def VSUBWEV_Q_DU : LSX3R_VVV<0x70318000>; +def VSUBWOD_H_BU : LSX3R_VVV<0x70340000>; +def VSUBWOD_W_HU : LSX3R_VVV<0x70348000>; +def VSUBWOD_D_WU : LSX3R_VVV<0x70350000>; +def VSUBWOD_Q_DU : LSX3R_VVV<0x70358000>; + +def VADDWEV_H_BU_B : LSX3R_VVV<0x703e0000>; +def VADDWEV_W_HU_H : LSX3R_VVV<0x703e8000>; +def VADDWEV_D_WU_W : LSX3R_VVV<0x703f0000>; +def VADDWEV_Q_DU_D : LSX3R_VVV<0x703f8000>; +def VADDWOD_H_BU_B : LSX3R_VVV<0x70400000>; +def VADDWOD_W_HU_H : LSX3R_VVV<0x70408000>; +def VADDWOD_D_WU_W : LSX3R_VVV<0x70410000>; +def VADDWOD_Q_DU_D : LSX3R_VVV<0x70418000>; + +def VAVG_B : LSX3R_VVV<0x70640000>; +def VAVG_H : LSX3R_VVV<0x70648000>; +def VAVG_W : LSX3R_VVV<0x70650000>; +def VAVG_D : LSX3R_VVV<0x70658000>; +def VAVG_BU : LSX3R_VVV<0x70660000>; +def VAVG_HU : LSX3R_VVV<0x70668000>; +def VAVG_WU : LSX3R_VVV<0x70670000>; +def VAVG_DU : LSX3R_VVV<0x70678000>; +def VAVGR_B : LSX3R_VVV<0x70680000>; +def VAVGR_H : LSX3R_VVV<0x70688000>; +def VAVGR_W : LSX3R_VVV<0x70690000>; +def VAVGR_D : LSX3R_VVV<0x70698000>; +def VAVGR_BU : LSX3R_VVV<0x706a0000>; +def VAVGR_HU : LSX3R_VVV<0x706a8000>; +def VAVGR_WU : LSX3R_VVV<0x706b0000>; +def VAVGR_DU : LSX3R_VVV<0x706b8000>; + +def VABSD_B : LSX3R_VVV<0x70600000>; +def VABSD_H : LSX3R_VVV<0x70608000>; +def VABSD_W : LSX3R_VVV<0x70610000>; +def VABSD_D : LSX3R_VVV<0x70618000>; +def VABSD_BU : LSX3R_VVV<0x70620000>; +def VABSD_HU : LSX3R_VVV<0x70628000>; +def VABSD_WU : LSX3R_VVV<0x70630000>; +def VABSD_DU : LSX3R_VVV<0x70638000>; + +def VADDA_B : LSX3R_VVV<0x705c0000>; +def VADDA_H : LSX3R_VVV<0x705c8000>; +def VADDA_W : LSX3R_VVV<0x705d0000>; +def VADDA_D : LSX3R_VVV<0x705d8000>; + +def VMAX_B : LSX3R_VVV<0x70700000>; +def VMAX_H : LSX3R_VVV<0x70708000>; +def VMAX_W : LSX3R_VVV<0x70710000>; +def VMAX_D : LSX3R_VVV<0x70718000>; +def VMAXI_B : LSX2RI5_VVI<0x72900000, simm5>; +def VMAXI_H : LSX2RI5_VVI<0x72908000, simm5>; +def VMAXI_W : LSX2RI5_VVI<0x72910000, simm5>; +def VMAXI_D : LSX2RI5_VVI<0x72918000, simm5>; +def VMAX_BU : LSX3R_VVV<0x70740000>; +def VMAX_HU : LSX3R_VVV<0x70748000>; +def VMAX_WU : LSX3R_VVV<0x70750000>; +def VMAX_DU : LSX3R_VVV<0x70758000>; +def VMAXI_BU : LSX2RI5_VVI<0x72940000>; +def VMAXI_HU : LSX2RI5_VVI<0x72948000>; +def VMAXI_WU : LSX2RI5_VVI<0x72950000>; +def VMAXI_DU : LSX2RI5_VVI<0x72958000>; + +def VMIN_B : LSX3R_VVV<0x70720000>; +def VMIN_H : LSX3R_VVV<0x70728000>; +def VMIN_W : LSX3R_VVV<0x70730000>; +def VMIN_D : LSX3R_VVV<0x70738000>; +def VMINI_B : LSX2RI5_VVI<0x72920000, simm5>; +def VMINI_H : LSX2RI5_VVI<0x72928000, simm5>; +def VMINI_W : LSX2RI5_VVI<0x72930000, simm5>; +def VMINI_D : LSX2RI5_VVI<0x72938000, simm5>; +def VMIN_BU : LSX3R_VVV<0x70760000>; +def VMIN_HU : LSX3R_VVV<0x70768000>; +def VMIN_WU : LSX3R_VVV<0x70770000>; +def VMIN_DU : LSX3R_VVV<0x70778000>; +def VMINI_BU : LSX2RI5_VVI<0x72960000>; +def VMINI_HU : LSX2RI5_VVI<0x72968000>; +def VMINI_WU : LSX2RI5_VVI<0x72970000>; +def VMINI_DU : LSX2RI5_VVI<0x72978000>; + +def VMUL_B : LSX3R_VVV<0x70840000>; +def VMUL_H : LSX3R_VVV<0x70848000>; +def VMUL_W : LSX3R_VVV<0x70850000>; +def VMUL_D : LSX3R_VVV<0x70858000>; + +def VMUH_B : LSX3R_VVV<0x70860000>; +def VMUH_H : LSX3R_VVV<0x70868000>; +def VMUH_W : LSX3R_VVV<0x70870000>; +def VMUH_D : LSX3R_VVV<0x70878000>; +def VMUH_BU : LSX3R_VVV<0x70880000>; +def VMUH_HU : LSX3R_VVV<0x70888000>; +def VMUH_WU : LSX3R_VVV<0x70890000>; +def VMUH_DU : LSX3R_VVV<0x70898000>; + +def VMULWEV_H_B : LSX3R_VVV<0x70900000>; +def VMULWEV_W_H : LSX3R_VVV<0x70908000>; +def VMULWEV_D_W : LSX3R_VVV<0x70910000>; +def VMULWEV_Q_D : LSX3R_VVV<0x70918000>; +def VMULWOD_H_B : LSX3R_VVV<0x70920000>; +def VMULWOD_W_H : LSX3R_VVV<0x70928000>; +def VMULWOD_D_W : LSX3R_VVV<0x70930000>; +def VMULWOD_Q_D : LSX3R_VVV<0x70938000>; +def VMULWEV_H_BU : LSX3R_VVV<0x70980000>; +def VMULWEV_W_HU : LSX3R_VVV<0x70988000>; +def VMULWEV_D_WU : LSX3R_VVV<0x70990000>; +def VMULWEV_Q_DU : LSX3R_VVV<0x70998000>; +def VMULWOD_H_BU : LSX3R_VVV<0x709a0000>; +def VMULWOD_W_HU : LSX3R_VVV<0x709a8000>; +def VMULWOD_D_WU : LSX3R_VVV<0x709b0000>; +def VMULWOD_Q_DU : LSX3R_VVV<0x709b8000>; +def VMULWEV_H_BU_B : LSX3R_VVV<0x70a00000>; +def VMULWEV_W_HU_H : LSX3R_VVV<0x70a08000>; +def VMULWEV_D_WU_W : LSX3R_VVV<0x70a10000>; +def VMULWEV_Q_DU_D : LSX3R_VVV<0x70a18000>; +def VMULWOD_H_BU_B : LSX3R_VVV<0x70a20000>; +def VMULWOD_W_HU_H : LSX3R_VVV<0x70a28000>; +def VMULWOD_D_WU_W : LSX3R_VVV<0x70a30000>; +def VMULWOD_Q_DU_D : LSX3R_VVV<0x70a38000>; + +def VMADD_B : LSX3R_VVVV<0x70a80000>; +def VMADD_H : LSX3R_VVVV<0x70a88000>; +def VMADD_W : LSX3R_VVVV<0x70a90000>; +def VMADD_D : LSX3R_VVVV<0x70a98000>; + +def VMSUB_B : LSX3R_VVVV<0x70aa0000>; +def VMSUB_H : LSX3R_VVVV<0x70aa8000>; +def VMSUB_W : LSX3R_VVVV<0x70ab0000>; +def VMSUB_D : LSX3R_VVVV<0x70ab8000>; + +def VMADDWEV_H_B : LSX3R_VVVV<0x70ac0000>; +def VMADDWEV_W_H : LSX3R_VVVV<0x70ac8000>; +def VMADDWEV_D_W : LSX3R_VVVV<0x70ad0000>; +def VMADDWEV_Q_D : LSX3R_VVVV<0x70ad8000>; +def VMADDWOD_H_B : LSX3R_VVVV<0x70ae0000>; +def VMADDWOD_W_H : LSX3R_VVVV<0x70ae8000>; +def VMADDWOD_D_W : LSX3R_VVVV<0x70af0000>; +def VMADDWOD_Q_D : LSX3R_VVVV<0x70af8000>; +def VMADDWEV_H_BU : LSX3R_VVVV<0x70b40000>; +def VMADDWEV_W_HU : LSX3R_VVVV<0x70b48000>; +def VMADDWEV_D_WU : LSX3R_VVVV<0x70b50000>; +def VMADDWEV_Q_DU : LSX3R_VVVV<0x70b58000>; +def VMADDWOD_H_BU : LSX3R_VVVV<0x70b60000>; +def VMADDWOD_W_HU : LSX3R_VVVV<0x70b68000>; +def VMADDWOD_D_WU : LSX3R_VVVV<0x70b70000>; +def VMADDWOD_Q_DU : LSX3R_VVVV<0x70b78000>; +def VMADDWEV_H_BU_B : LSX3R_VVVV<0x70bc0000>; +def VMADDWEV_W_HU_H : LSX3R_VVVV<0x70bc8000>; +def VMADDWEV_D_WU_W : LSX3R_VVVV<0x70bd0000>; +def VMADDWEV_Q_DU_D : LSX3R_VVVV<0x70bd8000>; +def VMADDWOD_H_BU_B : LSX3R_VVVV<0x70be0000>; +def VMADDWOD_W_HU_H : LSX3R_VVVV<0x70be8000>; +def VMADDWOD_D_WU_W : LSX3R_VVVV<0x70bf0000>; +def VMADDWOD_Q_DU_D : LSX3R_VVVV<0x70bf8000>; + +def VDIV_B : LSX3R_VVV<0x70e00000>; +def VDIV_H : LSX3R_VVV<0x70e08000>; +def VDIV_W : LSX3R_VVV<0x70e10000>; +def VDIV_D : LSX3R_VVV<0x70e18000>; +def VDIV_BU : LSX3R_VVV<0x70e40000>; +def VDIV_HU : LSX3R_VVV<0x70e48000>; +def VDIV_WU : LSX3R_VVV<0x70e50000>; +def VDIV_DU : LSX3R_VVV<0x70e58000>; + +def VMOD_B : LSX3R_VVV<0x70e20000>; +def VMOD_H : LSX3R_VVV<0x70e28000>; +def VMOD_W : LSX3R_VVV<0x70e30000>; +def VMOD_D : LSX3R_VVV<0x70e38000>; +def VMOD_BU : LSX3R_VVV<0x70e60000>; +def VMOD_HU : LSX3R_VVV<0x70e68000>; +def VMOD_WU : LSX3R_VVV<0x70e70000>; +def VMOD_DU : LSX3R_VVV<0x70e78000>; + +def VSAT_B : LSX2RI3_VVI<0x73242000>; +def VSAT_H : LSX2RI4_VVI<0x73244000>; +def VSAT_W : LSX2RI5_VVI<0x73248000>; +def VSAT_D : LSX2RI6_VVI<0x73250000>; +def VSAT_BU : LSX2RI3_VVI<0x73282000>; +def VSAT_HU : LSX2RI4_VVI<0x73284000>; +def VSAT_WU : LSX2RI5_VVI<0x73288000>; +def VSAT_DU : LSX2RI6_VVI<0x73290000>; + +def VEXTH_H_B : LSX2R_VV<0x729ee000>; +def VEXTH_W_H : LSX2R_VV<0x729ee400>; +def VEXTH_D_W : LSX2R_VV<0x729ee800>; +def VEXTH_Q_D : LSX2R_VV<0x729eec00>; +def VEXTH_HU_BU : LSX2R_VV<0x729ef000>; +def VEXTH_WU_HU : LSX2R_VV<0x729ef400>; +def VEXTH_DU_WU : LSX2R_VV<0x729ef800>; +def VEXTH_QU_DU : LSX2R_VV<0x729efc00>; + +def VSIGNCOV_B : LSX3R_VVV<0x712e0000>; +def VSIGNCOV_H : LSX3R_VVV<0x712e8000>; +def VSIGNCOV_W : LSX3R_VVV<0x712f0000>; +def VSIGNCOV_D : LSX3R_VVV<0x712f8000>; + +def VMSKLTZ_B : LSX2R_VV<0x729c4000>; +def VMSKLTZ_H : LSX2R_VV<0x729c4400>; +def VMSKLTZ_W : LSX2R_VV<0x729c4800>; +def VMSKLTZ_D : LSX2R_VV<0x729c4c00>; + +def VMSKGEZ_B : LSX2R_VV<0x729c5000>; + +def VMSKNZ_B : LSX2R_VV<0x729c6000>; + +def VLDI : LSX1RI13_VI<0x73e00000>; + +def VAND_V : LSX3R_VVV<0x71260000>; +def VOR_V : LSX3R_VVV<0x71268000>; +def VXOR_V : LSX3R_VVV<0x71270000>; +def VNOR_V : LSX3R_VVV<0x71278000>; +def VANDN_V : LSX3R_VVV<0x71280000>; +def VORN_V : LSX3R_VVV<0x71288000>; + +def VANDI_B : LSX2RI8_VVI<0x73d00000>; +def VORI_B : LSX2RI8_VVI<0x73d40000>; +def VXORI_B : LSX2RI8_VVI<0x73d80000>; +def VNORI_B : LSX2RI8_VVI<0x73dc0000>; + +def VSLL_B : LSX3R_VVV<0x70e80000>; +def VSLL_H : LSX3R_VVV<0x70e88000>; +def VSLL_W : LSX3R_VVV<0x70e90000>; +def VSLL_D : LSX3R_VVV<0x70e98000>; +def VSLLI_B : LSX2RI3_VVI<0x732c2000>; +def VSLLI_H : LSX2RI4_VVI<0x732c4000>; +def VSLLI_W : LSX2RI5_VVI<0x732c8000>; +def VSLLI_D : LSX2RI6_VVI<0x732d0000>; + +def VSRL_B : LSX3R_VVV<0x70ea0000>; +def VSRL_H : LSX3R_VVV<0x70ea8000>; +def VSRL_W : LSX3R_VVV<0x70eb0000>; +def VSRL_D : LSX3R_VVV<0x70eb8000>; +def VSRLI_B : LSX2RI3_VVI<0x73302000>; +def VSRLI_H : LSX2RI4_VVI<0x73304000>; +def VSRLI_W : LSX2RI5_VVI<0x73308000>; +def VSRLI_D : LSX2RI6_VVI<0x73310000>; + +def VSRA_B : LSX3R_VVV<0x70ec0000>; +def VSRA_H : LSX3R_VVV<0x70ec8000>; +def VSRA_W : LSX3R_VVV<0x70ed0000>; +def VSRA_D : LSX3R_VVV<0x70ed8000>; +def VSRAI_B : LSX2RI3_VVI<0x73342000>; +def VSRAI_H : LSX2RI4_VVI<0x73344000>; +def VSRAI_W : LSX2RI5_VVI<0x73348000>; +def VSRAI_D : LSX2RI6_VVI<0x73350000>; + +def VROTR_B : LSX3R_VVV<0x70ee0000>; +def VROTR_H : LSX3R_VVV<0x70ee8000>; +def VROTR_W : LSX3R_VVV<0x70ef0000>; +def VROTR_D : LSX3R_VVV<0x70ef8000>; +def VROTRI_B : LSX2RI3_VVI<0x72a02000>; +def VROTRI_H : LSX2RI4_VVI<0x72a04000>; +def VROTRI_W : LSX2RI5_VVI<0x72a08000>; +def VROTRI_D : LSX2RI6_VVI<0x72a10000>; + +def VSLLWIL_H_B : LSX2RI3_VVI<0x73082000>; +def VSLLWIL_W_H : LSX2RI4_VVI<0x73084000>; +def VSLLWIL_D_W : LSX2RI5_VVI<0x73088000>; +def VEXTL_Q_D : LSX2R_VV<0x73090000>; +def VSLLWIL_HU_BU : LSX2RI3_VVI<0x730c2000>; +def VSLLWIL_WU_HU : LSX2RI4_VVI<0x730c4000>; +def VSLLWIL_DU_WU : LSX2RI5_VVI<0x730c8000>; +def VEXTL_QU_DU : LSX2R_VV<0x730d0000>; + +def VSRLR_B : LSX3R_VVV<0x70f00000>; +def VSRLR_H : LSX3R_VVV<0x70f08000>; +def VSRLR_W : LSX3R_VVV<0x70f10000>; +def VSRLR_D : LSX3R_VVV<0x70f18000>; +def VSRLRI_B : LSX2RI3_VVI<0x72a42000>; +def VSRLRI_H : LSX2RI4_VVI<0x72a44000>; +def VSRLRI_W : LSX2RI5_VVI<0x72a48000>; +def VSRLRI_D : LSX2RI6_VVI<0x72a50000>; + +def VSRAR_B : LSX3R_VVV<0x70f20000>; +def VSRAR_H : LSX3R_VVV<0x70f28000>; +def VSRAR_W : LSX3R_VVV<0x70f30000>; +def VSRAR_D : LSX3R_VVV<0x70f38000>; +def VSRARI_B : LSX2RI3_VVI<0x72a82000>; +def VSRARI_H : LSX2RI4_VVI<0x72a84000>; +def VSRARI_W : LSX2RI5_VVI<0x72a88000>; +def VSRARI_D : LSX2RI6_VVI<0x72a90000>; + +def VSRLN_B_H : LSX3R_VVV<0x70f48000>; +def VSRLN_H_W : LSX3R_VVV<0x70f50000>; +def VSRLN_W_D : LSX3R_VVV<0x70f58000>; +def VSRAN_B_H : LSX3R_VVV<0x70f68000>; +def VSRAN_H_W : LSX3R_VVV<0x70f70000>; +def VSRAN_W_D : LSX3R_VVV<0x70f78000>; + +def VSRLNI_B_H : LSX2RI4_VVVI<0x73404000>; +def VSRLNI_H_W : LSX2RI5_VVVI<0x73408000>; +def VSRLNI_W_D : LSX2RI6_VVVI<0x73410000>; +def VSRLNI_D_Q : LSX2RI7_VVVI<0x73420000>; +def VSRANI_B_H : LSX2RI4_VVVI<0x73584000>; +def VSRANI_H_W : LSX2RI5_VVVI<0x73588000>; +def VSRANI_W_D : LSX2RI6_VVVI<0x73590000>; +def VSRANI_D_Q : LSX2RI7_VVVI<0x735a0000>; + +def VSRLRN_B_H : LSX3R_VVV<0x70f88000>; +def VSRLRN_H_W : LSX3R_VVV<0x70f90000>; +def VSRLRN_W_D : LSX3R_VVV<0x70f98000>; +def VSRARN_B_H : LSX3R_VVV<0x70fa8000>; +def VSRARN_H_W : LSX3R_VVV<0x70fb0000>; +def VSRARN_W_D : LSX3R_VVV<0x70fb8000>; + +def VSRLRNI_B_H : LSX2RI4_VVVI<0x73444000>; +def VSRLRNI_H_W : LSX2RI5_VVVI<0x73448000>; +def VSRLRNI_W_D : LSX2RI6_VVVI<0x73450000>; +def VSRLRNI_D_Q : LSX2RI7_VVVI<0x73460000>; +def VSRARNI_B_H : LSX2RI4_VVVI<0x735c4000>; +def VSRARNI_H_W : LSX2RI5_VVVI<0x735c8000>; +def VSRARNI_W_D : LSX2RI6_VVVI<0x735d0000>; +def VSRARNI_D_Q : LSX2RI7_VVVI<0x735e0000>; + +def VSSRLN_B_H : LSX3R_VVV<0x70fc8000>; +def VSSRLN_H_W : LSX3R_VVV<0x70fd0000>; +def VSSRLN_W_D : LSX3R_VVV<0x70fd8000>; +def VSSRAN_B_H : LSX3R_VVV<0x70fe8000>; +def VSSRAN_H_W : LSX3R_VVV<0x70ff0000>; +def VSSRAN_W_D : LSX3R_VVV<0x70ff8000>; +def VSSRLN_BU_H : LSX3R_VVV<0x71048000>; +def VSSRLN_HU_W : LSX3R_VVV<0x71050000>; +def VSSRLN_WU_D : LSX3R_VVV<0x71058000>; +def VSSRAN_BU_H : LSX3R_VVV<0x71068000>; +def VSSRAN_HU_W : LSX3R_VVV<0x71070000>; +def VSSRAN_WU_D : LSX3R_VVV<0x71078000>; + +def VSSRLNI_B_H : LSX2RI4_VVVI<0x73484000>; +def VSSRLNI_H_W : LSX2RI5_VVVI<0x73488000>; +def VSSRLNI_W_D : LSX2RI6_VVVI<0x73490000>; +def VSSRLNI_D_Q : LSX2RI7_VVVI<0x734a0000>; +def VSSRANI_B_H : LSX2RI4_VVVI<0x73604000>; +def VSSRANI_H_W : LSX2RI5_VVVI<0x73608000>; +def VSSRANI_W_D : LSX2RI6_VVVI<0x73610000>; +def VSSRANI_D_Q : LSX2RI7_VVVI<0x73620000>; +def VSSRLNI_BU_H : LSX2RI4_VVVI<0x734c4000>; +def VSSRLNI_HU_W : LSX2RI5_VVVI<0x734c8000>; +def VSSRLNI_WU_D : LSX2RI6_VVVI<0x734d0000>; +def VSSRLNI_DU_Q : LSX2RI7_VVVI<0x734e0000>; +def VSSRANI_BU_H : LSX2RI4_VVVI<0x73644000>; +def VSSRANI_HU_W : LSX2RI5_VVVI<0x73648000>; +def VSSRANI_WU_D : LSX2RI6_VVVI<0x73650000>; +def VSSRANI_DU_Q : LSX2RI7_VVVI<0x73660000>; + +def VSSRLRN_B_H : LSX3R_VVV<0x71008000>; +def VSSRLRN_H_W : LSX3R_VVV<0x71010000>; +def VSSRLRN_W_D : LSX3R_VVV<0x71018000>; +def VSSRARN_B_H : LSX3R_VVV<0x71028000>; +def VSSRARN_H_W : LSX3R_VVV<0x71030000>; +def VSSRARN_W_D : LSX3R_VVV<0x71038000>; +def VSSRLRN_BU_H : LSX3R_VVV<0x71088000>; +def VSSRLRN_HU_W : LSX3R_VVV<0x71090000>; +def VSSRLRN_WU_D : LSX3R_VVV<0x71098000>; +def VSSRARN_BU_H : LSX3R_VVV<0x710a8000>; +def VSSRARN_HU_W : LSX3R_VVV<0x710b0000>; +def VSSRARN_WU_D : LSX3R_VVV<0x710b8000>; + +def VSSRLRNI_B_H : LSX2RI4_VVVI<0x73504000>; +def VSSRLRNI_H_W : LSX2RI5_VVVI<0x73508000>; +def VSSRLRNI_W_D : LSX2RI6_VVVI<0x73510000>; +def VSSRLRNI_D_Q : LSX2RI7_VVVI<0x73520000>; +def VSSRARNI_B_H : LSX2RI4_VVVI<0x73684000>; +def VSSRARNI_H_W : LSX2RI5_VVVI<0x73688000>; +def VSSRARNI_W_D : LSX2RI6_VVVI<0x73690000>; +def VSSRARNI_D_Q : LSX2RI7_VVVI<0x736a0000>; +def VSSRLRNI_BU_H : LSX2RI4_VVVI<0x73544000>; +def VSSRLRNI_HU_W : LSX2RI5_VVVI<0x73548000>; +def VSSRLRNI_WU_D : LSX2RI6_VVVI<0x73550000>; +def VSSRLRNI_DU_Q : LSX2RI7_VVVI<0x73560000>; +def VSSRARNI_BU_H : LSX2RI4_VVVI<0x736c4000>; +def VSSRARNI_HU_W : LSX2RI5_VVVI<0x736c8000>; +def VSSRARNI_WU_D : LSX2RI6_VVVI<0x736d0000>; +def VSSRARNI_DU_Q : LSX2RI7_VVVI<0x736e0000>; + +def VCLO_B : LSX2R_VV<0x729c0000>; +def VCLO_H : LSX2R_VV<0x729c0400>; +def VCLO_W : LSX2R_VV<0x729c0800>; +def VCLO_D : LSX2R_VV<0x729c0c00>; +def VCLZ_B : LSX2R_VV<0x729c1000>; +def VCLZ_H : LSX2R_VV<0x729c1400>; +def VCLZ_W : LSX2R_VV<0x729c1800>; +def VCLZ_D : LSX2R_VV<0x729c1c00>; + +def VPCNT_B : LSX2R_VV<0x729c2000>; +def VPCNT_H : LSX2R_VV<0x729c2400>; +def VPCNT_W : LSX2R_VV<0x729c2800>; +def VPCNT_D : LSX2R_VV<0x729c2c00>; + +def VBITCLR_B : LSX3R_VVV<0x710c0000>; +def VBITCLR_H : LSX3R_VVV<0x710c8000>; +def VBITCLR_W : LSX3R_VVV<0x710d0000>; +def VBITCLR_D : LSX3R_VVV<0x710d8000>; +def VBITCLRI_B : LSX2RI3_VVI<0x73102000>; +def VBITCLRI_H : LSX2RI4_VVI<0x73104000>; +def VBITCLRI_W : LSX2RI5_VVI<0x73108000>; +def VBITCLRI_D : LSX2RI6_VVI<0x73110000>; + +def VBITSET_B : LSX3R_VVV<0x710e0000>; +def VBITSET_H : LSX3R_VVV<0x710e8000>; +def VBITSET_W : LSX3R_VVV<0x710f0000>; +def VBITSET_D : LSX3R_VVV<0x710f8000>; +def VBITSETI_B : LSX2RI3_VVI<0x73142000>; +def VBITSETI_H : LSX2RI4_VVI<0x73144000>; +def VBITSETI_W : LSX2RI5_VVI<0x73148000>; +def VBITSETI_D : LSX2RI6_VVI<0x73150000>; + +def VBITREV_B : LSX3R_VVV<0x71100000>; +def VBITREV_H : LSX3R_VVV<0x71108000>; +def VBITREV_W : LSX3R_VVV<0x71110000>; +def VBITREV_D : LSX3R_VVV<0x71118000>; +def VBITREVI_B : LSX2RI3_VVI<0x73182000>; +def VBITREVI_H : LSX2RI4_VVI<0x73184000>; +def VBITREVI_W : LSX2RI5_VVI<0x73188000>; +def VBITREVI_D : LSX2RI6_VVI<0x73190000>; + +def VFRSTP_B : LSX3R_VVVV<0x712b0000>; +def VFRSTP_H : LSX3R_VVVV<0x712b8000>; +def VFRSTPI_B : LSX2RI5_VVVI<0x729a0000>; +def VFRSTPI_H : LSX2RI5_VVVI<0x729a8000>; + +def VFADD_S : LSX3R_VVV<0x71308000>; +def VFADD_D : LSX3R_VVV<0x71310000>; +def VFSUB_S : LSX3R_VVV<0x71328000>; +def VFSUB_D : LSX3R_VVV<0x71330000>; +def VFMUL_S : LSX3R_VVV<0x71388000>; +def VFMUL_D : LSX3R_VVV<0x71390000>; +def VFDIV_S : LSX3R_VVV<0x713a8000>; +def VFDIV_D : LSX3R_VVV<0x713b0000>; + +def VFMADD_S : LSX4R_VVVV<0x09100000>; +def VFMADD_D : LSX4R_VVVV<0x09200000>; +def VFMSUB_S : LSX4R_VVVV<0x09500000>; +def VFMSUB_D : LSX4R_VVVV<0x09600000>; +def VFNMADD_S : LSX4R_VVVV<0x09900000>; +def VFNMADD_D : LSX4R_VVVV<0x09a00000>; +def VFNMSUB_S : LSX4R_VVVV<0x09d00000>; +def VFNMSUB_D : LSX4R_VVVV<0x09e00000>; + +def VFMAX_S : LSX3R_VVV<0x713c8000>; +def VFMAX_D : LSX3R_VVV<0x713d0000>; +def VFMIN_S : LSX3R_VVV<0x713e8000>; +def VFMIN_D : LSX3R_VVV<0x713f0000>; + +def VFMAXA_S : LSX3R_VVV<0x71408000>; +def VFMAXA_D : LSX3R_VVV<0x71410000>; +def VFMINA_S : LSX3R_VVV<0x71428000>; +def VFMINA_D : LSX3R_VVV<0x71430000>; + +def VFLOGB_S : LSX2R_VV<0x729cc400>; +def VFLOGB_D : LSX2R_VV<0x729cc800>; + +def VFCLASS_S : LSX2R_VV<0x729cd400>; +def VFCLASS_D : LSX2R_VV<0x729cd800>; + +def VFSQRT_S : LSX2R_VV<0x729ce400>; +def VFSQRT_D : LSX2R_VV<0x729ce800>; +def VFRECIP_S : LSX2R_VV<0x729cf400>; +def VFRECIP_D : LSX2R_VV<0x729cf800>; +def VFRSQRT_S : LSX2R_VV<0x729d0400>; +def VFRSQRT_D : LSX2R_VV<0x729d0800>; + +def VFCVTL_S_H : LSX2R_VV<0x729de800>; +def VFCVTH_S_H : LSX2R_VV<0x729dec00>; +def VFCVTL_D_S : LSX2R_VV<0x729df000>; +def VFCVTH_D_S : LSX2R_VV<0x729df400>; +def VFCVT_H_S : LSX3R_VVV<0x71460000>; +def VFCVT_S_D : LSX3R_VVV<0x71468000>; + +def VFRINTRNE_S : LSX2R_VV<0x729d7400>; +def VFRINTRNE_D : LSX2R_VV<0x729d7800>; +def VFRINTRZ_S : LSX2R_VV<0x729d6400>; +def VFRINTRZ_D : LSX2R_VV<0x729d6800>; +def VFRINTRP_S : LSX2R_VV<0x729d5400>; +def VFRINTRP_D : LSX2R_VV<0x729d5800>; +def VFRINTRM_S : LSX2R_VV<0x729d4400>; +def VFRINTRM_D : LSX2R_VV<0x729d4800>; +def VFRINT_S : LSX2R_VV<0x729d3400>; +def VFRINT_D : LSX2R_VV<0x729d3800>; + +def VFTINTRNE_W_S : LSX2R_VV<0x729e5000>; +def VFTINTRNE_L_D : LSX2R_VV<0x729e5400>; +def VFTINTRZ_W_S : LSX2R_VV<0x729e4800>; +def VFTINTRZ_L_D : LSX2R_VV<0x729e4c00>; +def VFTINTRP_W_S : LSX2R_VV<0x729e4000>; +def VFTINTRP_L_D : LSX2R_VV<0x729e4400>; +def VFTINTRM_W_S : LSX2R_VV<0x729e3800>; +def VFTINTRM_L_D : LSX2R_VV<0x729e3c00>; +def VFTINT_W_S : LSX2R_VV<0x729e3000>; +def VFTINT_L_D : LSX2R_VV<0x729e3400>; +def VFTINTRZ_WU_S : LSX2R_VV<0x729e7000>; +def VFTINTRZ_LU_D : LSX2R_VV<0x729e7400>; +def VFTINT_WU_S : LSX2R_VV<0x729e5800>; +def VFTINT_LU_D : LSX2R_VV<0x729e5c00>; + +def VFTINTRNE_W_D : LSX3R_VVV<0x714b8000>; +def VFTINTRZ_W_D : LSX3R_VVV<0x714b0000>; +def VFTINTRP_W_D : LSX3R_VVV<0x714a8000>; +def VFTINTRM_W_D : LSX3R_VVV<0x714a0000>; +def VFTINT_W_D : LSX3R_VVV<0x71498000>; + +def VFTINTRNEL_L_S : LSX2R_VV<0x729ea000>; +def VFTINTRNEH_L_S : LSX2R_VV<0x729ea400>; +def VFTINTRZL_L_S : LSX2R_VV<0x729e9800>; +def VFTINTRZH_L_S : LSX2R_VV<0x729e9c00>; +def VFTINTRPL_L_S : LSX2R_VV<0x729e9000>; +def VFTINTRPH_L_S : LSX2R_VV<0x729e9400>; +def VFTINTRML_L_S : LSX2R_VV<0x729e8800>; +def VFTINTRMH_L_S : LSX2R_VV<0x729e8c00>; +def VFTINTL_L_S : LSX2R_VV<0x729e8000>; +def VFTINTH_L_S : LSX2R_VV<0x729e8400>; + +def VFFINT_S_W : LSX2R_VV<0x729e0000>; +def VFFINT_D_L : LSX2R_VV<0x729e0800>; +def VFFINT_S_WU : LSX2R_VV<0x729e0400>; +def VFFINT_D_LU : LSX2R_VV<0x729e0c00>; +def VFFINTL_D_W : LSX2R_VV<0x729e1000>; +def VFFINTH_D_W : LSX2R_VV<0x729e1400>; +def VFFINT_S_L : LSX3R_VVV<0x71480000>; + +def VSEQ_B : LSX3R_VVV<0x70000000>; +def VSEQ_H : LSX3R_VVV<0x70008000>; +def VSEQ_W : LSX3R_VVV<0x70010000>; +def VSEQ_D : LSX3R_VVV<0x70018000>; +def VSEQI_B : LSX2RI5_VVI<0x72800000, simm5>; +def VSEQI_H : LSX2RI5_VVI<0x72808000, simm5>; +def VSEQI_W : LSX2RI5_VVI<0x72810000, simm5>; +def VSEQI_D : LSX2RI5_VVI<0x72818000, simm5>; + +def VSLE_B : LSX3R_VVV<0x70020000>; +def VSLE_H : LSX3R_VVV<0x70028000>; +def VSLE_W : LSX3R_VVV<0x70030000>; +def VSLE_D : LSX3R_VVV<0x70038000>; +def VSLEI_B : LSX2RI5_VVI<0x72820000, simm5>; +def VSLEI_H : LSX2RI5_VVI<0x72828000, simm5>; +def VSLEI_W : LSX2RI5_VVI<0x72830000, simm5>; +def VSLEI_D : LSX2RI5_VVI<0x72838000, simm5>; + +def VSLE_BU : LSX3R_VVV<0x70040000>; +def VSLE_HU : LSX3R_VVV<0x70048000>; +def VSLE_WU : LSX3R_VVV<0x70050000>; +def VSLE_DU : LSX3R_VVV<0x70058000>; +def VSLEI_BU : LSX2RI5_VVI<0x72840000>; +def VSLEI_HU : LSX2RI5_VVI<0x72848000>; +def VSLEI_WU : LSX2RI5_VVI<0x72850000>; +def VSLEI_DU : LSX2RI5_VVI<0x72858000>; + +def VSLT_B : LSX3R_VVV<0x70060000>; +def VSLT_H : LSX3R_VVV<0x70068000>; +def VSLT_W : LSX3R_VVV<0x70070000>; +def VSLT_D : LSX3R_VVV<0x70078000>; +def VSLTI_B : LSX2RI5_VVI<0x72860000, simm5>; +def VSLTI_H : LSX2RI5_VVI<0x72868000, simm5>; +def VSLTI_W : LSX2RI5_VVI<0x72870000, simm5>; +def VSLTI_D : LSX2RI5_VVI<0x72878000, simm5>; + +def VSLT_BU : LSX3R_VVV<0x70080000>; +def VSLT_HU : LSX3R_VVV<0x70088000>; +def VSLT_WU : LSX3R_VVV<0x70090000>; +def VSLT_DU : LSX3R_VVV<0x70098000>; +def VSLTI_BU : LSX2RI5_VVI<0x72880000>; +def VSLTI_HU : LSX2RI5_VVI<0x72888000>; +def VSLTI_WU : LSX2RI5_VVI<0x72890000>; +def VSLTI_DU : LSX2RI5_VVI<0x72898000>; + +def VFCMP_CAF_S : LSX3R_VVV<0x0c500000>; +def VFCMP_SAF_S : LSX3R_VVV<0x0c508000>; +def VFCMP_CLT_S : LSX3R_VVV<0x0c510000>; +def VFCMP_SLT_S : LSX3R_VVV<0x0c518000>; +def VFCMP_CEQ_S : LSX3R_VVV<0x0c520000>; +def VFCMP_SEQ_S : LSX3R_VVV<0x0c528000>; +def VFCMP_CLE_S : LSX3R_VVV<0x0c530000>; +def VFCMP_SLE_S : LSX3R_VVV<0x0c538000>; +def VFCMP_CUN_S : LSX3R_VVV<0x0c540000>; +def VFCMP_SUN_S : LSX3R_VVV<0x0c548000>; +def VFCMP_CULT_S : LSX3R_VVV<0x0c550000>; +def VFCMP_SULT_S : LSX3R_VVV<0x0c558000>; +def VFCMP_CUEQ_S : LSX3R_VVV<0x0c560000>; +def VFCMP_SUEQ_S : LSX3R_VVV<0x0c568000>; +def VFCMP_CULE_S : LSX3R_VVV<0x0c570000>; +def VFCMP_SULE_S : LSX3R_VVV<0x0c578000>; +def VFCMP_CNE_S : LSX3R_VVV<0x0c580000>; +def VFCMP_SNE_S : LSX3R_VVV<0x0c588000>; +def VFCMP_COR_S : LSX3R_VVV<0x0c5a0000>; +def VFCMP_SOR_S : LSX3R_VVV<0x0c5a8000>; +def VFCMP_CUNE_S : LSX3R_VVV<0x0c5c0000>; +def VFCMP_SUNE_S : LSX3R_VVV<0x0c5c8000>; + +def VFCMP_CAF_D : LSX3R_VVV<0x0c600000>; +def VFCMP_SAF_D : LSX3R_VVV<0x0c608000>; +def VFCMP_CLT_D : LSX3R_VVV<0x0c610000>; +def VFCMP_SLT_D : LSX3R_VVV<0x0c618000>; +def VFCMP_CEQ_D : LSX3R_VVV<0x0c620000>; +def VFCMP_SEQ_D : LSX3R_VVV<0x0c628000>; +def VFCMP_CLE_D : LSX3R_VVV<0x0c630000>; +def VFCMP_SLE_D : LSX3R_VVV<0x0c638000>; +def VFCMP_CUN_D : LSX3R_VVV<0x0c640000>; +def VFCMP_SUN_D : LSX3R_VVV<0x0c648000>; +def VFCMP_CULT_D : LSX3R_VVV<0x0c650000>; +def VFCMP_SULT_D : LSX3R_VVV<0x0c658000>; +def VFCMP_CUEQ_D : LSX3R_VVV<0x0c660000>; +def VFCMP_SUEQ_D : LSX3R_VVV<0x0c668000>; +def VFCMP_CULE_D : LSX3R_VVV<0x0c670000>; +def VFCMP_SULE_D : LSX3R_VVV<0x0c678000>; +def VFCMP_CNE_D : LSX3R_VVV<0x0c680000>; +def VFCMP_SNE_D : LSX3R_VVV<0x0c688000>; +def VFCMP_COR_D : LSX3R_VVV<0x0c6a0000>; +def VFCMP_SOR_D : LSX3R_VVV<0x0c6a8000>; +def VFCMP_CUNE_D : LSX3R_VVV<0x0c6c0000>; +def VFCMP_SUNE_D : LSX3R_VVV<0x0c6c8000>; + +def VBITSEL_V : LSX4R_VVVV<0x0d100000>; + +def VBITSELI_B : LSX2RI8_VVVI<0x73c40000>; + +def VSETEQZ_V : LSX2R_CV<0x729c9800>; +def VSETNEZ_V : LSX2R_CV<0x729c9c00>; +def VSETANYEQZ_B : LSX2R_CV<0x729ca000>; +def VSETANYEQZ_H : LSX2R_CV<0x729ca400>; +def VSETANYEQZ_W : LSX2R_CV<0x729ca800>; +def VSETANYEQZ_D : LSX2R_CV<0x729cac00>; +def VSETALLNEZ_B : LSX2R_CV<0x729cb000>; +def VSETALLNEZ_H : LSX2R_CV<0x729cb400>; +def VSETALLNEZ_W : LSX2R_CV<0x729cb800>; +def VSETALLNEZ_D : LSX2R_CV<0x729cbc00>; + +def VINSGR2VR_B : LSX2RI4_VRI<0x72eb8000>; +def VINSGR2VR_H : LSX2RI3_VRI<0x72ebc000>; +def VINSGR2VR_W : LSX2RI2_VRI<0x72ebe000>; +def VINSGR2VR_D : LSX2RI1_VRI<0x72ebf000>; +def VPICKVE2GR_B : LSX2RI4_RVI<0x72ef8000>; +def VPICKVE2GR_H : LSX2RI3_RVI<0x72efc000>; +def VPICKVE2GR_W : LSX2RI2_RVI<0x72efe000>; +def VPICKVE2GR_D : LSX2RI1_RVI<0x72eff000>; +def VPICKVE2GR_BU : LSX2RI4_RVI<0x72f38000>; +def VPICKVE2GR_HU : LSX2RI3_RVI<0x72f3c000>; +def VPICKVE2GR_WU : LSX2RI2_RVI<0x72f3e000>; +def VPICKVE2GR_DU : LSX2RI1_RVI<0x72f3f000>; + +def VREPLGR2VR_B : LSX2R_VR<0x729f0000>; +def VREPLGR2VR_H : LSX2R_VR<0x729f0400>; +def VREPLGR2VR_W : LSX2R_VR<0x729f0800>; +def VREPLGR2VR_D : LSX2R_VR<0x729f0c00>; + +def VREPLVE_B : LSX3R_VVR<0x71220000>; +def VREPLVE_H : LSX3R_VVR<0x71228000>; +def VREPLVE_W : LSX3R_VVR<0x71230000>; +def VREPLVE_D : LSX3R_VVR<0x71238000>; +def VREPLVEI_B : LSX2RI4_VVI<0x72f78000>; +def VREPLVEI_H : LSX2RI3_VVI<0x72f7c000>; +def VREPLVEI_W : LSX2RI2_VVI<0x72f7e000>; +def VREPLVEI_D : LSX2RI1_VVI<0x72f7f000>; + +def VBSLL_V : LSX2RI5_VVI<0x728e0000>; +def VBSRL_V : LSX2RI5_VVI<0x728e8000>; + +def VPACKEV_B : LSX3R_VVV<0x71160000>; +def VPACKEV_H : LSX3R_VVV<0x71168000>; +def VPACKEV_W : LSX3R_VVV<0x71170000>; +def VPACKEV_D : LSX3R_VVV<0x71178000>; +def VPACKOD_B : LSX3R_VVV<0x71180000>; +def VPACKOD_H : LSX3R_VVV<0x71188000>; +def VPACKOD_W : LSX3R_VVV<0x71190000>; +def VPACKOD_D : LSX3R_VVV<0x71198000>; + +def VPICKEV_B : LSX3R_VVV<0x711e0000>; +def VPICKEV_H : LSX3R_VVV<0x711e8000>; +def VPICKEV_W : LSX3R_VVV<0x711f0000>; +def VPICKEV_D : LSX3R_VVV<0x711f8000>; +def VPICKOD_B : LSX3R_VVV<0x71200000>; +def VPICKOD_H : LSX3R_VVV<0x71208000>; +def VPICKOD_W : LSX3R_VVV<0x71210000>; +def VPICKOD_D : LSX3R_VVV<0x71218000>; + +def VILVL_B : LSX3R_VVV<0x711a0000>; +def VILVL_H : LSX3R_VVV<0x711a8000>; +def VILVL_W : LSX3R_VVV<0x711b0000>; +def VILVL_D : LSX3R_VVV<0x711b8000>; +def VILVH_B : LSX3R_VVV<0x711c0000>; +def VILVH_H : LSX3R_VVV<0x711c8000>; +def VILVH_W : LSX3R_VVV<0x711d0000>; +def VILVH_D : LSX3R_VVV<0x711d8000>; + +def VSHUF_B : LSX4R_VVVV<0x0d500000>; + +def VSHUF_H : LSX3R_VVV<0x717a8000>; +def VSHUF_W : LSX3R_VVV<0x717b0000>; +def VSHUF_D : LSX3R_VVV<0x717b8000>; + +def VSHUF4I_B : LSX2RI8_VVI<0x73900000>; +def VSHUF4I_H : LSX2RI8_VVI<0x73940000>; +def VSHUF4I_W : LSX2RI8_VVI<0x73980000>; +def VSHUF4I_D : LSX2RI8_VVI<0x739c0000>; + +def VPERMI_W : LSX2RI8_VVI<0x73e40000>; + +def VEXTRINS_D : LSX2RI8_VVI<0x73800000>; +def VEXTRINS_W : LSX2RI8_VVI<0x73840000>; +def VEXTRINS_H : LSX2RI8_VVI<0x73880000>; +def VEXTRINS_B : LSX2RI8_VVI<0x738c0000>; + +let mayLoad = 1 in { +def VLD : LSX2RI12_VRI<0x2c000000>; +def VLDX : LSX3R_VRR<0x38400000>; + +def VLDREPL_B : LSX2RI12_VRI<0x30800000>; +def VLDREPL_H : LSX2RI11_VRI<0x30400000>; +def VLDREPL_W : LSX2RI10_VRI<0x30200000>; +def VLDREPL_D : LSX2RI9_VRI<0x30100000>; +} // mayLoad = 1 + +let mayStore = 1 in { +def VST : LSX2RI12_VRI<0x2c400000>; +def VSTX : LSX3R_VRR<0x38440000>; + +def VSTELM_B : LSX2RI8I4_VRII<0x31800000>; +def VSTELM_H : LSX2RI8I3_VRII<0x31400000, simm8_lsl1>; +def VSTELM_W : LSX2RI8I2_VRII<0x31200000, simm8_lsl2>; +def VSTELM_D : LSX2RI8I1_VRII<0x31100000, simm8_lsl3>; +} // mayStore = 1 + +} // Predicates = [HasExtLSX] + +// Pseudo-instructions + +let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isCodeGenOnly = 0, + isAsmParserOnly = 1 in { +def PseudoVREPLI_B : Pseudo<(outs LSX128:$vd), (ins simm10:$imm), [], + "vrepli.b", "$vd, $imm">; +def PseudoVREPLI_H : Pseudo<(outs LSX128:$vd), (ins simm10:$imm), [], + "vrepli.h", "$vd, $imm">; +def PseudoVREPLI_W : Pseudo<(outs LSX128:$vd), (ins simm10:$imm), [], + "vrepli.w", "$vd, $imm">; +def PseudoVREPLI_D : Pseudo<(outs LSX128:$vd), (ins simm10:$imm), [], + "vrepli.d", "$vd, $imm">; +} diff --git a/llvm/lib/Target/LoongArch/LoongArchRegisterInfo.td b/llvm/lib/Target/LoongArch/LoongArchRegisterInfo.td --- a/llvm/lib/Target/LoongArch/LoongArchRegisterInfo.td +++ b/llvm/lib/Target/LoongArch/LoongArchRegisterInfo.td @@ -37,6 +37,12 @@ let SubRegIndices = [sub_32]; } +def sub_64 : SubRegIndex<64>; +class LoongArchReg128 + : LoongArchRegWithSubRegs { + let SubRegIndices = [sub_64]; +} + let FallbackRegAltNameIndex = NoRegAltName in def RegAliasName : RegAltNameIndex; } // Namespace = "LoongArch" @@ -174,3 +180,13 @@ let isAllocatable = false in def FCSR : RegisterClass<"LoongArch", [i32], 32, (sequence "FCSR%u", 0, 3)>; + +// LSX registers + +foreach I = 0-31 in +def VR#I : LoongArchReg128("F"#I#"_64"), "vr"#I>, + DwarfRegAlias("F"#I#"_64")>; + +def LSX128 : RegisterClass<"LoongArch", + [v4f32, v2f64, v16i8, v8i16, v4i32, v2i64], + 128, (sequence "VR%u", 0, 31)>; diff --git a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCCodeEmitter.cpp b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCCodeEmitter.cpp --- a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCCodeEmitter.cpp +++ b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCCodeEmitter.cpp @@ -43,6 +43,10 @@ SmallVectorImpl &Fixups, const MCSubtargetInfo &STI) const override; + void expandToLDI(const MCInst &MI, SmallVectorImpl &CB, + SmallVectorImpl &Fixups, + const MCSubtargetInfo &STI) const; + /// TableGen'erated function for getting the binary encoding for an /// instruction. uint64_t getBinaryCodeForInstr(const MCInst &MI, @@ -65,12 +69,21 @@ /// Return binary encoding of an immediate operand specified by OpNo. /// The value returned is the value of the immediate shifted right - // arithmetically by 2. + // arithmetically by N. /// Note that this function is dedicated to specific immediate types, /// e.g. simm14_lsl2, simm16_lsl2, simm21_lsl2 and simm26_lsl2. - unsigned getImmOpValueAsr2(const MCInst &MI, unsigned OpNo, - SmallVectorImpl &Fixups, - const MCSubtargetInfo &STI) const; + template + unsigned getImmOpValueAsr(const MCInst &MI, unsigned OpNo, + SmallVectorImpl &Fixups, + const MCSubtargetInfo &STI) const { + const MCOperand &MO = MI.getOperand(OpNo); + if (MO.isImm()) { + unsigned Res = MI.getOperand(OpNo).getImm(); + assert((Res & ((1U << N) - 1U)) == 0 && "lowest N bits are non-zero"); + return Res >> N; + } + return getExprOpValue(MI, MO, Fixups, STI); + } unsigned getExprOpValue(const MCInst &MI, const MCOperand &MO, SmallVectorImpl &Fixups, @@ -101,21 +114,6 @@ return MI.getOperand(OpNo).getImm() - 1; } -unsigned -LoongArchMCCodeEmitter::getImmOpValueAsr2(const MCInst &MI, unsigned OpNo, - SmallVectorImpl &Fixups, - const MCSubtargetInfo &STI) const { - const MCOperand &MO = MI.getOperand(OpNo); - - if (MO.isImm()) { - unsigned Res = MI.getOperand(OpNo).getImm(); - assert((Res & 3) == 0 && "lowest 2 bits are non-zero"); - return Res >> 2; - } - - return getExprOpValue(MI, MO, Fixups, STI); -} - unsigned LoongArchMCCodeEmitter::getExprOpValue(const MCInst &MI, const MCOperand &MO, SmallVectorImpl &Fixups, @@ -273,6 +271,30 @@ return 0; } +void LoongArchMCCodeEmitter::expandToLDI(const MCInst &MI, + SmallVectorImpl &CB, + SmallVectorImpl &Fixups, + const MCSubtargetInfo &STI) const { + int64_t Imm = MI.getOperand(1).getImm() & 0x3FF; + switch (MI.getOpcode()) { + case LoongArch::PseudoVREPLI_B: + break; + case LoongArch::PseudoVREPLI_H: + Imm |= 0x400; + break; + case LoongArch::PseudoVREPLI_W: + Imm |= 0x800; + break; + case LoongArch::PseudoVREPLI_D: + Imm |= 0xC00; + break; + } + MCInst TmpInst = + MCInstBuilder(LoongArch::VLDI).addOperand(MI.getOperand(0)).addImm(Imm); + uint32_t Binary = getBinaryCodeForInstr(TmpInst, Fixups, STI); + support::endian::write(CB, Binary, support::little); +} + void LoongArchMCCodeEmitter::encodeInstruction( const MCInst &MI, SmallVectorImpl &CB, SmallVectorImpl &Fixups, const MCSubtargetInfo &STI) const { @@ -280,6 +302,16 @@ // Get byte count of instruction. unsigned Size = Desc.getSize(); + switch (MI.getOpcode()) { + default: + break; + case LoongArch::PseudoVREPLI_B: + case LoongArch::PseudoVREPLI_H: + case LoongArch::PseudoVREPLI_W: + case LoongArch::PseudoVREPLI_D: + return expandToLDI(MI, CB, Fixups, STI); + } + switch (Size) { default: llvm_unreachable("Unhandled encodeInstruction length!");