diff options
Diffstat (limited to 'llvm/lib')
-rw-r--r-- | llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp | 25 | ||||
-rw-r--r-- | llvm/lib/Target/RISCV/RISCVInstrInfoC.td | 18 |
2 files changed, 34 insertions, 9 deletions
diff --git a/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp b/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp index 3299a53ff5b..64f59c230ec 100644 --- a/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp +++ b/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp @@ -260,6 +260,19 @@ public: (VK == RISCVMCExpr::VK_RISCV_None || VK == RISCVMCExpr::VK_RISCV_LO); } + bool isSImm6NonZero() const { + RISCVMCExpr::VariantKind VK; + int64_t Imm; + bool IsValid; + bool IsConstantImm = evaluateConstantImm(Imm, VK); + if (!IsConstantImm) + IsValid = RISCVAsmParser::classifySymbolRef(getImm(), VK, Imm); + else + IsValid = ((Imm != 0) && isInt<6>(Imm)); + return IsValid && + (VK == RISCVMCExpr::VK_RISCV_None || VK == RISCVMCExpr::VK_RISCV_LO); + } + bool isUImm6NonZero() const { int64_t Imm; RISCVMCExpr::VariantKind VK; @@ -338,11 +351,11 @@ public: bool isSImm13Lsb0() const { return isBareSimmNLsb0<13>(); } - bool isSImm10Lsb0000() const { + bool isSImm10Lsb0000NonZero() const { int64_t Imm; RISCVMCExpr::VariantKind VK; bool IsConstantImm = evaluateConstantImm(Imm, VK); - return IsConstantImm && isShiftedInt<6, 4>(Imm) && + return IsConstantImm && (Imm != 0) && isShiftedInt<6, 4>(Imm) && VK == RISCVMCExpr::VK_RISCV_None; } @@ -613,6 +626,10 @@ bool RISCVAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, case Match_InvalidSImm6: return generateImmOutOfRangeError(Operands, ErrorInfo, -(1 << 5), (1 << 5) - 1); + case Match_InvalidSImm6NonZero: + return generateImmOutOfRangeError(Operands, ErrorInfo, -(1 << 5), + (1 << 5) - 1, + "immediate must be non-zero in the range"); case Match_InvalidUImm6NonZero: return generateImmOutOfRangeError(Operands, ErrorInfo, 1, (1 << 6) - 1); case Match_InvalidUImm7Lsb00: @@ -639,10 +656,10 @@ bool RISCVAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, return generateImmOutOfRangeError( Operands, ErrorInfo, 4, (1 << 10) - 4, "immediate must be a multiple of 4 bytes in the range"); - case Match_InvalidSImm10Lsb0000: + case Match_InvalidSImm10Lsb0000NonZero: return generateImmOutOfRangeError( Operands, ErrorInfo, -(1 << 9), (1 << 9) - 16, - "immediate must be a multiple of 16 bytes in the range"); + "immediate must be a multiple of 16 bytes and non-zero in the range"); case Match_InvalidSImm12: return generateImmOutOfRangeError(Operands, ErrorInfo, -(1 << 11), (1 << 11) - 1); diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoC.td b/llvm/lib/Target/RISCV/RISCVInstrInfoC.td index f39b128099d..fc9c1dea5a8 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoC.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoC.td @@ -35,6 +35,13 @@ def simm6 : Operand<XLenVT>, ImmLeaf<XLenVT, [{return isInt<6>(Imm);}]> { let DecoderMethod = "decodeSImmOperand<6>"; } +def simm6nonzero : Operand<XLenVT>, + ImmLeaf<XLenVT, [{return (Imm != 0) && isInt<6>(Imm);}]> { + let ParserMatchClass = SImmAsmOperand<6, "NonZero">; + let EncoderMethod = "getImmOpValue"; + let DecoderMethod = "decodeSImmOperand<6>"; +} + def uimm6nonzero : Operand<XLenVT>, ImmLeaf<XLenVT, [{return isUInt<6>(Imm) && (Imm != 0);}]> { let ParserMatchClass = UImmAsmOperand<6, "NonZero">; @@ -91,9 +98,10 @@ def uimm10_lsb00nonzero : Operand<XLenVT>, } // A 10-bit signed immediate where the least significant four bits are zero. -def simm10_lsb0000 : Operand<XLenVT>, - ImmLeaf<XLenVT, [{return isShiftedInt<6, 4>(Imm);}]> { - let ParserMatchClass = SImmAsmOperand<10, "Lsb0000">; +def simm10_lsb0000nonzero : Operand<XLenVT>, + ImmLeaf<XLenVT, + [{return (Imm != 0) && isShiftedInt<6, 4>(Imm);}]> { + let ParserMatchClass = SImmAsmOperand<10, "Lsb0000NonZero">; let EncoderMethod = "getImmOpValue"; let DecoderMethod = "decodeSImmOperand<10>"; } @@ -253,7 +261,7 @@ def C_NOP : RVInst16CI<0b000, 0b01, (outs), (ins), "c.nop", "">; let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in def C_ADDI : RVInst16CI<0b000, 0b01, (outs GPRNoX0:$rd_wb), - (ins GPRNoX0:$rd, simm6:$imm), + (ins GPRNoX0:$rd, simm6nonzero:$imm), "c.addi", "$rd, $imm"> { let Constraints = "$rd = $rd_wb"; let Inst{6-2} = imm{4-0}; @@ -282,7 +290,7 @@ def C_LI : RVInst16CI<0b010, 0b01, (outs GPRNoX0:$rd), (ins simm6:$imm), let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in def C_ADDI16SP : RVInst16CI<0b011, 0b01, (outs SP:$rd_wb), - (ins SP:$rd, simm10_lsb0000:$imm), + (ins SP:$rd, simm10_lsb0000nonzero:$imm), "c.addi16sp", "$rd, $imm"> { let Constraints = "$rd = $rd_wb"; let Inst{12} = imm{9}; |