diff --git a/llvm/lib/Target/M68k/AsmParser/M68kAsmParser.cpp b/llvm/lib/Target/M68k/AsmParser/M68kAsmParser.cpp --- a/llvm/lib/Target/M68k/AsmParser/M68kAsmParser.cpp +++ b/llvm/lib/Target/M68k/AsmParser/M68kAsmParser.cpp @@ -177,6 +177,11 @@ static std::unique_ptr createImm(const MCExpr *Expr, SMLoc Start, SMLoc End); + // Imm for TRAP instruction + bool isTrapImm() const; + // Imm for BKPT instruction + bool isBkptImm() const; + // MoveMask bool isMoveMask() const; void addMoveMaskOperands(MCInst &Inst, unsigned N) const; @@ -351,6 +356,22 @@ return Op; } +bool M68kOperand::isTrapImm() const { + int64_t Value; + if (!isImm() || !Expr->evaluateAsAbsolute(Value)) + return false; + + return isUInt<4>(Value); +} + +bool M68kOperand::isBkptImm() const { + int64_t Value; + if (!isImm() || !Expr->evaluateAsAbsolute(Value)) + return false; + + return isUInt<3>(Value); +} + // MoveMask bool M68kOperand::isMoveMask() const { if (!isMemOp()) diff --git a/llvm/lib/Target/M68k/M68kInstrControl.td b/llvm/lib/Target/M68k/M68kInstrControl.td --- a/llvm/lib/Target/M68k/M68kInstrControl.td +++ b/llvm/lib/Target/M68k/M68kInstrControl.td @@ -351,3 +351,41 @@ (ADDX8dd MxDRD8:$op, (MOV8di 0))>; def : Pat<(sub MxXRD32:$op, (i32 (MxSetCC_C MxCONDcs, CCR))), (ADDX32dd MxDRD32:$op, (MOV32ri 0))>; + +//===------------===// +// Trap / Breakpoint +//===------------===// + +let RenderMethod = "addImmOperands", ParserMethod = "parseImm" in { + def MxTrapImm : AsmOperandClass { + let Name = "MxTrapImm"; + let PredicateMethod = "isTrapImm"; + } + + def MxBkptImm : AsmOperandClass { + let Name = "MxBkptImm"; + let PredicateMethod = "isBkptImm"; + } +} + +let ParserMatchClass = MxTrapImm in +def MxTrapimm : MxOp; + +let ParserMatchClass = MxBkptImm in +def MxBkptimm : MxOp; + +def TRAP : MxInst<(outs), (ins MxTrapimm:$vect), "trap\t$vect", []> { + let Inst = (descend 0b0100, 0b1110, 0b0100, (operand "$vect", 4)); +} + +def TRAPV : MxInst<(outs), (ins), "trapv", []> { + let Inst = (descend 0b0100, 0b1110, 0b0111, 0b0110); +} + +def BKPT : MxInst<(outs), (ins MxBkptimm:$vect), "bkpt\t$vect", []> { + let Inst = (descend 0b0100, 0b1000, 0b0100, 0b1 , (operand "$vect", 3)); +} + +def ILLEGAL : MxInst<(outs), (ins), "illegal", []> { + let Inst = (descend 0b0100, 0b1010, 0b1111, 0b1100); +} diff --git a/llvm/test/MC/Disassembler/M68k/trap-break.txt b/llvm/test/MC/Disassembler/M68k/trap-break.txt new file mode 100644 --- /dev/null +++ b/llvm/test/MC/Disassembler/M68k/trap-break.txt @@ -0,0 +1,11 @@ +# RUN: llvm-mc -disassemble -triple m68k %s | FileCheck %s + +; CHECK: trap #13 +0x4e 0x4d +# CHECK: bkpt #7 +0x48 0x4f +# CHECK: trapv +0x4e 0x76 +# CHECK: illegal +0x4a 0xfc + diff --git a/llvm/test/MC/M68k/Control/trap-break.s b/llvm/test/MC/M68k/Control/trap-break.s new file mode 100644 --- /dev/null +++ b/llvm/test/MC/M68k/Control/trap-break.s @@ -0,0 +1,14 @@ +; RUN: llvm-mc -triple=m68k -show-encoding %s | FileCheck %s + +; CHECK: trap #13 +; CHECK-SAME: encoding: [0x4e,0x4d] +trap #13 +; CHECK: bkpt #7 +; CHECK-SAME: encoding: [0x48,0x4f] +bkpt #7 +; CHECK: trapv +; CHECK-SAME: encoding: [0x4e,0x76] +trapv +; CHECK: illegal +; CHECK-SAME: encoding: [0x4a,0xfc] +illegal