[llvm] r320024 - [RISCV] MC layer support for the standard RV64I instructions

Alex Bradbury via llvm-commits llvm-commits at lists.llvm.org
Thu Dec 7 02:53:49 PST 2017


Author: asb
Date: Thu Dec  7 02:53:48 2017
New Revision: 320024

URL: http://llvm.org/viewvc/llvm-project?rev=320024&view=rev
Log:
[RISCV] MC layer support for the standard RV64I instructions

Added:
    llvm/trunk/test/MC/RISCV/rv64i-invalid.s
    llvm/trunk/test/MC/RISCV/rv64i-valid.s
Modified:
    llvm/trunk/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp
    llvm/trunk/lib/Target/RISCV/RISCV.td
    llvm/trunk/lib/Target/RISCV/RISCVInstrFormats.td
    llvm/trunk/lib/Target/RISCV/RISCVInstrInfo.td
    llvm/trunk/test/MC/RISCV/rv32i-invalid.s

Modified: llvm/trunk/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp?rev=320024&r1=320023&r2=320024&view=diff
==============================================================================
--- llvm/trunk/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp (original)
+++ llvm/trunk/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp Thu Dec  7 02:53:48 2017
@@ -31,6 +31,7 @@ struct RISCVOperand;
 
 class RISCVAsmParser : public MCTargetAsmParser {
   SMLoc getLoc() const { return getParser().getTok().getLoc(); }
+  bool isRV64() const { return getSTI().hasFeature(RISCV::Feature64Bit); }
 
   unsigned validateTargetOperandClass(MCParsedAsmOperand &Op,
                                       unsigned Kind) override;
@@ -91,6 +92,8 @@ struct RISCVOperand : public MCParsedAsm
     Immediate,
   } Kind;
 
+  bool IsRV64;
+
   struct RegOp {
     unsigned RegNum;
   };
@@ -111,6 +114,7 @@ struct RISCVOperand : public MCParsedAsm
 public:
   RISCVOperand(const RISCVOperand &o) : MCParsedAsmOperand() {
     Kind = o.Kind;
+    IsRV64 = o.IsRV64;
     StartLoc = o.StartLoc;
     EndLoc = o.EndLoc;
     switch (Kind) {
@@ -202,6 +206,16 @@ public:
     return RISCVFPRndMode::stringToRoundingMode(Str) != RISCVFPRndMode::Invalid;
   }
 
+  bool isUImmLog2XLen() const {
+    int64_t Imm;
+    RISCVMCExpr::VariantKind VK;
+    if (!isImm())
+      return false;
+    if (!evaluateConstantImm(Imm, VK) || VK != RISCVMCExpr::VK_RISCV_None)
+      return false;
+    return (isRV64() && isUInt<6>(Imm)) || isUInt<5>(Imm);
+  }
+
   bool isUImm5() const {
     int64_t Imm;
     RISCVMCExpr::VariantKind VK;
@@ -259,6 +273,8 @@ public:
   SMLoc getStartLoc() const override { return StartLoc; }
   /// getEndLoc - Gets location of the last token of this operand
   SMLoc getEndLoc() const override { return EndLoc; }
+  /// True if this operand is for an RV64 instruction
+  bool isRV64() const { return IsRV64; }
 
   unsigned getReg() const override {
     assert(Kind == Register && "Invalid type access!");
@@ -290,29 +306,33 @@ public:
     }
   }
 
-  static std::unique_ptr<RISCVOperand> createToken(StringRef Str, SMLoc S) {
+  static std::unique_ptr<RISCVOperand> createToken(StringRef Str, SMLoc S,
+                                                   bool IsRV64) {
     auto Op = make_unique<RISCVOperand>(Token);
     Op->Tok = Str;
     Op->StartLoc = S;
     Op->EndLoc = S;
+    Op->IsRV64 = IsRV64;
     return Op;
   }
 
   static std::unique_ptr<RISCVOperand> createReg(unsigned RegNo, SMLoc S,
-                                                 SMLoc E) {
+                                                 SMLoc E, bool IsRV64) {
     auto Op = make_unique<RISCVOperand>(Register);
     Op->Reg.RegNum = RegNo;
     Op->StartLoc = S;
     Op->EndLoc = E;
+    Op->IsRV64 = IsRV64;
     return Op;
   }
 
   static std::unique_ptr<RISCVOperand> createImm(const MCExpr *Val, SMLoc S,
-                                                 SMLoc E) {
+                                                 SMLoc E, bool IsRV64) {
     auto Op = make_unique<RISCVOperand>(Immediate);
     Op->Imm.Val = Val;
     Op->StartLoc = S;
     Op->EndLoc = E;
+    Op->IsRV64 = IsRV64;
     return Op;
   }
 
@@ -482,6 +502,10 @@ bool RISCVAsmParser::MatchAndEmitInstruc
     }
     return Error(ErrorLoc, "invalid operand for instruction");
   }
+  case Match_InvalidUImmLog2XLen:
+    if (isRV64())
+      return generateImmOutOfRangeError(Operands, ErrorInfo, 0, (1 << 6) - 1);
+    return generateImmOutOfRangeError(Operands, ErrorInfo, 0, (1 << 5) - 1);
   case Match_InvalidUImm5:
     return generateImmOutOfRangeError(Operands, ErrorInfo, 0, (1 << 5) - 1);
   case Match_InvalidSImm12:
@@ -562,16 +586,16 @@ OperandMatchResultTy RISCVAsmParser::par
       }
     }
     if (HadParens)
-      Operands.push_back(RISCVOperand::createToken("(", FirstS));
+      Operands.push_back(RISCVOperand::createToken("(", FirstS, isRV64()));
     SMLoc S = getLoc();
     SMLoc E = SMLoc::getFromPointer(S.getPointer() - 1);
     getLexer().Lex();
-    Operands.push_back(RISCVOperand::createReg(RegNo, S, E));
+    Operands.push_back(RISCVOperand::createReg(RegNo, S, E, isRV64()));
   }
 
   if (HadParens) {
     getParser().Lex(); // Eat ')'
-    Operands.push_back(RISCVOperand::createToken(")", getLoc()));
+    Operands.push_back(RISCVOperand::createToken(")", getLoc(), isRV64()));
   }
 
   return MatchOperand_Success;
@@ -605,7 +629,7 @@ OperandMatchResultTy RISCVAsmParser::par
     return parseOperandWithModifier(Operands);
   }
 
-  Operands.push_back(RISCVOperand::createImm(Res, S, E));
+  Operands.push_back(RISCVOperand::createImm(Res, S, E, isRV64()));
   return MatchOperand_Success;
 }
 
@@ -645,7 +669,7 @@ RISCVAsmParser::parseOperandWithModifier
   }
 
   const MCExpr *ModExpr = RISCVMCExpr::create(SubExpr, VK, getContext());
-  Operands.push_back(RISCVOperand::createImm(ModExpr, S, E));
+  Operands.push_back(RISCVOperand::createImm(ModExpr, S, E, isRV64()));
   return MatchOperand_Success;
 }
 
@@ -657,7 +681,7 @@ RISCVAsmParser::parseMemOpBaseReg(Operan
   }
 
   getParser().Lex(); // Eat '('
-  Operands.push_back(RISCVOperand::createToken("(", getLoc()));
+  Operands.push_back(RISCVOperand::createToken("(", getLoc(), isRV64()));
 
   if (parseRegister(Operands) != MatchOperand_Success) {
     Error(getLoc(), "expected register");
@@ -670,7 +694,7 @@ RISCVAsmParser::parseMemOpBaseReg(Operan
   }
 
   getParser().Lex(); // Eat ')'
-  Operands.push_back(RISCVOperand::createToken(")", getLoc()));
+  Operands.push_back(RISCVOperand::createToken(")", getLoc(), isRV64()));
 
   return MatchOperand_Success;
 }
@@ -700,7 +724,7 @@ bool RISCVAsmParser::ParseInstruction(Pa
                                       StringRef Name, SMLoc NameLoc,
                                       OperandVector &Operands) {
   // First operand is token for instruction
-  Operands.push_back(RISCVOperand::createToken(Name, NameLoc));
+  Operands.push_back(RISCVOperand::createToken(Name, NameLoc, isRV64()));
 
   // If there are no more operands, then finish
   if (getLexer().is(AsmToken::EndOfStatement))

Modified: llvm/trunk/lib/Target/RISCV/RISCV.td
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/RISCV/RISCV.td?rev=320024&r1=320023&r2=320024&view=diff
==============================================================================
--- llvm/trunk/lib/Target/RISCV/RISCV.td (original)
+++ llvm/trunk/lib/Target/RISCV/RISCV.td Thu Dec  7 02:53:48 2017
@@ -40,6 +40,8 @@ def HasStdExtD : Predicate<"Subtarget->h
 
 def Feature64Bit
     : SubtargetFeature<"64bit", "HasRV64", "true", "Implements RV64">;
+def IsRV64 : Predicate<"Subtarget->is64Bit()">,
+                       AssemblerPredicate<"Feature64Bit">;
 
 def RV64           : HwMode<"+64bit">;
 def RV32           : HwMode<"-64bit">;

Modified: llvm/trunk/lib/Target/RISCV/RISCVInstrFormats.td
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/RISCV/RISCVInstrFormats.td?rev=320024&r1=320023&r2=320024&view=diff
==============================================================================
--- llvm/trunk/lib/Target/RISCV/RISCVInstrFormats.td (original)
+++ llvm/trunk/lib/Target/RISCV/RISCVInstrFormats.td Thu Dec  7 02:53:48 2017
@@ -188,6 +188,23 @@ class RVInstI<bits<3> funct3, RISCVOpcod
 class RVInstIShift<bit arithshift, bits<3> funct3, RISCVOpcode opcode,
                    dag outs, dag ins, string opcodestr, string argstr>
     : RVInst<outs, ins, opcodestr, argstr, [], InstFormatI> {
+  bits<6> shamt;
+  bits<5> rs1;
+  bits<5> rd;
+
+  let Inst{31} = 0;
+  let Inst{30} = arithshift;
+  let Inst{29-26} = 0;
+  let Inst{25-20} = shamt;
+  let Inst{19-15} = rs1;
+  let Inst{14-12} = funct3;
+  let Inst{11-7} = rd;
+  let Opcode = opcode.Value;
+}
+
+class RVInstIShiftW<bit arithshift, bits<3> funct3, RISCVOpcode opcode,
+                    dag outs, dag ins, string opcodestr, string argstr>
+    : RVInst<outs, ins, opcodestr, argstr, [], InstFormatI> {
   bits<5> shamt;
   bits<5> rs1;
   bits<5> rd;

Modified: llvm/trunk/lib/Target/RISCV/RISCVInstrInfo.td
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/RISCV/RISCVInstrInfo.td?rev=320024&r1=320023&r2=320024&view=diff
==============================================================================
--- llvm/trunk/lib/Target/RISCV/RISCVInstrInfo.td (original)
+++ llvm/trunk/lib/Target/RISCV/RISCVInstrInfo.td Thu Dec  7 02:53:48 2017
@@ -69,6 +69,22 @@ def fencearg : Operand<XLenVT> {
   let DecoderMethod = "decodeUImmOperand<4>";
 }
 
+def UImmLog2XLenAsmOperand : AsmOperandClass {
+  let Name = "UImmLog2XLen";
+  let RenderMethod = "addImmOperands";
+  let DiagnosticType = "InvalidUImmLog2XLen";
+}
+
+def uimmlog2xlen : Operand<XLenVT>, ImmLeaf<XLenVT, [{
+  if (Subtarget->is64Bit())
+    return isUInt<6>(Imm);
+  return isUInt<5>(Imm);
+}]> {
+  let ParserMatchClass = UImmLog2XLenAsmOperand;
+  // TODO: should ensure invalid shamt is rejected when decoding.
+  let DecoderMethod = "decodeUImmOperand<6>";
+}
+
 def uimm5 : Operand<XLenVT>, ImmLeaf<XLenVT, [{return isUInt<5>(Imm);}]> {
   let ParserMatchClass = UImmAsmOperand<5>;
   let DecoderMethod = "decodeUImmOperand<5>";
@@ -161,7 +177,7 @@ class ALU_ri<bits<3> funct3, string opco
 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
 class Shift_ri<bit arithshift, bits<3> funct3, string opcodestr>
     : RVInstIShift<arithshift, funct3, OPC_OP_IMM, (outs GPR:$rd),
-                   (ins GPR:$rs1, uimm5:$shamt), opcodestr,
+                   (ins GPR:$rs1, uimmlog2xlen:$shamt), opcodestr,
                    "$rd, $rs1, $shamt">;
 
 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
@@ -180,6 +196,17 @@ class CSR_ii<bits<3> funct3, string opco
               (ins uimm12:$imm12, uimm5:$rs1),
               opcodestr, "$rd, $imm12, $rs1">;
 
+let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
+class ShiftW_ri<bit arithshift, bits<3> funct3, string opcodestr>
+    : RVInstIShiftW<arithshift, funct3, OPC_OP_IMM_32, (outs GPR:$rd),
+                    (ins GPR:$rs1, uimm5:$shamt), opcodestr,
+                    "$rd, $rs1, $shamt">;
+
+let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
+class ALUW_rr<bits<7> funct7, bits<3> funct3, string opcodestr>
+    : RVInstR<funct7, funct3, OPC_OP_32, (outs GPR:$rd),
+              (ins GPR:$rs1, GPR:$rs2), opcodestr, "$rd, $rs1, $rs2">;
+
 //===----------------------------------------------------------------------===//
 // Instructions
 //===----------------------------------------------------------------------===//
@@ -279,6 +306,29 @@ def CSRRWI : CSR_ii<0b101, "csrrwi">;
 def CSRRSI : CSR_ii<0b110, "csrrsi">;
 def CSRRCI : CSR_ii<0b111, "csrrci">;
 
+/// RV64I instructions
+
+let Predicates = [IsRV64] in {
+def LWU   : Load_ri<0b110, "lwu">;
+def LD    : Load_ri<0b011, "ld">;
+def SD    : Store_rri<0b011, "sd">;
+
+let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
+def ADDIW : RVInstI<0b000, OPC_OP_IMM_32, (outs GPR:$rd),
+                    (ins GPR:$rs1, simm12:$imm12),
+                    "addiw", "$rd, $rs1, $imm12">;
+
+def SLLIW : ShiftW_ri<0, 0b001, "slliw">;
+def SRLIW : ShiftW_ri<0, 0b101, "srliw">;
+def SRAIW : ShiftW_ri<1, 0b101, "sraiw">;
+
+def ADDW  : ALUW_rr<0b0000000, 0b000, "addw">;
+def SUBW  : ALUW_rr<0b0100000, 0b000, "subw">;
+def SLLW  : ALUW_rr<0b0000000, 0b001, "sllw">;
+def SRLW  : ALUW_rr<0b0000000, 0b101, "srlw">;
+def SRAW  : ALUW_rr<0b0100000, 0b101, "sraw">;
+} // Predicates = [IsRV64]
+
 //===----------------------------------------------------------------------===//
 // Pseudo-instructions and codegen patterns
 //
@@ -293,9 +343,9 @@ class PatGprGpr<SDPatternOperator OpNode
     : Pat<(OpNode GPR:$rs1, GPR:$rs2), (Inst GPR:$rs1, GPR:$rs2)>;
 class PatGprSimm12<SDPatternOperator OpNode, RVInstI Inst>
     : Pat<(OpNode GPR:$rs1, simm12:$imm12), (Inst GPR:$rs1, simm12:$imm12)>;
-class PatGprUimm5<SDPatternOperator OpNode, RVInstIShift Inst>
-    : Pat<(OpNode GPR:$rs1, uimm5:$shamt),
-          (Inst GPR:$rs1, uimm5:$shamt)>;
+class PatGprUimmLog2XLen<SDPatternOperator OpNode, RVInstIShift Inst>
+    : Pat<(OpNode GPR:$rs1, uimmlog2xlen:$shamt),
+          (Inst GPR:$rs1, uimmlog2xlen:$shamt)>;
 
 /// Immediates
 
@@ -315,11 +365,11 @@ def : PatGprSimm12<and, ANDI>;
 def : PatGprGpr<xor, XOR>;
 def : PatGprSimm12<xor, XORI>;
 def : PatGprGpr<shl, SLL>;
-def : PatGprUimm5<shl, SLLI>;
+def : PatGprUimmLog2XLen<shl, SLLI>;
 def : PatGprGpr<srl, SRL>;
-def : PatGprUimm5<srl, SRLI>;
+def : PatGprUimmLog2XLen<srl, SRLI>;
 def : PatGprGpr<sra, SRA>;
-def : PatGprUimm5<sra, SRAI>;
+def : PatGprUimmLog2XLen<sra, SRAI>;
 
 /// Setcc
 

Modified: llvm/trunk/test/MC/RISCV/rv32i-invalid.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/RISCV/rv32i-invalid.s?rev=320024&r1=320023&r2=320024&view=diff
==============================================================================
--- llvm/trunk/test/MC/RISCV/rv32i-invalid.s (original)
+++ llvm/trunk/test/MC/RISCV/rv32i-invalid.s Thu Dec  7 02:53:48 2017
@@ -111,8 +111,8 @@ slti a10, a2, 0x20 # CHECK: :[[@LINE]]:6
 slt x32, s0, s0 # CHECK: :[[@LINE]]:5: error: invalid operand for instruction
 
 # RV64I mnemonics
-addiw a0, sp, 100 # CHECK: :[[@LINE]]:1: error: unrecognized instruction mnemonic
-sraw t0, s2, zero # CHECK: :[[@LINE]]:1: error: unrecognized instruction mnemonic
+addiw a0, sp, 100 # CHECK: :[[@LINE]]:1: error: instruction use requires an option to be enabled
+sraw t0, s2, zero # CHECK: :[[@LINE]]:1: error: instruction use requires an option to be enabled
 
 # Invalid operand types
 xori sp, 22, 220 # CHECK: :[[@LINE]]:10: error: invalid operand for instruction

Added: llvm/trunk/test/MC/RISCV/rv64i-invalid.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/RISCV/rv64i-invalid.s?rev=320024&view=auto
==============================================================================
--- llvm/trunk/test/MC/RISCV/rv64i-invalid.s (added)
+++ llvm/trunk/test/MC/RISCV/rv64i-invalid.s Thu Dec  7 02:53:48 2017
@@ -0,0 +1,20 @@
+# RUN: not llvm-mc -triple riscv64 < %s 2>&1 | FileCheck %s
+
+# Out of range immediates
+## uimm5
+slliw a0, a0, 32 # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [0, 31]
+srliw a0, a0, -1 # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [0, 31]
+sraiw a0, a0, -19 # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [0, 31]
+
+## simm12
+addiw a0, a1, -2049 # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [-2048, 2047]
+ld ra, 2048(sp) # CHECK: :[[@LINE]]:8: error: immediate must be an integer in the range [-2048, 2047]
+
+# Illegal operand modifier
+## uimm5
+slliw a0, a0, %lo(1) # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [0, 31]
+srliw a0, a0, %lo(a) # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [0, 31]
+sraiw a0, a0, %hi(2) # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [0, 31]
+
+## simm12
+addiw a0, a1, %hi(foo) # CHECK: :[[@LINE]]:15: error: immediate must be an integer in the range [-2048, 2047]

Added: llvm/trunk/test/MC/RISCV/rv64i-valid.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/RISCV/rv64i-valid.s?rev=320024&view=auto
==============================================================================
--- llvm/trunk/test/MC/RISCV/rv64i-valid.s (added)
+++ llvm/trunk/test/MC/RISCV/rv64i-valid.s Thu Dec  7 02:53:48 2017
@@ -0,0 +1,98 @@
+# RUN: llvm-mc %s -triple=riscv64 -show-encoding \
+# RUN:     | FileCheck -check-prefixes=CHECK,CHECK-INST %s
+# RUN: llvm-mc -filetype=obj -triple riscv64 < %s \
+# RUN:     | llvm-objdump -d - | FileCheck -check-prefix=CHECK-INST %s
+
+# CHECK-INST: lwu zero, 4(ra)
+# CHECK: encoding: [0x03,0xe0,0x40,0x00]
+lwu x0, 4(x1)
+# CHECK-INST: lwu sp, 4(gp)
+# CHECK: encoding: [0x03,0xe1,0x41,0x00]
+lwu x2, +4(x3)
+# CHECK-INST: lwu tp, -2048(t0)
+# CHECK: encoding: [0x03,0xe2,0x02,0x80]
+lwu x4, -2048(x5)
+# CHECK-INST: lwu t1, -2048(t2)
+# CHECK: encoding: [0x03,0xe3,0x03,0x80]
+lwu x6, %lo(2048)(x7)
+# CHECK-INST: lwu s0, 2047(s1)
+# CHECK: encoding: [0x03,0xe4,0xf4,0x7f]
+lwu x8, 2047(x9)
+
+# CHECK-INST: ld a0, -2048(a1)
+# CHECK: encoding: [0x03,0xb5,0x05,0x80]
+ld x10, -2048(x11)
+# CHECK-INST: ld a2, -2048(a3)
+# CHECK: encoding: [0x03,0xb6,0x06,0x80]
+ld x12, %lo(2048)(x13)
+# CHECK-INST: ld a4, 2047(a5)
+# CHECK: encoding: [0x03,0xb7,0xf7,0x7f]
+ld x14, 2047(x15)
+
+# CHECK-INST: sd a6, -2048(a7)
+# CHECK: encoding: [0x23,0xb0,0x08,0x81]
+sd x16, -2048(x17)
+# CHECK-INST: sd s2, -2048(s3)
+# CHECK: encoding: [0x23,0xb0,0x29,0x81]
+sd x18, %lo(2048)(x19)
+# CHECK-INST: sd s4, 2047(s5)
+# CHECK: encoding: [0xa3,0xbf,0x4a,0x7f]
+sd x20, 2047(x21)
+
+# CHECK-INST: slli s6, s7, 45
+# CHECK: encoding: [0x13,0x9b,0xdb,0x02]
+slli x22, x23, 45
+# CHECK-INST: srli s8, s9, 0
+# CHECK: encoding: [0x13,0xdc,0x0c,0x00]
+srli x24, x25, 0
+# CHECK-INST: srai s10, s11, 31
+# CHECK: encoding: [0x13,0xdd,0xfd,0x41]
+srai x26, x27, 31
+
+# CHECK-INST: addiw t3, t4, -2048
+# CHECK: encoding: [0x1b,0x8e,0x0e,0x80]
+addiw x28, x29, -2048
+# CHECK-INST: addiw t5, t6, 2047
+# CHECK: encoding: [0x1b,0x8f,0xff,0x7f]
+addiw x30, x31, 2047
+
+# CHECK-INST: slliw zero, ra, 0
+# CHECK: encoding: [0x1b,0x90,0x00,0x00]
+slliw zero, ra, 0
+# CHECK-INST: slliw sp, gp, 31
+# CHECK: encoding: [0x1b,0x91,0xf1,0x01]
+slliw sp, gp, 31
+# CHECK-INST: srliw tp, t0, 0
+# CHECK: encoding: [0x1b,0xd2,0x02,0x00]
+srliw tp, t0, 0
+# CHECK-INST: srliw t1, t2, 31
+# CHECK: encoding: [0x1b,0xd3,0xf3,0x01]
+srliw t1, t2, 31
+# CHECK-INST: sraiw s0, s1, 0
+# CHECK: encoding: [0x1b,0xd4,0x04,0x40]
+sraiw s0, s1, 0
+# CHECK-INST: sraiw a0, a1, 31
+# CHECK: encoding: [0x1b,0xd5,0xf5,0x41]
+sraiw a0, a1, 31
+
+# CHECK-INST: addw a2, a3, a4
+# CHECK: encoding: [0x3b,0x86,0xe6,0x00]
+addw a2, a3, a4
+# CHECK-INST: addw a5, a6, a7
+# CHECK: encoding: [0xbb,0x07,0x18,0x01]
+addw a5, a6, a7
+# CHECK-INST: subw s2, s3, s4
+# CHECK: encoding: [0x3b,0x89,0x49,0x41]
+subw s2, s3, s4
+# CHECK-INST: subw s5, s6, s7
+# CHECK: encoding: [0xbb,0x0a,0x7b,0x41]
+subw s5, s6, s7
+# CHECK-INST: sllw s8, s9, s10
+# CHECK: encoding: [0x3b,0x9c,0xac,0x01]
+sllw s8, s9, s10
+# CHECK-INST: srlw s11, t3, t4
+# CHECK: encoding: [0xbb,0x5d,0xde,0x01]
+srlw s11, t3, t4
+# CHECK-INST: sraw t5, t6, zero
+# CHECK: encoding: [0x3b,0xdf,0x0f,0x40]
+sraw t5, t6, zero




More information about the llvm-commits mailing list