Some SH4 floating point instructions have ambiguous encodings that depend on FPSCR variables. Exhaustively, these are: FMOV XDm,DRn (sz 1) FMOV FRm,FRn (sz 0) FMOV DRm,@(R0,Rn) (sz 1) FMOV.S FRm,@(R0,Rn) (sz 0) FCMP/EQ DRm,DRn (pr 1) FCMP/EQ FRm,FRn (pr 0) FMOV @Rm+,XDn (sz 1) FMOV.S @Rm+,FRn (sz 0) FMOV XDm,@(R0,Rn) (sz 1) FMOV.S FRm,@(R0,Rn) (sz 0) FMUL DRm,DRn (pr 1) FMUL FRm,FRn (pr 0) FMOV.S @Rm+,FRn (sz 0) FMOV @Rm+,DRn (sz 1) FLOAT FPUL,DRn (pr 1) FLOAT FPUL,FRn (pr 0) FNEG DRn (pr 1) FNEG FRn (pr 0) FTRC DRm,FPUL (pr 1) FTRC FRm,FPUL (pr 0) FMOV.S @(R0,Rm),FRn (sz 0) FMOV @(R0,Rm),DRn (sz 1) FMOV.S @Rm,FRn (sz 0) FMOV @Rm,DRn (sz 1) FMOV XDm,XDn (sz 1) FMOV FRm,FRn (sz 0) FABS FRn (pr 0) FABS DRn (pr 1) FMOV.S FRm,@Rn (sz 0) FMOV DRm,@Rn (sz 1) FSUB DRm,DRn (pr 1) FSUB FRm,FRn (pr 0) FDIV DRm,DRn (pr 1) FDIV FRm,FRn (pr 0) FCMP/GT DRm,DRn (pr 1) FCMP/GT FRm,FRn (pr 0) FMOV DRm,DRn (sz 1) FMOV FRm,FRn (sz 0) FMOV.S FRm,@-Rn (sz 0) FMOV DRm,@-Rn (sz 1) FADD DRm,DRn (pr 1) FADD FRm,FRn (pr 0) FMOV.S FRm,@Rn (sz 0) FMOV XDm,@Rn (sz 1) FMOV.S @(R0,Rm),FRn (sz 0) FMOV @(R0,Rm),XDn (sz 1) FMOV DRm,XDn (sz 1) FMOV FRm,FRn (sz 0) FMOV XDm,@-Rn (sz 1) FMOV.S FRm,@-Rn (sz 0) FSQRT DRn (pr 1) FSQRT FRn (pr 0) FMOV.S @Rm,FRn (sz 0) FMOV @Rm,XDn (sz 1) This commit automatically calculates which FPU instructions require FPSCR-discrimination, and automatically inserts the appropriate conditional logic in the instruction decoder.
1797 lines
57 KiB
C
1797 lines
57 KiB
C
#include <stdio.h>
|
|
|
|
#include "decode_print.h"
|
|
|
|
enum decode_status decode_and_print_instruction(struct architectural_state * state, struct memory_map * map, uint16_t code, char const ** instruction_buf, char * operand_buf, uint32_t size)
|
|
{
|
|
switch (code & 0b1111000000000000) {
|
|
case 0b0001000000000000: // MOV.L Rm,@(disp,Rn)
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t d = (code >> 0) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@(%d,R%d)", m, d, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0101000000000000: // MOV.L @(disp,Rm),Rn
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 4) - 1);
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(%d,R%d),R%d", d, m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0111000000000000: // ADD #imm,Rn
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "#%d,R%d", i, n);
|
|
*instruction_buf = "ADD";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1001000000000000: // MOV.W @(disp,PC),Rn
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(%d,PC),R%d", d, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1010000000000000: // BRA label
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 12) - 1);
|
|
snprintf(operand_buf, size, "%d", d);
|
|
*instruction_buf = "BRA";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1011000000000000: // BSR label
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 12) - 1);
|
|
snprintf(operand_buf, size, "%d", d);
|
|
*instruction_buf = "BSR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1101000000000000: // MOV.L @(disp,PC),Rn
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(%d,PC),R%d", d, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1110000000000000: // MOV #imm,Rn
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "#%d,R%d", i, n);
|
|
*instruction_buf = "MOV";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
switch (code & 0b1111000000001111) {
|
|
case 0b0000000000000100: // MOV.B Rm,@(R0,Rn)
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@(R0,R%d)", m, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000000101: // MOV.W Rm,@(R0,Rn)
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@(R0,R%d)", m, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000000110: // MOV.L Rm,@(R0,Rn)
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@(R0,R%d)", m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000000111: // MUL.L Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "MUL.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001100: // MOV.B @(R0,Rm),Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(R0,R%d),R%d", m, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001101: // MOV.W @(R0,Rm),Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(R0,R%d),R%d", m, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001110: // MOV.L @(R0,Rm),Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(R0,R%d),R%d", m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001111: // MAC.L @Rm+,@Rn+
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,@R%d+", m, n);
|
|
*instruction_buf = "MAC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000000: // MOV.B Rm,@Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@R%d", m, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000001: // MOV.W Rm,@Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@R%d", m, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000010: // MOV.L Rm,@Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@R%d", m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000100: // MOV.B Rm,@-Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@-R%d", m, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000101: // MOV.W Rm,@-Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@-R%d", m, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000110: // MOV.L Rm,@-Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,@-R%d", m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000000111: // DIV0S Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "DIV0S";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001000: // TST Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "TST";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001001: // AND Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "AND";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001010: // XOR Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "XOR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001011: // OR Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "OR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001100: // CMP/STR Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "CMP/STR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001101: // XTRCT Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "XTRCT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001110: // MULU.W Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "MULU.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0010000000001111: // MULS.W Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "MULS.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000000: // CMP/EQ Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "CMP/EQ";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000010: // CMP/HS Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "CMP/HS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000011: // CMP/GE Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "CMP/GE";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000100: // DIV1 Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "DIV1";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000101: // DMULU.L Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "DMULU.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000110: // CMP/HI Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "CMP/HI";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000000111: // CMP/GT Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "CMP/GT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001000: // SUB Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SUB";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001010: // SUBC Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SUBC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001011: // SUBV Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SUBV";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001100: // ADD Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "ADD";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001101: // DMULS.L Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "DMULS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001110: // ADDC Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "ADDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0011000000001111: // ADDV Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "ADDV";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001100: // SHAD Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SHAD";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001101: // SHLD Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SHLD";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001111: // MAC.W @Rm+,@Rn+
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,@R%d+", m, n);
|
|
*instruction_buf = "MAC.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000000: // MOV.B @Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d,R%d", m, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000001: // MOV.W @Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d,R%d", m, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000010: // MOV.L @Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d,R%d", m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000011: // MOV Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "MOV";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000100: // MOV.B @Rm+,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,R%d", m, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000101: // MOV.W @Rm+,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,R%d", m, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000110: // MOV.L @Rm+,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,R%d", m, n);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000000111: // NOT Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "NOT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001000: // SWAP.B Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SWAP.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001001: // SWAP.W Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "SWAP.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001010: // NEGC Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "NEGC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001011: // NEG Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "NEG";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001100: // EXTU.B Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "EXTU.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001101: // EXTU.W Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "EXTU.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001110: // EXTS.B Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "EXTS.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0110000000001111: // EXTS.W Rm,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d", m, n);
|
|
*instruction_buf = "EXTS.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111000000000000: // FADD FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FADD";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000001: // FSUB FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FSUB";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000010: // FMUL FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FMUL";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000011: // FDIV FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FDIV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000100: // FCMP/EQ FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FCMP/EQ";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000101: // FCMP/GT FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FCMP/GT";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000110: // FMOV.S @(R0,Rm),FRn
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(R0,R%d),FR%d", m, n);
|
|
*instruction_buf = "FMOV.S";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000111: // FMOV.S FRm,@(R0,Rn)
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,@(R0,R%d)", m, n);
|
|
*instruction_buf = "FMOV.S";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001000: // FMOV.S @Rm,FRn
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d,FR%d", m, n);
|
|
*instruction_buf = "FMOV.S";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001001: // FMOV.S @Rm+,FRn
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,FR%d", m, n);
|
|
*instruction_buf = "FMOV.S";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001010: // FMOV.S FRm,@Rn
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,@R%d", m, n);
|
|
*instruction_buf = "FMOV.S";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001011: // FMOV.S FRm,@-Rn
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,@-R%d", m, n);
|
|
*instruction_buf = "FMOV.S";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001100: // FMOV FRm,FRn
|
|
{
|
|
if (state->fpscr.bits.sz == 0) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FR%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001110: // FMAC FR0,FRm,FRn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR0,FR%d,FR%d", m, n);
|
|
*instruction_buf = "FMAC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
switch (code & 0b1111111100000000) {
|
|
case 0b1000000000000000: // MOV.B R0,@(disp,Rn)
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 4) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R0,@(%d,R%d)", d, n);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000000100000000: // MOV.W R0,@(disp,Rn)
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 4) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R0,@(%d,R%d)", d, n);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000010000000000: // MOV.B @(disp,Rm),R0
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 4) - 1);
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(%d,R%d),R0", d, m);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000010100000000: // MOV.W @(disp,Rm),R0
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 4) - 1);
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@(%d,R%d),R0", d, m);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000100000000000: // CMP/EQ #imm,R0
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,R0", i);
|
|
*instruction_buf = "CMP/EQ";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000100100000000: // BT label
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "%d", d);
|
|
*instruction_buf = "BT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000101100000000: // BF label
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "%d", d);
|
|
*instruction_buf = "BF";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000110100000000: // BT/S label
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "%d", d);
|
|
*instruction_buf = "BT/S";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1000111100000000: // BF/S label
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "%d", d);
|
|
*instruction_buf = "BF/S";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100000000000000: // MOV.B R0,@(disp,GBR)
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "R0,@(%d,GBR)", d);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100000100000000: // MOV.W R0,@(disp,GBR)
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "R0,@(%d,GBR)", d);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100001000000000: // MOV.L R0,@(disp,GBR)
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "R0,@(%d,GBR)", d);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100001100000000: // TRAPA #imm
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d", i);
|
|
*instruction_buf = "TRAPA";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100010000000000: // MOV.B @(disp,GBR),R0
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "@(%d,GBR),R0", d);
|
|
*instruction_buf = "MOV.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100010100000000: // MOV.W @(disp,GBR),R0
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "@(%d,GBR),R0", d);
|
|
*instruction_buf = "MOV.W";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100011000000000: // MOV.L @(disp,GBR),R0
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "@(%d,GBR),R0", d);
|
|
*instruction_buf = "MOV.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100011100000000: // MOVA @(disp,PC),R0
|
|
{
|
|
uint32_t d = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "@(%d,PC),R0", d);
|
|
*instruction_buf = "MOVA";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100100000000000: // TST #imm,R0
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,R0", i);
|
|
*instruction_buf = "TST";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100100100000000: // AND #imm,R0
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,R0", i);
|
|
*instruction_buf = "AND";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100101000000000: // XOR #imm,R0
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,R0", i);
|
|
*instruction_buf = "XOR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100101100000000: // OR #imm,R0
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,R0", i);
|
|
*instruction_buf = "OR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100110000000000: // TST.B #imm,@(R0,GBR)
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,@(R0,GBR)", i);
|
|
*instruction_buf = "TST.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100110100000000: // AND.B #imm,@(R0,GBR)
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,@(R0,GBR)", i);
|
|
*instruction_buf = "AND.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100111000000000: // XOR.B #imm,@(R0,GBR)
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,@(R0,GBR)", i);
|
|
*instruction_buf = "XOR.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1100111100000000: // OR.B #imm,@(R0,GBR)
|
|
{
|
|
uint32_t i = (code >> 0) & ((1 << 8) - 1);
|
|
snprintf(operand_buf, size, "#%d,@(R0,GBR)", i);
|
|
*instruction_buf = "OR.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
switch (code & 0b1111000011111111) {
|
|
case 0b0000000000000010: // STC SR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SR,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000000011: // BSRF Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "BSRF";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001010: // STS MACH,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "MACH,R%d", n);
|
|
*instruction_buf = "STS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000010010: // STC GBR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "GBR,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000011010: // STS MACL,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "MACL,R%d", n);
|
|
*instruction_buf = "STS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000100010: // STC VBR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "VBR,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000100011: // BRAF Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "BRAF";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000101001: // MOVT Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "MOVT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000101010: // STS PR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "PR,R%d", n);
|
|
*instruction_buf = "STS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000110010: // STC SSR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SSR,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000111010: // STC SGR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SGR,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000001000010: // STC SPC,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SPC,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000001011010: // STS FPUL,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FPUL,R%d", n);
|
|
*instruction_buf = "STS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000001101010: // STS FPSCR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FPSCR,R%d", n);
|
|
*instruction_buf = "STS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000011111010: // STC DBR,Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "DBR,R%d", n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000000: // SHLL Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLL";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000001: // SHLR Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000010: // STS.L MACH,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "MACH,@-R%d", n);
|
|
*instruction_buf = "STS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000011: // STC.L SR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SR,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000100: // ROTL Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "ROTL";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000101: // ROTR Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "ROTR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000110: // LDS.L @Rm+,MACH
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,MACH", m);
|
|
*instruction_buf = "LDS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000000111: // LDC.L @Rm+,SR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,SR", m);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001000: // SHLL2 Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLL2";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001001: // SHLR2 Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLR2";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001010: // LDS Rm,MACH
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,MACH", m);
|
|
*instruction_buf = "LDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001011: // JSR @Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d", n);
|
|
*instruction_buf = "JSR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000001110: // LDC Rm,SR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,SR", m);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010000: // DT Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "DT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010001: // CMP/PZ Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "CMP/PZ";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010010: // STS.L MACL,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "MACL,@-R%d", n);
|
|
*instruction_buf = "STS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010011: // STC.L GBR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "GBR,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010101: // CMP/PL Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "CMP/PL";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010110: // LDS.L @Rm+,MACL
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,MACL", m);
|
|
*instruction_buf = "LDS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000010111: // LDC.L @Rm+,GBR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,GBR", m);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000011000: // SHLL8 Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLL8";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000011001: // SHLR8 Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLR8";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000011010: // LDS Rm,MACL
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,MACL", m);
|
|
*instruction_buf = "LDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000011011: // TAS.B @Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d", n);
|
|
*instruction_buf = "TAS.B";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000011110: // LDC Rm,GBR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,GBR", m);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100000: // SHAL Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHAL";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100001: // SHAR Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHAR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100010: // STS.L PR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "PR,@-R%d", n);
|
|
*instruction_buf = "STS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100011: // STC.L VBR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "VBR,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100100: // ROTCL Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "ROTCL";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100101: // ROTCR Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "ROTCR";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100110: // LDS.L @Rm+,PR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,PR", m);
|
|
*instruction_buf = "LDS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000100111: // LDC.L @Rm+,VBR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,VBR", m);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000101000: // SHLL16 Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLL16";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000101001: // SHLR16 Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d", n);
|
|
*instruction_buf = "SHLR16";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000101010: // LDS Rm,PR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,PR", m);
|
|
*instruction_buf = "LDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000101011: // JMP @Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d", n);
|
|
*instruction_buf = "JMP";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000101110: // LDC Rm,VBR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,VBR", m);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000110010: // STC.L SGR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SGR,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000110011: // STC.L SSR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SSR,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000110111: // LDC.L @Rm+,SSR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,SSR", m);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000000111110: // LDC Rm,SSR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,SSR", m);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001000011: // STC.L SPC,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "SPC,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001000111: // LDC.L @Rm+,SPC
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,SPC", m);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001001110: // LDC Rm,SPC
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,SPC", m);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001010010: // STS.L FPUL,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FPUL,@-R%d", n);
|
|
*instruction_buf = "STS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001010110: // LDS.L @Rm+,FPUL
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,FPUL", m);
|
|
*instruction_buf = "LDS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001011010: // LDS Rm,FPUL
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,FPUL", m);
|
|
*instruction_buf = "LDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001100010: // STS.L FPSCR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FPSCR,@-R%d", n);
|
|
*instruction_buf = "STS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001100110: // LDS.L @Rm+,FPSCR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,FPSCR", m);
|
|
*instruction_buf = "LDS.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000001101010: // LDS Rm,FPSCR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,FPSCR", m);
|
|
*instruction_buf = "LDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000011110010: // STC.L DBR,@-Rn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "DBR,@-R%d", n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000011110110: // LDC.L @Rm+,DBR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,DBR", m);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000011111010: // LDC Rm,DBR
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d,DBR", m);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111000000001101: // FSTS FPUL,FRn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FPUL,FR%d", n);
|
|
*instruction_buf = "FSTS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111000000011101: // FLDS FRm,FPUL
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FPUL", m);
|
|
*instruction_buf = "FLDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111000000101101: // FLOAT FPUL,FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FPUL,FR%d", n);
|
|
*instruction_buf = "FLOAT";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000111101: // FTRC FRm,FPUL
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d,FPUL", m);
|
|
*instruction_buf = "FTRC";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000001001101: // FNEG FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d", n);
|
|
*instruction_buf = "FNEG";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000001011101: // FABS FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d", n);
|
|
*instruction_buf = "FABS";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000001101101: // FSQRT FRn
|
|
{
|
|
if (state->fpscr.bits.pr == 0) {
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d", n);
|
|
*instruction_buf = "FSQRT";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000010001101: // FLDI0 FRn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d", n);
|
|
*instruction_buf = "FLDI0";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111000010011101: // FLDI1 FRn
|
|
{
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "FR%d", n);
|
|
*instruction_buf = "FLDI1";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
switch (code & 0b1111111111111111) {
|
|
case 0b0000000000001000: // CLRT
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "CLRT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001001: // NOP
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "NOP";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000001011: // RTS
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "RTS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000011000: // SETT
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "SETT";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000011001: // DIV0U
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "DIV0U";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000011011: // SLEEP
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "SLEEP";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000101000: // CLRMAC
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "CLRMAC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000000101011: // RTE
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "RTE";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000001001000: // CLRS
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "CLRS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0000000001011000: // SETS
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "SETS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111001111111101: // FSCHG
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "FSCHG";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111101111111101: // FRCHG
|
|
{
|
|
operand_buf[0] = 0;
|
|
*instruction_buf = "FRCHG";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
switch (code & 0b1111000010001111) {
|
|
case 0b0000000010000010: // STC Rm_BANK,Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d_BANK,R%d", m, n);
|
|
*instruction_buf = "STC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000010000011: // STC.L Rm_BANK,@-Rn
|
|
{
|
|
uint32_t m = (code >> 4) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "R%d_BANK,@-R%d", m, n);
|
|
*instruction_buf = "STC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000010000111: // LDC.L @Rm+,Rn_BANK
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 4) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,R%d_BANK", m, n);
|
|
*instruction_buf = "LDC.L";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b0100000010001110: // LDC Rm,Rn_BANK
|
|
{
|
|
uint32_t m = (code >> 8) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 4) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "R%d,R%d_BANK", m, n);
|
|
*instruction_buf = "LDC";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
switch (code & 0b1111000100011111) {
|
|
case 0b1111000000000000: // FADD DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FADD";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000001: // FSUB DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FSUB";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000010: // FMUL DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FMUL";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000011: // FDIV DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FDIV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000100: // FCMP/EQ DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FCMP/EQ";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000000101: // FCMP/GT DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FCMP/GT";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001100: // FMOV DRm,DRn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,DR%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000011100: // FMOV XDm,DRn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "XD%d,DR%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000100001100: // FMOV DRm,XDn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,XD%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000100011100: // FMOV XDm,XDn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "XD%d,XD%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
}
|
|
switch (code & 0b1111000100001111) {
|
|
case 0b1111000000000110: // FMOV @(R0,Rm),DRn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@(R0,R%d),DR%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001000: // FMOV @Rm,DRn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@R%d,DR%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001001: // FMOV @Rm+,DRn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,DR%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000100000110: // FMOV @(R0,Rm),XDn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@(R0,R%d),XD%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000100001000: // FMOV @Rm,XDn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@R%d,XD%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000100001001: // FMOV @Rm+,XDn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 4) & ((1 << 4) - 1);
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "@R%d+,XD%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
}
|
|
switch (code & 0b1111000000011111) {
|
|
case 0b1111000000000111: // FMOV DRm,@(R0,Rn)
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "DR%d,@(R0,R%d)", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001010: // FMOV DRm,@Rn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "DR%d,@R%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000001011: // FMOV DRm,@-Rn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "DR%d,@-R%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000010111: // FMOV XDm,@(R0,Rn)
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "XD%d,@(R0,R%d)", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000011010: // FMOV XDm,@Rn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "XD%d,@R%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000011011: // FMOV XDm,@-Rn
|
|
{
|
|
if (state->fpscr.bits.sz == 1) {
|
|
uint32_t m = (code >> 5) & ((1 << 3) - 1);
|
|
uint32_t n = (code >> 8) & ((1 << 4) - 1);
|
|
snprintf(operand_buf, size, "XD%d,@-R%d", m, n);
|
|
*instruction_buf = "FMOV";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
}
|
|
switch (code & 0b1111000111111111) {
|
|
case 0b1111000000101101: // FLOAT FPUL,DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "FPUL,DR%d", n);
|
|
*instruction_buf = "FLOAT";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000000111101: // FTRC DRm,FPUL
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t m = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,FPUL", m);
|
|
*instruction_buf = "FTRC";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000001001101: // FNEG DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d", n);
|
|
*instruction_buf = "FNEG";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000001011101: // FABS DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d", n);
|
|
*instruction_buf = "FABS";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000001101101: // FSQRT DRn
|
|
{
|
|
if (state->fpscr.bits.pr == 1) {
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d", n);
|
|
*instruction_buf = "FSQRT";
|
|
return DECODE__DEFINED;
|
|
} else break;
|
|
}
|
|
case 0b1111000010101101: // FCNVSD FPUL,DRn
|
|
{
|
|
uint32_t n = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "FPUL,DR%d", n);
|
|
*instruction_buf = "FCNVSD";
|
|
return DECODE__DEFINED;
|
|
}
|
|
case 0b1111000010111101: // FCNVDS DRm,FPUL
|
|
{
|
|
uint32_t m = (code >> 9) & ((1 << 3) - 1);
|
|
snprintf(operand_buf, size, "DR%d,FPUL", m);
|
|
*instruction_buf = "FCNVDS";
|
|
return DECODE__DEFINED;
|
|
}
|
|
}
|
|
return DECODE__UNDEFINED;
|
|
}
|