/*************************************************************************** dsp56dsm.c Disassembler for the portable Motorola/Freescale dsp56k emulator. Written by Andrew Gardner ***************************************************************************/ /* This disassembler has been 75% tested. There may remain some bugs, but it disassembles Polygonet Commanders' memtest code 100% accurate (to my knowledge). */ #include "dsp56k.h" /*******************/ /* Dasm prototypes */ /*******************/ static size_t dsp56k_dasm_addsub_2 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_mac_1 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_macr_1 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_move_1 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_mpy_1 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_mpyr_1 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_tfr_2 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_mpy_2 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_mac_2 (const UINT16 op_byte, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_clr (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_add (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_move (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_tfr (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_rnd (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_tst (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_inc (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_inc24 (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_or (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_asr (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_asl (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_lsr (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_lsl (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_eor (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_subl (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_sub (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_clr24 (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_sbc (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_cmp (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_neg (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_not (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_dec (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_dec24 (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_and (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_abs (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_ror (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_rol (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_cmpm (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_mpy (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_mpyr (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_mac (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_macr (const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register); static size_t dsp56k_dasm_adc (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_andi (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_asl4 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_asr4 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_asr16 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_bfop (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_bcc (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc); static size_t dsp56k_dasm_bcc_1 (const UINT16 op, char* opcode_str, char* arg_str, const offs_t pc); static size_t dsp56k_dasm_bcc_2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_bra (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc); static size_t dsp56k_dasm_bra_1 (const UINT16 op, char* opcode_str, char* arg_str, const offs_t pc); static size_t dsp56k_dasm_bra_2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_brkcc (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_bscc (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc); static size_t dsp56k_dasm_bscc_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_bsr (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc); static size_t dsp56k_dasm_bsr_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_chkaau (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_debug (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_debugcc (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_div (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_dmac (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_do (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_do_1 (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_do_2 (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_doforever (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_enddo (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_ext (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_illegal (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_imac (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_impy (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jcc (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jcc_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jmp (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jmp_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jscc (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jscc_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jsr (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jsr_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_jsr_2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_lea (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_lea_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_macsuuu (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_move_2 (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movec (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movec_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movec_2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movec_3 (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movec_4 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movec_5 (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movei (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movem (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movem_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movem_2 (const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movep (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_movep_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_moves (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_mpysuuu (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_negc (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_nop (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_norm (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_ori (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_rep (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_rep_1 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_rep_2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_repcc (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_reset (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_rti (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_rts (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_stop (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_swap (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_swi (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_tcc (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_tfr2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_tfr3 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_tst2 (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_wait (const UINT16 op, char* opcode_str, char* arg_str); static size_t dsp56k_dasm_zero (const UINT16 op, char* opcode_str, char* arg_str); /***************************/ /* Table decoder functions */ /***************************/ static int decode_BBB_table (UINT16 BBB); static void decode_cccc_table (UINT16 cccc, char *mnemonic); static void decode_DDDDD_table(UINT16 DDDDD, char *SD); static void decode_DD_table (UINT16 DD, char *SD); static void decode_DDF_table (UINT16 DD, UINT16 F, char *S, char *D); static void decode_EE_table (UINT16 EE, char *D); static void decode_F_table (UINT16 F, char *SD); static void decode_h0hF_table (UINT16 h0h, UINT16 F, char *S, char *D); static void decode_HH_table (UINT16 HH, char *SD); static void decode_HHH_table (UINT16 HHH, char *SD); static void decode_IIII_table (UINT16 IIII, char *S, char *D); static void decode_JJJF_table (UINT16 JJJ, UINT16 F, char *S, char *D); static void decode_JJF_table (UINT16 JJ, UINT16 F, char *S, char *D); static void decode_JF_table (UINT16 J, UINT16 F, char *S, char *D); static void decode_k_table (UINT16 k, char *Dnot); static void decode_kSign_table(UINT16 k, char *plusMinus); static void decode_KKK_table (UINT16 KKK, char *D1, char *D2); static int decode_NN_table (UINT16 NN); static int decode_TT_table (UINT16 TT); static void decode_QQF_table (UINT16 QQ, UINT16 F, char *S1, char *S2, char *D); static void decode_QQF_special_table(UINT16 QQ, UINT16 F, char *S1, char *S2, char *D); static void decode_QQQF_table (UINT16 QQQ, UINT16 F, char *S1, char *S2, char *D); static int decode_RR_table (UINT16 RR); static int decode_rr_table (UINT16 rr); static void decode_s_table (UINT16 s, char *arithmetic); static void decode_ss_table (UINT16 ss, char *arithmetic); static void decode_uuuuF_table(UINT16 uuuu, UINT16 F, char *arg, char *S, char *D); static void decode_Z_table (UINT16 Z, char *ea); static void assemble_ea_from_m_table (UINT16 m, int n, char *ea); static void assemble_eas_from_m_table(UINT16 mm, int n1, int n2, char *ea1, char *ea2); static void assemble_ea_from_MM_table(UINT16 MM, int n, char *ea); static void assemble_ea_from_t_table (UINT16 t, UINT16 val, char *ea); static void assemble_ea_from_q_table (UINT16 q, int n, char *ea); static void assemble_ea_from_z_table (UINT16 z, int n, char *ea); static void assemble_D_from_P_table(UINT16 P, UINT16 ppppp, char *D); static void assemble_arguments_from_W_table(UINT16 W, char *args, char ma, char *SD, char *ea); static void assemble_reg_from_W_table(UINT16 W, char *args, char ma, char *SD, INT8 xx); static void assemble_address_from_IO_short_address(UINT16 pp, char *ea); static INT8 get_6_bit_signed_value(UINT16 bits); /**********************************/ /* Parallel memory move functions */ /**********************************/ static void decode_x_memory_data_move(const UINT16 op, char* parallel_move_str); static void decode_x_memory_data_move2(const UINT16 op, char* parallel_move_str, char* d_register); static void decode_dual_x_memory_data_read(const UINT16 op, char* parallel_move_str, char* parallel_move_str2); static void decode_register_to_register_data_move(const UINT16 op, char* parallel_move_str, char* d_register); static void decode_x_memory_data_write_and_register_data_move(const UINT16 op, char* parallel_move_str, char* parallel_move_str2); static void decode_address_register_update(const UINT16 op, char* parallel_move_str); static void decode_x_memory_data_move_with_short_displacement(const UINT16 op, const UINT16 op2, char* parallel_move_str); /********************/ /* Helper functions */ /********************/ #define BITS(CUR,MASK) (dsp56k_op_mask(CUR,MASK)) static UINT16 dsp56k_op_mask(UINT16 op, UINT16 mask); static void pad_string(const int dest_length, char* string); enum bbbType { BBB_UPPER, BBB_MIDDLE, BBB_LOWER }; /*****************************/ /* Main disassembly function */ /*****************************/ CPU_DISASSEMBLE( dsp56k ) { /* ORDER: Handle parallel types in the ALU */ /* Handle the rest */ unsigned size = 0; char arg_str[128] = ""; char opcode_str[128] = ""; char parallel_move_str[128] = ""; char parallel_move_str2[128] = ""; const UINT16 op = oprom[0] | (oprom[1] << 8); const UINT16 op2 = oprom[2] | (oprom[3] << 8); /* Dual X Memory Data Read : 011m mKKK -rr- ---- : A-142*/ if ((op & 0xe000) == 0x6000) { /* Quote: (MOVE, MAC(R), MPY(R), ADD, SUB, TFR) */ UINT16 op_byte = op & 0x00ff; /* ADD : 011m mKKK 0rru Fuuu : A-22 */ /* SUB : 011m mKKK 0rru Fuuu : A-202 */ if ((op & 0xe080) == 0x6000) { size = dsp56k_dasm_addsub_2(op_byte, opcode_str, arg_str); } /* MAC : 011m mKKK 1xx0 F1QQ : A-122 */ else if ((op & 0xe094) == 0x6084) { size = dsp56k_dasm_mac_1(op_byte, opcode_str, arg_str); } /* MACR: 011m mKKK 1--1 F1QQ : A-124 */ else if ((op & 0xe094) == 0x6094) { size = dsp56k_dasm_macr_1(op_byte, opcode_str, arg_str); } /* MOVE : 011m mKKK 0rr1 0000 : A-128 */ else if ((op & 0xe09f) == 0x6010) { size = dsp56k_dasm_move_1(op_byte, opcode_str, arg_str); } /* MPY : 011m mKKK 1xx0 F0QQ : A-160 */ else if ((op & 0xe094) == 0x6080) { size = dsp56k_dasm_mpy_1(op_byte, opcode_str, arg_str); } /* MPYR : 011m mKKK 1--1 F0QQ : A-162 */ else if ((op & 0xe094) == 0x6090) { size = dsp56k_dasm_mpyr_1(op_byte, opcode_str, arg_str); } /* TFR : 011m mKKK 0rr1 F0DD : A-212 */ else if ((op & 0xe094) == 0x6010) { size = dsp56k_dasm_tfr_2(op_byte, opcode_str, arg_str); } /* Now evaluate the parallel data move */ decode_dual_x_memory_data_read(op, parallel_move_str, parallel_move_str2); } /* X Memory Data Write and Register Data Move : 0001 011k RRDD ---- : A-140 */ else if ((op & 0xfe00) == 0x1600) { /* Quote: (MPY or MAC) */ UINT16 op_byte = op & 0x00ff; /* MPY : 0001 0110 RRDD FQQQ : A-160 */ if ((op & 0xff00) == 0x1600) { size = dsp56k_dasm_mpy_2(op_byte, opcode_str, arg_str); } /* MAC : 0001 0111 RRDD FQQQ : A-122 */ else if ((op & 0xff00) == 0x1700) { size = dsp56k_dasm_mac_2(op_byte, opcode_str, arg_str); } /* Now evaluate the parallel data move */ decode_x_memory_data_write_and_register_data_move(op, parallel_move_str, parallel_move_str2); } /* Handle Other parallel types */ else { /***************************************/ /* 32 General parallel move operations */ /***************************************/ enum pType { kNoParallelDataMove, kRegisterToRegister, kAddressRegister, kXMemoryDataMove, kXMemoryDataMove2, kXMemoryDataMoveWithDisp }; UINT16 op_byte = 0x0000; char d_register[32] = ""; int parallelType = -1; /* Note: it's important that NPDM comes before RtRDM here */ /* No Parallel Data Move : 0100 1010 ---- ---- : A-131 */ if ((op & 0xff00) == 0x4a00) { op_byte = op & 0x00ff; parallelType = kNoParallelDataMove; } /* Register to Register Data Move : 0100 IIII ---- ---- : A-133 */ else if ((op & 0xf000) == 0x4000) { op_byte = op & 0x00ff; parallelType = kRegisterToRegister; } /* Address Register Update : 0011 0zRR ---- ---- : A-135 */ else if ((op & 0xf800) == 0x3000) { op_byte = op & 0x00ff; parallelType = kAddressRegister; } /* X Memory Data Move : 1mRR HHHW ---- ---- : A-137 */ else if ((op & 0x8000) == 0x8000) { op_byte = op & 0x00ff; parallelType = kXMemoryDataMove; } /* X Memory Data Move : 0101 HHHW ---- ---- : A-137 */ else if ((op & 0xf000) == 0x5000) { op_byte = op & 0x00ff; parallelType = kXMemoryDataMove2; } /* X Memory Data Move with short displacement : 0000 0101 BBBB BBBB ---- HHHW ---- ---- : A-139 */ else if ((op & 0xff00) == 0x0500) { /* Now check it against all the other potential collisions */ /* This is necessary because "don't care bits" get in the way. */ /* MOVE(M) : 0000 0101 BBBB BBBB 0000 001W --0- -HHH : A-152 MOVE(C) : 0000 0101 BBBB BBBB 0011 1WDD DDD0 ---- : A-144 MOVE : 0000 0101 BBBB BBBB ---- HHHW 0001 0001 : A-128 */ if (((op2 & 0xfe20) != 0x0200) && ((op2 & 0xf810) != 0x3800) && ((op2 & 0x00ff) != 0x0011)) { op_byte = op2 & 0x00ff; parallelType = kXMemoryDataMoveWithDisp; } } if (parallelType != -1) { /* Note: There is much overlap between opcodes down here */ /* To this end, certain ops must come before others in the list */ /* CLR : .... .... 0000 F001 : A-60 */ if ((op_byte & 0x00f7) == 0x0001) { size = dsp56k_dasm_clr(op_byte, opcode_str, arg_str, d_register); } /* ADD : .... .... 0000 FJJJ : A-22 */ else if ((op_byte & 0x00f0) == 0x0000) { size = dsp56k_dasm_add(op_byte, opcode_str, arg_str, d_register); } /* MOVE : .... .... 0001 0001 : A-128 */ else if ((op_byte & 0x00ff) == 0x0011) { size = dsp56k_dasm_move(op_byte, opcode_str, arg_str, d_register); } /* TFR : .... .... 0001 FJJJ : A-212 */ else if ((op_byte & 0x00f0) == 0x0010) { size = dsp56k_dasm_tfr(op_byte, opcode_str, arg_str, d_register); } /* RND : .... .... 0010 F000 : A-188 */ else if ((op_byte & 0x00f7) == 0x0020) { size = dsp56k_dasm_rnd(op_byte, opcode_str, arg_str, d_register); } /* TST : .... .... 0010 F001 : A-218 */ else if ((op_byte & 0x00f7) == 0x0021) { size = dsp56k_dasm_tst(op_byte, opcode_str, arg_str, d_register); } /* INC : .... .... 0010 F010 : A-104 */ else if ((op_byte & 0x00f7) == 0x0022) { size = dsp56k_dasm_inc(op_byte, opcode_str, arg_str, d_register); } /* INC24 : .... .... 0010 F011 : A-106 */ else if ((op_byte & 0x00f7) == 0x0023) { size = dsp56k_dasm_inc24(op_byte, opcode_str, arg_str, d_register); } /* OR : .... .... 0010 F1JJ : A-176 */ else if ((op_byte & 0x00f4) == 0x0024) { size = dsp56k_dasm_or(op_byte, opcode_str, arg_str, d_register); } /* ASR : .... .... 0011 F000 : A-32 */ else if ((op_byte & 0x00f7) == 0x0030) { size = dsp56k_dasm_asr(op_byte, opcode_str, arg_str, d_register); } /* ASL : .... .... 0011 F001 : A-28 */ else if ((op_byte & 0x00f7) == 0x0031) { size = dsp56k_dasm_asl(op_byte, opcode_str, arg_str, d_register); } /* LSR : .... .... 0011 F010 : A-120 */ else if ((op_byte & 0x00f7) == 0x0032) { size = dsp56k_dasm_lsr(op_byte, opcode_str, arg_str, d_register); } /* LSL : .... .... 0011 F011 : A-118 */ else if ((op_byte & 0x00f7) == 0x0033) { size = dsp56k_dasm_lsl(op_byte, opcode_str, arg_str, d_register); } /* EOR : .... .... 0011 F1JJ : A-94 */ else if ((op_byte & 0x00f4) == 0x0034) { size = dsp56k_dasm_eor(op_byte, opcode_str, arg_str, d_register); } /* SUBL : .... .... 0100 F001 : A-204 */ else if ((op_byte & 0x00f7) == 0x0041) { size = dsp56k_dasm_subl(op_byte, opcode_str, arg_str, d_register); } /* SUB : .... .... 0100 FJJJ : A-202 */ else if ((op_byte & 0x00f0) == 0x0040) { size = dsp56k_dasm_sub(op_byte, opcode_str, arg_str, d_register); } /* CLR24 : .... .... 0101 F001 : A-62 */ else if ((op_byte & 0x00f7) == 0x0051) { size = dsp56k_dasm_clr24(op_byte, opcode_str, arg_str, d_register); } /* SBC : .... .... 0101 F01J : A-198 */ else if ((op_byte & 0x00f6) == 0x0052) { size = dsp56k_dasm_sbc(op_byte, opcode_str, arg_str, d_register); } /* CMP : .... .... 0101 FJJJ : A-64 */ else if ((op_byte & 0x00f0) == 0x0050) { size = dsp56k_dasm_cmp(op_byte, opcode_str, arg_str, d_register); } /* NEG : .... .... 0110 F000 : A-166 */ else if ((op_byte & 0x00f7) == 0x0060) { size = dsp56k_dasm_neg(op_byte, opcode_str, arg_str, d_register); } /* NOT : .... .... 0110 F001 : A-174 */ else if ((op_byte & 0x00f7) == 0x0061) { size = dsp56k_dasm_not(op_byte, opcode_str, arg_str, d_register); } /* DEC : .... .... 0110 F010 : A-72 */ else if ((op_byte & 0x00f7) == 0x0062) { size = dsp56k_dasm_dec(op_byte, opcode_str, arg_str, d_register); } /* DEC24 : .... .... 0110 F011 : A-74 */ else if ((op_byte & 0x00f7) == 0x0063) { size = dsp56k_dasm_dec24(op_byte, opcode_str, arg_str, d_register); } /* AND : .... .... 0110 F1JJ : A-24 */ else if ((op_byte & 0x00f4) == 0x0064) { size = dsp56k_dasm_and(op_byte, opcode_str, arg_str, d_register); } /* ABS : .... .... 0111 F001 : A-18 */ if ((op_byte & 0x00f7) == 0x0071) { size = dsp56k_dasm_abs(op_byte, opcode_str, arg_str, d_register); } /* ROR : .... .... 0111 F010 : A-192 */ else if ((op_byte & 0x00f7) == 0x0072) { size = dsp56k_dasm_ror(op_byte, opcode_str, arg_str, d_register); } /* ROL : .... .... 0111 F011 : A-190 */ else if ((op_byte & 0x00f7) == 0x0073) { size = dsp56k_dasm_rol(op_byte, opcode_str, arg_str, d_register); } /* CMPM : .... .... 0111 FJJJ : A-66 */ else if ((op_byte & 0x00f0) == 0x0070) { size = dsp56k_dasm_cmpm(op_byte, opcode_str, arg_str, d_register); } /* MPY : .... .... 1k00 FQQQ : A-160 -- CONFIRMED TYPO IN DOCS (HHHH vs HHHW) */ else if ((op_byte & 0x00b0) == 0x0080) { size = dsp56k_dasm_mpy(op_byte, opcode_str, arg_str, d_register); } /* MPYR : .... .... 1k01 FQQQ : A-162 */ else if ((op_byte & 0x00b0) == 0x0090) { size = dsp56k_dasm_mpyr(op_byte, opcode_str, arg_str, d_register); } /* MAC : .... .... 1k10 FQQQ : A-122 */ else if ((op_byte & 0x00b0) == 0x00a0) { size = dsp56k_dasm_mac(op_byte, opcode_str, arg_str, d_register); } /* MACR : .... .... 1k11 FQQQ : A-124 -- DRAMA - rr vs xx (805) */ else if ((op_byte & 0x00b0) == 0x00b0) { size = dsp56k_dasm_macr(op_byte, opcode_str, arg_str, d_register); } /* Now evaluate the parallel data move */ switch (parallelType) { case kNoParallelDataMove: /* DO NOTHING */ size = 1; break; case kRegisterToRegister: decode_register_to_register_data_move(op, parallel_move_str, d_register); size = 1; break; case kAddressRegister: decode_address_register_update(op, parallel_move_str); size = 1; break; case kXMemoryDataMove: decode_x_memory_data_move(op, parallel_move_str); size = 1; break; case kXMemoryDataMove2: decode_x_memory_data_move2(op, parallel_move_str, d_register); size = 1; break; case kXMemoryDataMoveWithDisp: decode_x_memory_data_move_with_short_displacement(op, op2, parallel_move_str); size = 2; break; } } } /* Assemble and return parallel move operation */ if (size > 0) { char space[32] = ""; pad_string(11, opcode_str); if (strlen(parallel_move_str) != 0) pad_string(15, arg_str); if (strlen(parallel_move_str2) != 0) sprintf(space, " "); sprintf(buffer, "%s%s%s%s%s", opcode_str, arg_str, parallel_move_str, space, parallel_move_str2); return (size | DASMFLAG_SUPPORTED); } /******************************/ /* Remaining non-parallel ops */ /******************************/ /* ADC : 0001 0101 0000 F01J : A-20 */ if ((op & 0xfff6) == 0x1502) { size = dsp56k_dasm_adc(op, opcode_str, arg_str); } /* ANDI : 0001 1EE0 iiii iiii : A-26 */ /* (MoveP sneaks in here if you don't check 0x0600) */ else if (((op & 0xf900) == 0x1800) & ((op & 0x0600) != 0x0000)) { size = dsp56k_dasm_andi(op, opcode_str, arg_str); } /* ASL4 : 0001 0101 0011 F001 : A-30 */ else if ((op & 0xfff7) == 0x1531) { size = dsp56k_dasm_asl4(op, opcode_str, arg_str); } /* ASR4 : 0001 0101 0011 F000 : A-34 */ else if ((op & 0xfff7) == 0x1530) { size = dsp56k_dasm_asr4(op, opcode_str, arg_str); } /* ASR16 : 0001 0101 0111 F000 : A-36 */ else if ((op & 0xfff7) == 0x1570) { size = dsp56k_dasm_asr16(op, opcode_str, arg_str); } /* BFCHG : 0001 0100 11Pp pppp BBB1 0010 iiii iiii : A-38 */ else if (((op & 0xffc0) == 0x14c0) && ((op2 & 0x1f00) == 0x1200)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFCHG : 0001 0100 101- --RR BBB1 0010 iiii iiii : A-38 */ else if (((op & 0xffe0) == 0x14a0) && ((op2 & 0x1f00) == 0x1200)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFCHG : 0001 0100 100D DDDD BBB1 0010 iiii iiii : A-38 */ else if (((op & 0xffe0) == 0x1480) && ((op2 & 0x1f00) == 0x1200)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFCLR : 0001 0100 11Pp pppp BBB0 0100 iiii iiii : A-40 */ else if (((op & 0xffc0) == 0x14c0) && ((op2 & 0x1f00) == 0x0400)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFCLR : 0001 0100 101- --RR BBB0 0100 iiii iiii : A-40 */ else if (((op & 0xffe0) == 0x14a0) && ((op2 & 0x1f00) == 0x0400)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFCLR : 0001 0100 100D DDDD BBB0 0100 iiii iiii : A-40 */ else if (((op & 0xffe0) == 0x1480) && ((op2 & 0x1f00) == 0x0400)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFSET : 0001 0100 11Pp pppp BBB1 1000 iiii iiii : A-42 */ else if (((op & 0xffc0) == 0x14c0) && ((op2 & 0x1f00) == 0x1800)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFSET : 0001 0100 101- --RR BBB1 1000 iiii iiii : A-42 */ else if (((op & 0xffe0) == 0x14a0) && ((op2 & 0x1f00) == 0x1800)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFSET : 0001 0100 100D DDDD BBB1 1000 iiii iiii : A-42 */ else if (((op & 0xffe0) == 0x1480) && ((op2 & 0x1f00) == 0x1800)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFTSTH : 0001 0100 01Pp pppp BBB1 0000 iiii iiii : A-44 */ else if (((op & 0xffc0) == 0x1440) && ((op2 & 0x1f00) == 0x1000)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFTSTH : 0001 0100 001- --RR BBB1 0000 iiii iiii : A-44 */ else if (((op & 0xffe0) == 0x1420) && ((op2 & 0x1f00) == 0x1000)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFTSTH : 0001 0100 000D DDDD BBB1 0000 iiii iiii : A-44 */ else if (((op & 0xffe0) == 0x1400) && ((op2 & 0x1f00) == 0x1000)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFTSTL : 0001 0100 01Pp pppp BBB0 0000 iiii iiii : A-46 */ else if (((op & 0xffc0) == 0x1440) && ((op2 & 0x1f00) == 0x0000)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFTSTL : 0001 0100 001- --RR BBB0 0000 iiii iiii : A-46 */ else if (((op & 0xffe0) == 0x1420) && ((op2 & 0x1f00) == 0x0000)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* BFTSTL : 0001 0100 000D DDDD BBB0 0000 iiii iiii : A-46 */ else if (((op & 0xffe0) == 0x1400) && ((op2 & 0x1f00) == 0x0000)) { size = dsp56k_dasm_bfop(op, op2, opcode_str, arg_str); } /* Bcc : 0000 0111 --11 cccc xxxx xxxx xxxx xxxx : A-48 */ else if (((op & 0xff30) == 0x0730) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_bcc(op, op2, opcode_str, arg_str, pc); } /* Bcc : 0010 11cc ccee eeee : A-48 */ else if ((op & 0xfc00) == 0x2c00) { size = dsp56k_dasm_bcc_1(op, opcode_str, arg_str, pc); } /* Bcc : 0000 0111 RR10 cccc : A-48 */ else if ((op & 0xff30) == 0x0720) { size = dsp56k_dasm_bcc_2(op, opcode_str, arg_str); } /* BRA : 0000 0001 0011 11-- xxxx xxxx xxxx xxxx : A-50 */ else if (((op & 0xfffc) == 0x013c) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_bra(op, op2, opcode_str, arg_str, pc); } /* BRA : 0000 1011 aaaa aaaa : A-50 */ else if ((op & 0xff00) == 0x0b00) { size = dsp56k_dasm_bra_1(op, opcode_str, arg_str, pc); } /* BRA : 0000 0001 0010 11RR : A-50 */ else if ((op & 0xfffc) == 0x012c) { size = dsp56k_dasm_bra_2(op, opcode_str, arg_str); } /* BRKc : 0000 0001 0001 cccc : A-52 */ else if ((op & 0xfff0) == 0x0110) { size = dsp56k_dasm_brkcc(op, opcode_str, arg_str); } /* BScc : 0000 0111 --01 cccc xxxx xxxx xxxx xxxx : A-54 */ else if (((op & 0xff30) == 0x0710) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_bscc(op, op2, opcode_str, arg_str, pc); } /* BScc: 0000 0111 RR00 cccc : A-54 */ else if ((op & 0xff30) == 0x0700) { size = dsp56k_dasm_bscc_1(op, opcode_str, arg_str); } /* BSR : 0000 0001 0011 10-- xxxx xxxx xxxx xxxx : A-56 */ else if (((op & 0xfffc) == 0x0138) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_bsr(op, op2, opcode_str, arg_str, pc); } /* BSR : 0000 0001 0010 10RR : A-56 */ else if ((op & 0xfffc) == 0x0128) { size = dsp56k_dasm_bsr_1(op, opcode_str, arg_str); } /* CHKAAU : 0000 0000 0000 0100 : A-58 */ else if ((op & 0xffff) == 0x0004) { size = dsp56k_dasm_chkaau(op, opcode_str, arg_str); } /* DEBUG : 0000 0000 0000 0001 : A-68 */ else if ((op & 0xffff) == 0x0001) { size = dsp56k_dasm_debug(op, opcode_str, arg_str); } /* DEBUGcc : 0000 0000 0101 cccc : A-70 */ else if ((op & 0xfff0) == 0x0050) { size = dsp56k_dasm_debugcc(op, opcode_str, arg_str); } /* DIV : 0001 0101 0--0 F1DD : A-76 */ /* WARNING : DOCS SAY THERE IS A PARALLEL MOVE HERE !!! */ else if ((op & 0xff94) == 0x1504) { size = dsp56k_dasm_div(op, opcode_str, arg_str); } /* DMAC : 0001 0101 10s1 FsQQ : A-80 */ else if ((op & 0xffd0) == 0x1590) { size = dsp56k_dasm_dmac(op, opcode_str, arg_str); } /* DO : 0000 0000 110- --RR xxxx xxxx xxxx xxxx : A-82 */ else if (((op & 0xffe0) == 0x00c0) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_do(op, op2, opcode_str, arg_str); } /* DO : 0000 1110 iiii iiii xxxx xxxx xxxx xxxx : A-82 */ else if (((op & 0xff00) == 0x0e00) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_do_1(op, op2, opcode_str, arg_str); } /* DO : 0000 0100 000D DDDD xxxx xxxx xxxx xxxx : A-82 */ else if (((op & 0xffe0) == 0x0400) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_do_2(op, op2, opcode_str, arg_str); } /* DO FOREVER : 0000 0000 0000 0010 xxxx xxxx xxxx xxxx : A-88 */ else if (((op & 0xffff) == 0x0002) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_doforever(op, op2, opcode_str, arg_str); } /* ENDDO : 0000 0000 0000 1001 : A-92 */ else if ((op & 0xffff) == 0x0009) { size = dsp56k_dasm_enddo(op, opcode_str, arg_str); } /* EXT : 0001 0101 0101 F010 : A-96 */ else if ((op & 0xfff7) == 0x1552) { size = dsp56k_dasm_ext(op, opcode_str, arg_str); } /* ILLEGAL : 0000 0000 0000 1111 : A-98 */ else if ((op & 0xffff) == 0x000f) { size = dsp56k_dasm_illegal(op, opcode_str, arg_str); } /* IMAC : 0001 0101 1010 FQQQ : A-100 */ else if ((op & 0xfff0) == 0x15a0) { size = dsp56k_dasm_imac(op, opcode_str, arg_str); } /* IMPY : 0001 0101 1000 FQQQ : A-102 */ else if ((op & 0xfff0) == 0x1580) { size = dsp56k_dasm_impy(op, opcode_str, arg_str); } /* Jcc : 0000 0110 --11 cccc xxxx xxxx xxxx xxxx : A-108 */ else if (((op & 0xff30) == 0x0630) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_jcc(op, op2, opcode_str, arg_str); } /* Jcc : 0000 0110 RR10 cccc : A-108 */ else if ((op & 0xff30) == 0x0620 ) { size = dsp56k_dasm_jcc_1(op, opcode_str, arg_str); } /* JMP : 0000 0001 0011 01-- xxxx xxxx xxxx xxxx : A-110 */ else if (((op & 0xfffc) == 0x0134) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_jmp(op, op2, opcode_str, arg_str); } /* JMP : 0000 0001 0010 01RR : A-110 */ else if ((op & 0xfffc) == 0x0124) { size = dsp56k_dasm_jmp_1(op, opcode_str, arg_str); } /* JScc : 0000 0110 --01 cccc xxxx xxxx xxxx xxxx : A-112 */ else if (((op & 0xff30) == 0x0610) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_jscc(op, op2, opcode_str, arg_str); } /* JScc : 0000 0110 RR00 cccc : A-112 */ else if ((op & 0xff30) == 0x0600) { size = dsp56k_dasm_jscc_1(op, opcode_str, arg_str); } /* JSR : 0000 0001 0011 00-- xxxx xxxx xxxx xxxx : A-114 */ else if (((op & 0xfffc) == 0x0130) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_jsr(op, op2, opcode_str, arg_str); } /* JSR : 0000 1010 AAAA AAAA : A-114 */ else if ((op & 0xff00) == 0x0a00) { size = dsp56k_dasm_jsr_1(op, opcode_str, arg_str); } /* JSR : 0000 0001 0010 00RR : A-114 */ else if ((op & 0xfffc) == 0x0120) { size = dsp56k_dasm_jsr_2(op, opcode_str, arg_str); } /* LEA : 0000 0001 11TT MMRR : A-116 */ else if ((op & 0xffc0) == 0x01c0) { size = dsp56k_dasm_lea(op, opcode_str, arg_str); } /* LEA : 0000 0001 10NN MMRR : A-116 */ else if ((op & 0xffc0) == 0x0180) { size = dsp56k_dasm_lea_1(op, opcode_str, arg_str); } /* MAC(su,uu) : 0001 0101 1110 FsQQ : A-126 */ else if ((op & 0xfff0) == 0x15e0) { size = dsp56k_dasm_macsuuu(op, opcode_str, arg_str); } /* MOVE : 0000 0101 BBBB BBBB ---- HHHW 0001 0001 : A-128 */ else if (((op & 0xff00) == 0x0500) && ((op2 & 0x00ff) == 0x0011)) { size = dsp56k_dasm_move_2(op, op2, opcode_str, arg_str); } /* MOVE(C) : 0011 1WDD DDD0 MMRR : A-144 */ else if ((op & 0xf810) == 0x3800) { size = dsp56k_dasm_movec(op, opcode_str, arg_str); } /* MOVE(C) : 0011 1WDD DDD1 q0RR : A-144 */ else if ((op & 0xf814) == 0x3810) { size = dsp56k_dasm_movec_1(op, opcode_str, arg_str); } /* MOVE(C) : 0011 1WDD DDD1 Z11- : A-144 */ else if ((op & 0xf816) == 0x3816) { size = dsp56k_dasm_movec_2(op, opcode_str, arg_str); } /* MOVE(C) : 0011 1WDD DDD1 t10- xxxx xxxx xxxx xxxx : A-144 */ else if (((op & 0xf816) == 0x3814) && ((op2 & 0x0000) == 0x0000)) { size = dsp56k_dasm_movec_3(op, op2, opcode_str, arg_str); } /* MOVE(C) : 0010 10dd dddD DDDD : A-144 */ else if ((op & 0xfc00) == 0x2800) { size = dsp56k_dasm_movec_4(op, opcode_str, arg_str); } /* MOVE(C) : 0000 0101 BBBB BBBB 0011 1WDD DDD0 ---- : A-144 */ else if (((op & 0xff00) == 0x0500) && ((op2 & 0xf810) == 0x3800)) { size = dsp56k_dasm_movec_5(op, op2, opcode_str, arg_str); } /* MOVE(I) : 0010 00DD BBBB BBBB : A-150 */ else if ((op & 0xfc00) == 0x2000) { size = dsp56k_dasm_movei(op, opcode_str, arg_str); } /* MOVE(M) : 0000 001W RR0M MHHH : A-152 */ else if ((op & 0xfe20) == 0x0200) { size = dsp56k_dasm_movem(op, opcode_str, arg_str); } /* MOVE(M) : 0000 001W RR11 mmRR : A-152 */ else if ((op & 0xfe30) == 0x0230) { size = dsp56k_dasm_movem_1(op, opcode_str, arg_str); } /* MOVE(M) : 0000 0101 BBBB BBBB 0000 001W --0- -HHH : A-152 */ else if (((op & 0xff00) == 0x0500) && ((op2 & 0xfe20) == 0x0200)) { size = dsp56k_dasm_movem_2(op, op2, opcode_str, arg_str); } /* MOVE(P) : 0001 100W HH1p pppp : A-156 */ else if ((op & 0xfe20) == 0x1820) { size = dsp56k_dasm_movep(op, opcode_str, arg_str); } /* MOVE(P) : 0000 110W RRmp pppp : A-156 */ else if ((op & 0xfe00) == 0x0c00) { size = dsp56k_dasm_movep_1(op, opcode_str, arg_str); } /* MOVE(S) : 0001 100W HH0a aaaa : A-158 */ else if ((op & 0xfe20) == 0x1800) { size = dsp56k_dasm_moves(op, opcode_str, arg_str); } /* MPY(su,uu) : 0001 0101 1100 FsQQ : A-164 */ else if ((op & 0xfff0) == 0x15c0) { size = dsp56k_dasm_mpysuuu(op, opcode_str, arg_str); } /* NEGC : 0001 0101 0110 F000 : A-168 */ else if ((op & 0xfff7) == 0x1560) { size = dsp56k_dasm_negc(op, opcode_str, arg_str); } /* NOP : 0000 0000 0000 0000 : A-170 */ else if ((op & 0xffff) == 0x0000) { size = dsp56k_dasm_nop(op, opcode_str, arg_str); } /* NORM : 0001 0101 0010 F0RR : A-172 */ else if ((op & 0xfff4) == 0x1520) { size = dsp56k_dasm_norm(op, opcode_str, arg_str); } /* ORI : 0001 1EE1 iiii iiii : A-178 */ else if ((op & 0xf900) == 0x1900) { size = dsp56k_dasm_ori(op, opcode_str, arg_str); } /* REP : 0000 0000 111- --RR : A-180 */ else if ((op & 0xffe0) == 0x00e0) { size = dsp56k_dasm_rep(op, opcode_str, arg_str); } /* REP : 0000 1111 iiii iiii : A-180 */ else if ((op & 0xff00) == 0x0f00) { size = dsp56k_dasm_rep_1(op, opcode_str, arg_str); } /* REP : 0000 0100 001D DDDD : A-180 */ else if ((op & 0xffe0) == 0x0420) { size = dsp56k_dasm_rep_2(op, opcode_str, arg_str); } /* REPcc : 0000 0001 0101 cccc : A-184 */ else if ((op & 0xfff0) == 0x0150) { size = dsp56k_dasm_repcc(op, opcode_str, arg_str); } /* RESET : 0000 0000 0000 1000 : A-186 */ else if ((op & 0xffff) == 0x0008) { size = dsp56k_dasm_reset(op, opcode_str, arg_str); } /* RTI : 0000 0000 0000 0111 : A-194 */ else if ((op & 0xffff) == 0x0007) { size = dsp56k_dasm_rti(op, opcode_str, arg_str); } /* RTS : 0000 0000 0000 0110 : A-196 */ else if ((op & 0xffff) == 0x0006) { size = dsp56k_dasm_rts(op, opcode_str, arg_str); } /* STOP : 0000 0000 0000 1010 : A-200 */ else if ((op & 0xffff) == 0x000a) { size = dsp56k_dasm_stop(op, opcode_str, arg_str); } /* SWAP : 0001 0101 0111 F001 : A-206 */ else if ((op & 0xfff7) == 0x1571) { size = dsp56k_dasm_swap(op, opcode_str, arg_str); } /* SWI : 0000 0000 0000 0101 : A-208 */ else if ((op & 0xffff) == 0x0005) { size = dsp56k_dasm_swi(op, opcode_str, arg_str); } /* Tcc : 0001 00cc ccTT Fh0h : A-210 */ else if ((op & 0xfc02) == 0x1000) { size = dsp56k_dasm_tcc(op, opcode_str, arg_str); } /* TFR(2) : 0001 0101 0000 F00J : A-214 */ else if ((op & 0xfff6) == 0x1500) { size = dsp56k_dasm_tfr2(op, opcode_str, arg_str); } /* TFR(3) : 0010 01mW RRDD FHHH : A-216 */ else if ((op & 0xfc00) == 0x2400) { size = dsp56k_dasm_tfr3(op, opcode_str, arg_str); } /* TST(2) : 0001 0101 0001 -1DD : A-220 */ else if ((op & 0xfff4) == 0x1514) { size = dsp56k_dasm_tst2(op, opcode_str, arg_str); } /* WAIT : 0000 0000 0000 1011 : A-222 */ else if ((op & 0xffff) == 0x000b) { size = dsp56k_dasm_wait(op, opcode_str, arg_str); } /* ZERO : 0001 0101 0101 F000 : A-224 */ else if ((op & 0xfff7) == 0x1550) { size = dsp56k_dasm_zero(op, opcode_str, arg_str); } /* Assemble opcode string buffer */ if (size >= 1) { pad_string(11, opcode_str); sprintf(buffer, "%s%s", opcode_str, arg_str); } /* Not recognized? Nudge debugger onto the next word */ else if (size == 0) { sprintf(buffer, "unknown"); size = 1; } return (size | DASMFLAG_SUPPORTED); } /*******************************/ /* 32 Parallel move operations */ /*******************************/ /* ADD : 011m mKKK 0rru Fuuu : A-22 */ /* SUB : 011m mKKK 0rru Fuuu : A-202 */ static size_t dsp56k_dasm_addsub_2(const UINT16 op_byte, char* opcode_str, char* arg_str) { /* TODO: How strange. Same as SUB? Investigate */ char D[32]; char S1[32]; char arg[32]; decode_uuuuF_table(BITS(op_byte,0x17), BITS(op_byte,0x08), arg, S1, D); sprintf(opcode_str, "%s", arg); sprintf(arg_str, "%s,%s", S1, D); return 1; } /* MAC : 011m mKKK 1xx0 F1QQ : A-122 */ static size_t dsp56k_dasm_mac_1(const UINT16 op_byte, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; char S2[32]; /* Oddly, these 4 mpxx ops have identical operand ordering as compared to single memory move equivalents */ decode_QQF_table(BITS(op_byte,0x03), BITS(op_byte,0x08), S1, S2, D); sprintf(arg_str, "%s,%s,%s", S1, S2, D); sprintf(opcode_str, "mac"); return 1; } /* MACR: 011m mKKK 1--1 F1QQ : A-124 */ static size_t dsp56k_dasm_macr_1(const UINT16 op_byte, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; char S2[32]; /* Oddly, these 4 mpxx ops have identical operand ordering as compared to single memory move equivalents */ decode_QQF_table(BITS(op_byte,0x03), BITS(op_byte,0x08), S1, S2, D); sprintf(arg_str, "%s,%s,%s", S1, S2, D); sprintf(opcode_str, "macr"); return 1; } /* MOVE : 011m mKKK 0rr1 0000 : A-128 */ static size_t dsp56k_dasm_move_1(const UINT16 op_byte, char* opcode_str, char* arg_str) { /* TODO: This MOVE opcode is .identical. to the TFR one. Investigate */ char D[32]; char S1[32]; decode_DDF_table(BITS(op_byte,0x03), BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "tfr"); sprintf(arg_str, "%s,%s", S1, D); return 1; } /* MPY : 011m mKKK 1xx0 F0QQ : A-160 */ static size_t dsp56k_dasm_mpy_1(const UINT16 op_byte, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; char S2[32]; /* Oddly, these 4 mpxx ops have identical operand ordering as compared to single memory move equivalents */ decode_QQF_table(BITS(op_byte,0x03), BITS(op_byte,0x08), S1, S2, D); sprintf(arg_str, "%s,%s,%s", S1, S2, D); sprintf(opcode_str, "mpy"); return 1; } /* MPYR : 011m mKKK 1--1 F0QQ : A-162 */ static size_t dsp56k_dasm_mpyr_1(const UINT16 op_byte, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; char S2[32]; /* Oddly, these 4 mpxx ops have identical operand ordering as compared to single memory move equivalents */ decode_QQF_table(BITS(op_byte,0x03), BITS(op_byte,0x08), S1, S2, D); sprintf(arg_str, "%s,%s,%s", S1, S2, D); sprintf(opcode_str, "mpyr"); return 1; } /* TFR : 011m mKKK 0rr1 F0DD : A-212 */ static size_t dsp56k_dasm_tfr_2(const UINT16 op_byte, char* opcode_str, char* arg_str) { /* TODO - Same as move above. Investigate */ char D[32]; char S1[32]; decode_DDF_table(BITS(op_byte,0x03), BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "tfr"); sprintf(arg_str, "%s,%s", S1, D); return 1; } /* MPY : 0001 0110 RRDD FQQQ : A-160 */ static size_t dsp56k_dasm_mpy_2(const UINT16 op_byte, char* opcode_str, char* arg_str) { /* TODO // MPY - 0001 0110 RRDD FQQQ decode_k_table(BITS(op,0x0100), Dnot); Rnum = decode_RR_table(BITS(op,0x00c0)); decode_DD_table(BITS(op,0x0030), S); decode_QQQF_table(BITS(op,0x0007), BITS(op,0x0008), S1, S2, D); sprintf(buffer, "mpy %s,%s,%s %s,(R%d)+N%d %s,%s", S1, S2, D, Dnot, Rnum, Rnum, S, Dnot); // Strange, but not entirely out of the question - this 'k' parameter is hardcoded // I cheat here and do the parallel memory data move above - this specific one is only used twice retSize = 1; */ return 0; } /* MAC : 0001 0111 RRDD FQQQ : A-122 */ static size_t dsp56k_dasm_mac_2(const UINT16 op_byte, char* opcode_str, char* arg_str) { /* TODO // MAC - 0001 0111 RRDD FQQQ decode_k_table(BITS(op,0x0100), Dnot); Rnum = decode_RR_table(BITS(op,0x00c0)); decode_DD_table(BITS(op,0x0030), S); decode_QQQF_table(BITS(op,0x0007), BITS(op,0x0008), S1, S2, D); sprintf(buffer, "mac %s,%s,%s %s,(R%d)+N%d %s,%s", S1, S2, D, Dnot, Rnum, Rnum, S, Dnot); // Strange, but not entirely out of the question - this 'k' parameter is hardcoded // I cheat here and do the parallel memory data move above - this specific one is only used twice retSize = 1; */ return 0; } /* CLR : .... .... 0000 F001 : A-60 */ static size_t dsp56k_dasm_clr(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "clr"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* ADD : .... .... 0000 FJJJ : A-22 */ static size_t dsp56k_dasm_add(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJJF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "add"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* MOVE : .... .... 0001 0001 : A-128 */ static size_t dsp56k_dasm_move(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { /* Equivalent to a NOP (+ parallel move) */ sprintf(opcode_str, "move"); sprintf(arg_str, " "); sprintf(d_register, " "); return 1; } /* TFR : .... .... 0001 FJJJ : A-212 */ static size_t dsp56k_dasm_tfr(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJJF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "tfr"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* RND : .... .... 0010 F000 : A-188 */ static size_t dsp56k_dasm_rnd(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "rnd"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* TST : .... .... 0010 F001 : A-218 */ static size_t dsp56k_dasm_tst(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "tst"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* INC : .... .... 0010 F010 : A-104 */ static size_t dsp56k_dasm_inc(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "inc"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* INC24 : .... .... 0010 F011 : A-106 */ static size_t dsp56k_dasm_inc24(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "inc24"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* OR : .... .... 0010 F1JJ : A-176 */ static size_t dsp56k_dasm_or(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJF_table(BITS(op_byte,0x03),BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "or"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* ASR : .... .... 0011 F000 : A-32 */ static size_t dsp56k_dasm_asr(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "asr"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* ASL : .... .... 0011 F001 : A-28 */ static size_t dsp56k_dasm_asl(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "asl"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* LSR : .... .... 0011 F010 : A-120 */ static size_t dsp56k_dasm_lsr(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "lsr"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* LSL : .... .... 0011 F011 : A-118 */ static size_t dsp56k_dasm_lsl(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "lsl"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* EOR : .... .... 0011 F1JJ : A-94 */ static size_t dsp56k_dasm_eor(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJF_table(BITS(op_byte,0x03),BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "eor"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* SUBL : .... .... 0100 F001 : A-204 */ static size_t dsp56k_dasm_subl(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { sprintf(opcode_str, "subl"); /* Only one option for the F table */ if (!BITS(op_byte,0x08)) { sprintf(arg_str, "B,A"); sprintf(d_register, "A"); } else { sprintf(arg_str, "!"); } return 1; } /* SUB : .... .... 0100 FJJJ : A-202 */ static size_t dsp56k_dasm_sub(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJJF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "sub"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* CLR24 : .... .... 0101 F001 : A-62 */ static size_t dsp56k_dasm_clr24(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "clr24"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* SBC : .... .... 0101 F01J : A-198 */ static size_t dsp56k_dasm_sbc(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JF_table(BITS(op_byte,0x01), BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "sbc"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* CMP : .... .... 0101 FJJJ : A-64 */ static size_t dsp56k_dasm_cmp(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJJF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, D); /* TODO: This is a JJJF limited */ sprintf(opcode_str, "cmp"); sprintf(arg_str, "%s,%s", S1,D); sprintf(d_register, "%s", D); return 1; } /* NEG : .... .... 0110 F000 : A-166 */ static size_t dsp56k_dasm_neg(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "neg"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* NOT : .... .... 0110 F001 : A-174 */ static size_t dsp56k_dasm_not(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "not"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* DEC : .... .... 0110 F010 : A-72 */ static size_t dsp56k_dasm_dec(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "dec"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* DEC24 : .... .... 0110 F011 : A-74 */ static size_t dsp56k_dasm_dec24(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "dec24"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* AND : .... .... 0110 F1JJ : A-24 */ static size_t dsp56k_dasm_and(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJF_table(BITS(op_byte,0x03),BITS(op_byte,0x08), S1, D); sprintf(opcode_str, "and"); sprintf(arg_str, "%s,%s", S1, D); sprintf(d_register, "%s", D); return 1; } /* ABS : .... .... 0111 F001 : A-18 */ static size_t dsp56k_dasm_abs(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "abs"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* ROR : .... .... 0111 F010 : A-192 */ static size_t dsp56k_dasm_ror(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "ror"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* ROL : .... .... 0111 F011 : A-190 */ static size_t dsp56k_dasm_rol(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; decode_F_table(BITS(op_byte,0x08), D); sprintf(opcode_str, "rol"); sprintf(arg_str, "%s", D); sprintf(d_register, "%s", D); return 1; } /* CMPM : .... .... 0111 FJJJ : A-66 */ static size_t dsp56k_dasm_cmpm(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; decode_JJJF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, D); /* TODO: This is JJJF limited */ sprintf(opcode_str, "cmpm"); sprintf(arg_str, "%s,%s", S1,D); sprintf(d_register, "%s", D); return 1; } /* MPY : .... .... 1k00 FQQQ : A-160 -- CONFIRMED TYPO IN DOCS (HHHH vs HHHW) */ static size_t dsp56k_dasm_mpy(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; char S2[32]; char SIGN[32]; decode_QQQF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, S2, D); decode_kSign_table(BITS(op_byte,0x40), SIGN); sprintf(opcode_str, "mpy"); sprintf(arg_str, "(%s)%s,%s,%s", SIGN, S2, S1, D); sprintf(d_register, "%s", D); return 1; } /* MPYR : .... .... 1k01 FQQQ : A-162 */ static size_t dsp56k_dasm_mpyr(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; char S2[32]; char SIGN[32]; decode_QQQF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, S2, D); decode_kSign_table(BITS(op_byte,0x40), SIGN); sprintf(opcode_str, "mpyr"); sprintf(arg_str, "(%s)%s,%s,%s", SIGN, S2, S1, D); sprintf(d_register, "%s", D); return 1; } /* MAC : .... .... 1k10 FQQQ : A-122 */ static size_t dsp56k_dasm_mac(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; char S2[32]; char SIGN[32]; decode_QQQF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, S2, D); decode_kSign_table(BITS(op_byte,0x40), SIGN); sprintf(opcode_str, "mac"); sprintf(arg_str, "(%s)%s,%s,%s", SIGN, S2, S1, D); sprintf(d_register, "%s", D); return 1; } /* MACR : .... .... 1k11 FQQQ : A-124 -- DRAMA - rr vs xx (805) */ static size_t dsp56k_dasm_macr(const UINT16 op_byte, char* opcode_str, char* arg_str, char* d_register) { char D[32]; char S1[32]; char S2[32]; char SIGN[32]; decode_QQQF_table(BITS(op_byte,0x07), BITS(op_byte,0x08), S1, S2, D); decode_kSign_table(BITS(op_byte,0x40), SIGN); sprintf(opcode_str, "macr"); /* TODO: It's a little odd that macr is S1,S2 while everyone else (mac, mpy, mpyr) is S2,S1. Check! */ sprintf(arg_str, "(%s)%s,%s,%s", SIGN, S1, S2, D); sprintf(d_register, "%s", D); return 1; } /******************************/ /* Remaining non-parallel ops */ /******************************/ /* ADC : 0001 0101 0000 F01J : A-20 */ static size_t dsp56k_dasm_adc(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; decode_JF_table(BITS(op,0x0001), BITS(op,0x0008), S1, D); sprintf(opcode_str, "adc"); sprintf(arg_str, "%s,%s", S1, D); return 1; } /* ANDI : 0001 1EE0 iiii iiii : A-26 */ static size_t dsp56k_dasm_andi(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_EE_table(BITS(op,0x0600), D); sprintf(opcode_str, "and(i)"); sprintf(arg_str, "#%02x,%s", BITS(op,0x00ff), D); return 1; } /* ASL4 : 0001 0101 0011 F001 : A-30 */ static size_t dsp56k_dasm_asl4(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "asl4"); sprintf(arg_str, "%s", D); return 1; } /* ASR4 : 0001 0101 0011 F000 : A-34 */ static size_t dsp56k_dasm_asr4(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "asr4"); sprintf(arg_str, "%s", D); return 1; } /* ASR16 : 0001 0101 0111 F000 : A-36 */ static size_t dsp56k_dasm_asr16(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "asr16"); sprintf(arg_str, "%s", D); return 1; } /* BFCHG : 0001 0100 11Pp pppp BBB1 0010 iiii iiii : A-38 */ /* BFCHG : 0001 0100 101- --RR BBB1 0010 iiii iiii : A-38 */ /* BFCHG : 0001 0100 100D DDDD BBB1 0010 iiii iiii : A-38 */ /* BFCLR : 0001 0100 11Pp pppp BBB0 0100 iiii iiii : A-40 */ /* BFCLR : 0001 0100 101- --RR BBB0 0100 iiii iiii : A-40 */ /* BFCLR : 0001 0100 100D DDDD BBB0 0100 iiii iiii : A-40 */ /* BFSET : 0001 0100 11Pp pppp BBB1 1000 iiii iiii : A-42 */ /* BFSET : 0001 0100 101- --RR BBB1 1000 iiii iiii : A-42 */ /* BFSET : 0001 0100 100D DDDD BBB1 1000 iiii iiii : A-42 */ /* BFTSTH : 0001 0100 01Pp pppp BBB1 0000 iiii iiii : A-44 */ /* BFTSTH : 0001 0100 001- --RR BBB1 0000 iiii iiii : A-44 */ /* BFTSTH : 0001 0100 000D DDDD BBB1 0000 iiii iiii : A-44 */ /* BFTSTL : 0001 0100 01Pp pppp BBB0 0000 iiii iiii : A-46 */ /* BFTSTL : 0001 0100 001- --RR BBB0 0000 iiii iiii : A-46 */ /* BFTSTL : 0001 0100 000D DDDD BBB0 0000 iiii iiii : A-46 */ static size_t dsp56k_dasm_bfop(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { char D[32]; int upperMiddleLower = -1; UINT16 iVal = 0x0000; UINT16 rVal = 0x0000; /* Decode the common parts */ upperMiddleLower = decode_BBB_table(BITS(op2,0xe000)); iVal = BITS(op2,0x00ff); switch(upperMiddleLower) { case BBB_UPPER: iVal <<= 8; break; case BBB_MIDDLE: iVal <<= 4; break; case BBB_LOWER: iVal <<= 0; break; } switch(BITS(op,0x00e0)) { case 0x6: case 0x7: case 0x2: case 0x3: assemble_D_from_P_table(BITS(op,0x0020), BITS(op,0x001f), D); break; case 0x5: case 0x1: rVal = decode_RR_table(BITS(op,0x0003)); sprintf(D, "X:(R%d)", rVal); break; case 0x4: case 0x0: decode_DDDDD_table(BITS(op,0x001f), D); break; } sprintf(arg_str, "#%04x,%s", iVal, D); switch(BITS(op2,0x1f00)) { case 0x12: sprintf(opcode_str, "bfchg"); break; case 0x04: sprintf(opcode_str, "bfclr"); break; case 0x18: sprintf(opcode_str, "bfset"); break; case 0x10: sprintf(opcode_str, "bftsth"); break; case 0x00: sprintf(opcode_str, "bftstl"); break; } return 2; } /* Bcc : 0000 0111 --11 cccc xxxx xxxx xxxx xxxx : A-48 */ static size_t dsp56k_dasm_bcc(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "b.%s", M); sprintf(arg_str, "%d (0x%04x)", (INT16)op2, pc + 2 + (INT16)op2); return 2; } /* Bcc : 0010 11cc ccee eeee : A-48 */ static size_t dsp56k_dasm_bcc_1(const UINT16 op, char* opcode_str, char* arg_str, const offs_t pc) { char M[32]; INT8 relativeInt; decode_cccc_table(BITS(op,0x3c0), M); relativeInt = get_6_bit_signed_value(BITS(op,0x003f)); sprintf(opcode_str, "b.%s", M); sprintf(arg_str, "%d (0x%04x)", relativeInt, pc + 1 + relativeInt); return 1; } /* Bcc : 0000 0111 RR10 cccc : A-48 */ static size_t dsp56k_dasm_bcc_2(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char M[32]; decode_cccc_table(BITS(op,0x000f), M); Rnum = decode_RR_table(BITS(op,0x00c0)); sprintf(opcode_str, "b.%s", M); sprintf(arg_str, "R%d", Rnum); return 1; } /* BRA : 0000 0001 0011 11-- xxxx xxxx xxxx xxxx : A-50 */ static size_t dsp56k_dasm_bra(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc) { sprintf(opcode_str, "bra"); sprintf(arg_str, "%d (0x%04x)", (INT16)op2, pc + 2 + op2); return 2; } /* BRA : 0000 1011 aaaa aaaa : A-50 */ static size_t dsp56k_dasm_bra_1(const UINT16 op, char* opcode_str, char* arg_str, const offs_t pc) { sprintf(opcode_str, "bra"); sprintf(arg_str, "%d (0x%02x)", (INT8)BITS(op,0x00ff), pc + 1 + (INT8)BITS(op,0x00ff)); return 1; } /* BRA : 0000 0001 0010 11RR : A-50 */ static size_t dsp56k_dasm_bra_2(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "bra"); sprintf(arg_str, "R%d", Rnum); return 1; } /* BRKc : 0000 0001 0001 cccc : A-52 */ static size_t dsp56k_dasm_brkcc(const UINT16 op, char* opcode_str, char* arg_str) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "brk.%s", M); sprintf(arg_str, " "); return 1; } /* BScc : 0000 0111 --01 cccc xxxx xxxx xxxx xxxx : A-54 */ static size_t dsp56k_dasm_bscc(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "bs.%s", M); sprintf(arg_str, "%d (0x%04x)", (INT16)op2, pc + 2 + (INT16)op2); return (2 | DASMFLAG_STEP_OVER); /* probably */ } /* BScc: 0000 0111 RR00 cccc : A-54 */ static size_t dsp56k_dasm_bscc_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char M[32]; decode_cccc_table(BITS(op,0x000f), M); Rnum = decode_RR_table(BITS(op,0x00c0)); sprintf(opcode_str, "bs.%s", M); sprintf(arg_str, "R%d", Rnum); return (1 | DASMFLAG_STEP_OVER); /* probably. What's the diff between a branch and a jump? */ } /* BSR : 0000 0001 0011 10-- xxxx xxxx xxxx xxxx : A-56 */ static size_t dsp56k_dasm_bsr(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str, const offs_t pc) { sprintf(opcode_str, "bsr"); sprintf(arg_str, "%d (0x%04x)", (INT16)op2, pc + 2 + (INT16)op2); return (2 | DASMFLAG_STEP_OVER); } /* BSR : 0000 0001 0010 10RR : A-56 */ static size_t dsp56k_dasm_bsr_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "bsr"); sprintf(arg_str, "R%d", Rnum); return (1 | DASMFLAG_STEP_OVER); } /* CHKAAU : 0000 0000 0000 0100 : A-58 */ static size_t dsp56k_dasm_chkaau(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "chkaau"); sprintf(arg_str, " "); return 1; } /* DEBUG : 0000 0000 0000 0001 : A-68 */ static size_t dsp56k_dasm_debug(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "debug"); sprintf(arg_str, " "); return 1; } /* DEBUGcc : 0000 0000 0101 cccc : A-70 */ static size_t dsp56k_dasm_debugcc(const UINT16 op, char* opcode_str, char* arg_str) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "debug.%s", M); sprintf(arg_str, " "); return 1; } /* DIV : 0001 0101 0--0 F1DD : A-76 */ /* WARNING : DOCS SAY THERE IS A PARALLEL MOVE HERE !!! */ static size_t dsp56k_dasm_div(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; decode_DDF_table(BITS(op,0x0003), BITS(op,0x0008), S1, D); sprintf(opcode_str, "div"); sprintf(arg_str, "%s,%s", S1, D); return 1; } /* DMAC : 0001 0101 10s1 FsQQ : A-80 */ static size_t dsp56k_dasm_dmac(const UINT16 op, char* opcode_str, char* arg_str) { char A[32]; char D[32]; char S1[32]; char S2[32]; decode_ss_table(BITS(op,0x0024), A); decode_QQF_special_table(BITS(op,0x0003), BITS(op,0x0008), S1, S2, D); /* Special QQF */ sprintf(opcode_str, "dmac(%s)", A); sprintf(arg_str, "%s,%s,%s", S1, S2, D); return 1; } /* DO : 0000 0000 110- --RR xxxx xxxx xxxx xxxx : A-82 */ static size_t dsp56k_dasm_do(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { int Rnum; Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "do"); sprintf(arg_str, "X:(R%d),%02x", Rnum, op2); return 2; } /* DO : 0000 1110 iiii iiii xxxx xxxx xxxx xxxx : A-82 */ static size_t dsp56k_dasm_do_1(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { sprintf(opcode_str, "do"); sprintf(arg_str, "#%02x,%04x", BITS(op,0x00ff), op2); return 2; } /* DO : 0000 0100 000D DDDD xxxx xxxx xxxx xxxx : A-82 */ static size_t dsp56k_dasm_do_2(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { char S1[32]; decode_DDDDD_table(BITS(op,0x001f), S1); sprintf(opcode_str, "do"); sprintf(arg_str, "%s,%04x", S1, op2); return 2; } /* DO FOREVER : 0000 0000 0000 0010 xxxx xxxx xxxx xxxx : A-88 */ static size_t dsp56k_dasm_doforever(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { sprintf(opcode_str, "doForever"); sprintf(arg_str, "%04x", op2); return 2; } /* ENDDO : 0000 0000 0000 1001 : A-92 */ static size_t dsp56k_dasm_enddo(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "enddo"); sprintf(arg_str, " "); return 1; } /* EXT : 0001 0101 0101 F010 : A-96 */ static size_t dsp56k_dasm_ext(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "ext"); sprintf(arg_str, "%s", D); return 1; } /* ILLEGAL : 0000 0000 0000 1111 : A-98 */ static size_t dsp56k_dasm_illegal(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "illegal"); sprintf(arg_str, " "); return 1; } /* IMAC : 0001 0101 1010 FQQQ : A-100 */ static size_t dsp56k_dasm_imac(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; char S2[32]; decode_QQQF_table(BITS(op,0x0007), BITS(op,0x0008), S1, S2, D); sprintf(opcode_str, "imac"); sprintf(arg_str, "%s,%s,%s", S1, S2, D); return 1; } /* IMPY : 0001 0101 1000 FQQQ : A-102 */ static size_t dsp56k_dasm_impy(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; char S2[32]; decode_QQQF_table(BITS(op,0x0007), BITS(op,0x0008), S1, S2, D); sprintf(opcode_str, "impy"); sprintf(arg_str, "%s,%s,%s", S1, S2, D); return 1; } /* Jcc : 0000 0110 --11 cccc xxxx xxxx xxxx xxxx : A-108 */ static size_t dsp56k_dasm_jcc(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "j.%s", M); sprintf(arg_str, "%04x", op2); return 2; } /* Jcc : 0000 0110 RR10 cccc : A-108 */ static size_t dsp56k_dasm_jcc_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char M[32]; decode_cccc_table(BITS(op,0x000f), M); Rnum = decode_RR_table(BITS(op,0x00c0)); sprintf(opcode_str, "j.%s", M); sprintf(arg_str, "R%d", Rnum); return 1; } /* JMP : 0000 0001 0011 01-- xxxx xxxx xxxx xxxx : A-110 */ static size_t dsp56k_dasm_jmp(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { sprintf(opcode_str, "jmp"); sprintf(arg_str, "%04x", op2); return 2; } /* JMP : 0000 0001 0010 01RR : A-110 */ static size_t dsp56k_dasm_jmp_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "jmp"); sprintf(arg_str, "R%d", Rnum); return 1; } /* JScc : 0000 0110 --01 cccc xxxx xxxx xxxx xxxx : A-112 */ static size_t dsp56k_dasm_jscc(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "js.%s", M); sprintf(arg_str, "%04x", op2); return (2 |DASMFLAG_STEP_OVER); /* probably */ } /* JScc : 0000 0110 RR00 cccc : A-112 */ static size_t dsp56k_dasm_jscc_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char M[32]; decode_cccc_table(BITS(op,0x000f), M); Rnum = decode_RR_table(BITS(op,0x00c0)); sprintf(opcode_str, "js.%s", M); sprintf(arg_str, "R%d", Rnum); return (1 | DASMFLAG_STEP_OVER); /* probably. What's the diff between a branch and a jump? */ } /* JSR : 0000 0001 0011 00-- xxxx xxxx xxxx xxxx : A-114 */ static size_t dsp56k_dasm_jsr(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { sprintf(opcode_str, "jsr"); sprintf(arg_str, "%04x", op2); return (2 | DASMFLAG_STEP_OVER); } /* JSR : 0000 1010 AAAA AAAA : A-114 */ static size_t dsp56k_dasm_jsr_1(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "jsr"); sprintf(arg_str, "%d (0x%02x)", BITS(op,0x00ff), BITS(op,0x00ff)); return (1 | DASMFLAG_STEP_OVER); } /* JSR : 0000 0001 0010 00RR : A-114 */ static size_t dsp56k_dasm_jsr_2(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "jsr"); sprintf(arg_str, "R%d", Rnum); return (1 | DASMFLAG_STEP_OVER); } /* LEA : 0000 0001 11TT MMRR : A-116 */ static size_t dsp56k_dasm_lea(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; int Tnum; char ea[32]; Tnum = decode_TT_table(BITS(op,0x0030)); Rnum = decode_RR_table(BITS(op,0x0003)); assemble_ea_from_MM_table(BITS(op,0x000c), Rnum, ea); sprintf(opcode_str, "lea"); sprintf(arg_str, "%s,R%d", ea, Tnum); return 1; } /* LEA : 0000 0001 10NN MMRR : A-116 */ static size_t dsp56k_dasm_lea_1(const UINT16 op, char* opcode_str, char* arg_str) { int Nnum; int Rnum; char ea[32]; Nnum = decode_NN_table(BITS(op,0x0030)); Rnum = decode_RR_table(BITS(op,0x0003)); assemble_ea_from_MM_table(BITS(op,0x000c), Rnum, ea); sprintf(opcode_str, "lea"); sprintf(arg_str, "%s,N%d", ea, Nnum); return 1; } /* MAC(su,uu) : 0001 0101 1110 FsQQ : A-126 */ static size_t dsp56k_dasm_macsuuu(const UINT16 op, char* opcode_str, char* arg_str) { char A[32]; char D[32]; char S1[32]; char S2[32]; decode_s_table(BITS(op,0x0004), A); decode_QQF_special_table(BITS(op,0x0003), BITS(op,0x0008), S1, S2, D); /* Special QQF */ sprintf(opcode_str, "mac(%s)", A); sprintf(arg_str, "%s,%s,%s", S1, S2, D); return 1; } /* MOVE : 0000 0101 BBBB BBBB ---- HHHW 0001 0001 : A-128 */ static size_t dsp56k_dasm_move_2(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { INT8 B; char SD[32]; char args[32]; B = BITS(op,0x00ff); decode_HHH_table(BITS(op2,0x0e00), SD); assemble_reg_from_W_table(BITS(op2,0x0100), args, 'X', SD, B); sprintf(opcode_str, "move"); sprintf(arg_str, "%s", args); return 2; } /* MOVE(C) : 0011 1WDD DDD0 MMRR : A-144 */ static size_t dsp56k_dasm_movec(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char ea[32]; char SD[32]; char args[32]; decode_DDDDD_table(BITS(op,0x03e0), SD); Rnum = decode_RR_table(BITS(op,0x0003)); assemble_ea_from_MM_table(BITS(op,0x000c), Rnum, ea); assemble_arguments_from_W_table(BITS(op,0x0400), args, 'X', SD, ea); sprintf(opcode_str, "move(c)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(C) : 0011 1WDD DDD1 q0RR : A-144 */ static size_t dsp56k_dasm_movec_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char ea[32]; char SD[32]; char args[32]; decode_DDDDD_table(BITS(op,0x03e0), SD); Rnum = decode_RR_table(BITS(op,0x0003)); assemble_ea_from_q_table(BITS(op,0x0008), Rnum, ea); assemble_arguments_from_W_table(BITS(op,0x0400), args, 'X', SD, ea); sprintf(opcode_str, "move(c)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(C) : 0011 1WDD DDD1 Z11- : A-144 */ static size_t dsp56k_dasm_movec_2(const UINT16 op, char* opcode_str, char* arg_str) { char ea[32]; char SD[32]; char args[32]; decode_DDDDD_table(BITS(op,0x03e0), SD); decode_Z_table(BITS(op,0x0008), ea); assemble_arguments_from_W_table(BITS(op,0x0400), args, 'X', SD, ea); sprintf(opcode_str, "move(c)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(C) : 0011 1WDD DDD1 t10- xxxx xxxx xxxx xxxx : A-144 */ static size_t dsp56k_dasm_movec_3(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { char ea[32]; char SD[32]; char args[32]; decode_DDDDD_table(BITS(op,0x03e0), SD); assemble_ea_from_t_table(BITS(op,0x0008), op2, ea); if (BITS(op,0x0400)) /* order fixed - 02/03/05 */ sprintf(args, "%s,%s", ea, SD); else sprintf(args, "%s,%s", SD, ea); sprintf(opcode_str, "move(c)"); sprintf(arg_str, "%s", args); return 2; } /* MOVE(C) : 0010 10dd dddD DDDD : A-144 */ static size_t dsp56k_dasm_movec_4(const UINT16 op, char* opcode_str, char* arg_str) { char D1[32]; char S1[32]; decode_DDDDD_table(BITS(op,0x03e0), S1); decode_DDDDD_table(BITS(op,0x001f), D1); sprintf(opcode_str, "move(c)"); sprintf(arg_str, "%s,%s", S1, D1); return 1; } /* MOVE(C) : 0000 0101 BBBB BBBB 0011 1WDD DDD0 ---- : A-144 */ static size_t dsp56k_dasm_movec_5(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { INT8 B; char SD[32]; char args[32]; B = BITS(op,0x00ff); decode_DDDDD_table(BITS(op2,0x03e0), SD); assemble_reg_from_W_table(BITS(op2,0x0400), args, 'X', SD, B); sprintf(opcode_str, "move(c)"); sprintf(arg_str, "%s", args); return 2; } /* MOVE(I) : 0010 00DD BBBB BBBB : A-150 */ static size_t dsp56k_dasm_movei(const UINT16 op, char* opcode_str, char* arg_str) { char D1[32]; decode_DD_table(BITS(op,0x0300), D1); sprintf(opcode_str, "move(i)"); sprintf(arg_str, "#%02x,%s", BITS(op,0x00ff), D1); return 1; } /* MOVE(M) : 0000 001W RR0M MHHH : A-152 */ static size_t dsp56k_dasm_movem(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char ea[32]; char SD[32]; char args[32]; Rnum = decode_RR_table(BITS(op,0x00c0)); decode_HHH_table(BITS(op,0x0007), SD); assemble_ea_from_MM_table(BITS(op,0x0018), Rnum, ea); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'P', SD, ea); sprintf(opcode_str, "move(m)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(M) : 0000 001W RR11 mmRR : A-152 */ static size_t dsp56k_dasm_movem_1(const UINT16 op, char* opcode_str, char* arg_str) { char ea[32]; char SD[32]; char ea2[32]; char args[32]; assemble_eas_from_m_table(BITS(op,0x000c), BITS(op,0x00c0), BITS(op,0x0003), ea, ea2); sprintf(SD, "P:%s", ea); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, ea2); sprintf(opcode_str, "move(m)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(M) : 0000 0101 BBBB BBBB 0000 001W --0- -HHH : A-152 */ static size_t dsp56k_dasm_movem_2(const UINT16 op, const UINT16 op2, char* opcode_str, char* arg_str) { INT8 B; char SD[32]; char args[32]; B = BITS(op,0x00ff); decode_HHH_table(BITS(op2,0x0007), SD); assemble_reg_from_W_table(BITS(op2,0x0100), args, 'P', SD, B); sprintf(opcode_str, "move(m)"); sprintf(arg_str, "%s", args); /* !!! The docs list the read/write order backwards for all move(m)'s - crackbabies ??? */ return 2; } /* MOVE(P) : 0001 100W HH1p pppp : A-156 */ static size_t dsp56k_dasm_movep(const UINT16 op, char* opcode_str, char* arg_str) { char A[32]; char SD[32]; char args[32]; char fullAddy[128]; decode_HH_table(BITS(op,0x00c0), SD); assemble_address_from_IO_short_address(BITS(op,0x001f), fullAddy); /* Convert Short Absolute Address to full 16-bit */ sprintf(A, "%02x (%s)", BITS(op,0x001f), fullAddy); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, A); sprintf(opcode_str, "move(p)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(P) : 0000 110W RRmp pppp : A-156 */ static size_t dsp56k_dasm_movep_1(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char ea[32]; char SD[32]; char args[32]; char fullAddy[128]; /* Convert Short Absolute Address to full 16-bit */ Rnum = decode_RR_table(BITS(op,0x00c0)); assemble_ea_from_m_table(BITS(op,0x0020), Rnum, ea); assemble_address_from_IO_short_address(BITS(op,0x001f), fullAddy); sprintf(SD, "X:%02x (%s)", BITS(op,0x001f), fullAddy); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, ea); sprintf(opcode_str, "move(p)"); sprintf(arg_str, "%s", args); return 1; } /* MOVE(S) : 0001 100W HH0a aaaa : A-158 */ static size_t dsp56k_dasm_moves(const UINT16 op, char* opcode_str, char* arg_str) { char A[32]; char SD[32]; char args[32]; decode_HH_table(BITS(op,0x00c0), SD); sprintf(A, "00%02x", BITS(op,0x001f)); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, A); sprintf(opcode_str, "move(s)"); sprintf(arg_str, "%s", args); return 1; } /* MPY(su,uu) : 0001 0101 1100 FsQQ : A-164 */ static size_t dsp56k_dasm_mpysuuu(const UINT16 op, char* opcode_str, char* arg_str) { char A[32]; char D[32]; char S1[32]; char S2[32]; decode_s_table(BITS(op,0x0004), A); decode_QQF_special_table(BITS(op,0x0003), BITS(op,0x0008), S1, S2, D); /* Special QQF */ sprintf(opcode_str, "mpy(%s)", A); sprintf(arg_str, "%s,%s,%s", S1, S2, D); return 1; } /* NEGC : 0001 0101 0110 F000 : A-168 */ static size_t dsp56k_dasm_negc(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "negc"); sprintf(arg_str, "%s", D); return 1; } /* NOP : 0000 0000 0000 0000 : A-170 */ static size_t dsp56k_dasm_nop(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "nop"); sprintf(arg_str, " "); return 1; } /* NORM : 0001 0101 0010 F0RR : A-172 */ static size_t dsp56k_dasm_norm(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char D[32]; decode_F_table(BITS(op,0x0008), D); Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "norm"); sprintf(arg_str, "R%d,%s", Rnum, D); return 1; } /* ORI : 0001 1EE1 iiii iiii : A-178 */ static size_t dsp56k_dasm_ori(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_EE_table(BITS(op,0x0600), D); sprintf(opcode_str, "or(i)"); sprintf(arg_str, "#%02x,%s", BITS(op,0x00ff), D); return 1; } /* REP : 0000 0000 111- --RR : A-180 */ static size_t dsp56k_dasm_rep(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; Rnum = decode_RR_table(BITS(op,0x0003)); sprintf(opcode_str, "rep"); sprintf(arg_str, "X:(R%d)", Rnum); return 1; } /* REP : 0000 1111 iiii iiii : A-180 */ static size_t dsp56k_dasm_rep_1(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "rep"); sprintf(arg_str, "%d (0x%02x)", BITS(op,0x00ff), BITS(op,0x00ff)); return 1; } /* REP : 0000 0100 001D DDDD : A-180 */ static size_t dsp56k_dasm_rep_2(const UINT16 op, char* opcode_str, char* arg_str) { char S1[32]; decode_DDDDD_table(BITS(op,0x001f), S1); sprintf(opcode_str, "rep"); sprintf(arg_str, "%s", S1); return 1; } /* REPcc : 0000 0001 0101 cccc : A-184 */ static size_t dsp56k_dasm_repcc(const UINT16 op, char* opcode_str, char* arg_str) { char M[32]; decode_cccc_table(BITS(op,0x000f), M); sprintf(opcode_str, "rep.%s", M); sprintf(arg_str, " "); return 1; } /* RESET : 0000 0000 0000 1000 : A-186 */ static size_t dsp56k_dasm_reset(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "reset"); sprintf(arg_str, " "); return 1; } /* RTI : 0000 0000 0000 0111 : A-194 */ static size_t dsp56k_dasm_rti(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "rti"); sprintf(arg_str, " "); return (1 | DASMFLAG_STEP_OUT); } /* RTS : 0000 0000 0000 0110 : A-196 */ static size_t dsp56k_dasm_rts(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "rts"); sprintf(arg_str, " "); return (1 | DASMFLAG_STEP_OUT); } /* STOP : 0000 0000 0000 1010 : A-200 */ static size_t dsp56k_dasm_stop(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "stop"); sprintf(arg_str, " "); return 1; } /* SWAP : 0001 0101 0111 F001 : A-206 */ static size_t dsp56k_dasm_swap(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "swap"); sprintf(arg_str, "%s", D); return 1; } /* SWI : 0000 0000 0000 0101 : A-208 */ static size_t dsp56k_dasm_swi(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "swi"); sprintf(arg_str, " "); return 1; } /* Tcc : 0001 00cc ccTT Fh0h : A-210 */ static size_t dsp56k_dasm_tcc(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum = -1; char M[32]; char D[32]; char S[32]; decode_cccc_table(BITS(op,0x03c0), M); sprintf(opcode_str, "t.%s", M); Rnum = decode_RR_table(BITS(op,0x0030)); decode_h0hF_table(BITS(op,0x0007),BITS(op,0x0008), S, D); sprintf(arg_str, "%s,%s R0,R%d", S, D, Rnum); /* TODO: Investigate if (S1[0] == D[0] && D[0] == 'A') sprintf(buffer, "t.%s %s,%s", M, S1, D); else sprintf(buffer, "t.%s %s,%s R0,R%d", M, S1, D, Rnum); */ return 1; } /* TFR(2) : 0001 0101 0000 F00J : A-214 */ static size_t dsp56k_dasm_tfr2(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; char S1[32]; decode_JF_table(BITS(op,0x0001),BITS(op,0x0008), D, S1); sprintf(opcode_str, "tfr2"); sprintf(arg_str, "%s,%s", S1, D); return 1; } /* TFR(3) : 0010 01mW RRDD FHHH : A-216 */ static size_t dsp56k_dasm_tfr3(const UINT16 op, char* opcode_str, char* arg_str) { int Rnum; char ea[32]; char D1[32]; char S1[32]; char SD[32]; char args[32]; decode_DDF_table(BITS(op,0x0030), BITS(op,0x0008), D1, S1); /* Intentionally switched */ decode_HHH_table(BITS(op,0x0007), SD); Rnum = decode_RR_table(BITS(op,0x00c0)); assemble_ea_from_m_table(BITS(op,0x0200), Rnum, ea); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, ea); sprintf(opcode_str, "tfr3"); sprintf(arg_str, "%s,%s %s", S1, D1, args); return 1; } /* TST(2) : 0001 0101 0001 -1DD : A-220 */ static size_t dsp56k_dasm_tst2(const UINT16 op, char* opcode_str, char* arg_str) { char S1[32]; decode_DD_table(BITS(op,0x0003), S1); sprintf(opcode_str, "tst2"); sprintf(arg_str, "%s", S1); return 1; } /* WAIT : 0000 0000 0000 1011 : A-222 */ static size_t dsp56k_dasm_wait(const UINT16 op, char* opcode_str, char* arg_str) { sprintf(opcode_str, "wait"); sprintf(arg_str, " "); return 1; } /* ZERO : 0001 0101 0101 F000 : A-224 */ static size_t dsp56k_dasm_zero(const UINT16 op, char* opcode_str, char* arg_str) { char D[32]; decode_F_table(BITS(op,0x0008), D); sprintf(opcode_str, "zero"); sprintf(arg_str, "%s", D); return 1; } /**********************************/ /* Parallel memory move functions */ /**********************************/ /* X Memory Data Move : 1mRR HHHW ---- ---- : A-137 */ static void decode_x_memory_data_move(const UINT16 op, char* parallel_move_str) { int Rnum; char SD[32]; char ea[32]; char args[32]; Rnum = decode_RR_table(BITS(op,0x3000)); decode_HHH_table(BITS(op,0x0e00), SD); assemble_ea_from_m_table(BITS(op,0x4000), Rnum, ea); assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, ea); sprintf(parallel_move_str, "%s", args); } /* X Memory Data Move : 0101 HHHW ---- ---- : A-137 */ static void decode_x_memory_data_move2(const UINT16 op, char* parallel_move_str, char* d_register) { char SD[32] ; char args[32] ; char dest[32] ; if (d_register[0] == 'B') sprintf(dest, "(A1)"); else if (d_register[0] == 'A') sprintf(dest, "(B1)"); else sprintf(dest, "(A1)"); decode_HHH_table(BITS(op,0x0e00), SD) ; assemble_arguments_from_W_table(BITS(op,0x0100), args, 'X', SD, dest) ; sprintf(parallel_move_str, "%s", args); } /* Dual X Memory Data Read : 011m mKKK -rr- ---- : A-142*/ static void decode_dual_x_memory_data_read(const UINT16 op, char* parallel_move_str, char* parallel_move_str2) { int Rnum; char D1[32] = ""; char D2[32] = ""; char ea1[32] = ""; char ea2[32] = ""; Rnum = decode_rr_table(BITS(op,0x0060)); decode_KKK_table(BITS(op,0x0700), D1, D2); assemble_eas_from_m_table(BITS(op,0x1800), Rnum, 3, ea1, ea2); /* TODO : The ^F's should likely be replaced */ if (Rnum == -1) { sprintf(ea1, "(!!)!"); } sprintf(parallel_move_str, "X:%s,%s", ea1, D1); sprintf(parallel_move_str2, "X:%s,%s", ea2, D2); } /* Register to Register Data Move : 0100 IIII ---- ---- : A-133 */ static void decode_register_to_register_data_move(const UINT16 op, char* parallel_move_str, char* d_register) { char S[32]; char D[32]; decode_IIII_table(BITS(op,0x0f00), S, D); if (S[0] == 'F') { S[0] = d_register[0]; S[1] = 0x00; } if (D[0] == '^' && D[1] == 'F') { if (d_register[0] == 'B') sprintf(D, "A"); else if (d_register[0] == 'A') sprintf(D, "B"); else sprintf(D, "A"); /* In the case of no data ALU operation */ } sprintf(parallel_move_str, "%s,%s", S, D); } /* Address Register Update : 0011 0zRR ---- ---- : A-135 */ static void decode_address_register_update(const UINT16 op, char* parallel_move_str) { char ea[32]; int Rnum; Rnum = decode_RR_table(BITS(op,0x0300)); assemble_ea_from_z_table(BITS(op,0x0400), Rnum, ea); sprintf(parallel_move_str, "%s", ea); } /* X Memory Data Write and Register Data Move : 0001 011k RRDD ---- : A-140 */ static void decode_x_memory_data_write_and_register_data_move(const UINT16 op, char* parallel_move_str, char* parallel_move_str2) { int Rnum; char S[32]; char Dnot[32]; /* TODO : Cross-check the Dnot stuff against the MPY & MAC things. */ /* It's likely correct as-is, since the ALU op and this guy probably decode the same bit, */ /* but i may have to pass in d_register just to be sure? */ decode_k_table(BITS(op,0x0100), Dnot); Rnum = decode_RR_table(BITS(op,0x00c0)); decode_DD_table(BITS(op,0x0030), S); /* TODO : is Nn correct here? */ sprintf(parallel_move_str, "%s,X:(R%d)+N%d", Dnot, Rnum, Rnum); sprintf(parallel_move_str2, "%s,%s", S, Dnot); } /* X Memory Data Move with short displacement : 0000 0101 BBBB BBBB ---- HHHW ---- ---- : A-139 */ static void decode_x_memory_data_move_with_short_displacement(const UINT16 op, const UINT16 op2, char* parallel_move_str) { INT8 B; char SD[32]; char args[32]; B = (char)(op & 0x00ff); decode_HHH_table(BITS(op2,0x0e00), SD); assemble_reg_from_W_table(BITS(op2,0x0100), args, 'X', SD, B); sprintf(parallel_move_str, "%s", args); } /******************/ /* Table decoding */ /******************/ static int decode_BBB_table(UINT16 BBB) { switch(BBB) { case 0x4: return BBB_UPPER ; break; case 0x2: return BBB_MIDDLE; break; case 0x1: return BBB_LOWER ; break; } return BBB_LOWER; /* Not really safe... */ } static void decode_cccc_table(UINT16 cccc, char *mnemonic) { switch (cccc) { case 0x0: sprintf(mnemonic, "cc(hs)"); break; case 0x1: sprintf(mnemonic, "ge "); break; case 0x2: sprintf(mnemonic, "ne "); break; case 0x3: sprintf(mnemonic, "pl "); break; case 0x4: sprintf(mnemonic, "nn "); break; case 0x5: sprintf(mnemonic, "ec "); break; case 0x6: sprintf(mnemonic, "lc "); break; case 0x7: sprintf(mnemonic, "gt "); break; case 0x8: sprintf(mnemonic, "cs(lo)"); break; case 0x9: sprintf(mnemonic, "lt "); break; case 0xa: sprintf(mnemonic, "eq "); break; case 0xb: sprintf(mnemonic, "mi "); break; case 0xc: sprintf(mnemonic, "nr "); break; case 0xd: sprintf(mnemonic, "es "); break; case 0xe: sprintf(mnemonic, "ls "); break; case 0xf: sprintf(mnemonic, "le "); break; } } static void decode_DDDDD_table(UINT16 DDDDD, char *SD) { switch(DDDDD) { case 0x00: sprintf(SD, "X0"); break; case 0x01: sprintf(SD, "Y0"); break; case 0x02: sprintf(SD, "X1"); break; case 0x03: sprintf(SD, "Y1"); break; case 0x04: sprintf(SD, "A"); break; case 0x05: sprintf(SD, "B"); break; case 0x06: sprintf(SD, "A0"); break; case 0x07: sprintf(SD, "B0"); break; case 0x08: sprintf(SD, "LC"); break; case 0x09: sprintf(SD, "SR"); break; case 0x0a: sprintf(SD, "OMR"); break; case 0x0b: sprintf(SD, "SP"); break; case 0x0c: sprintf(SD, "A1"); break; case 0x0d: sprintf(SD, "B1"); break; case 0x0e: sprintf(SD, "A2"); break; case 0x0f: sprintf(SD, "B2"); break; case 0x10: sprintf(SD, "R0"); break; case 0x11: sprintf(SD, "R1"); break; case 0x12: sprintf(SD, "R2"); break; case 0x13: sprintf(SD, "R3"); break; case 0x14: sprintf(SD, "M0"); break; case 0x15: sprintf(SD, "M1"); break; case 0x16: sprintf(SD, "M2"); break; case 0x17: sprintf(SD, "M3"); break; case 0x18: sprintf(SD, "SSH"); break; case 0x19: sprintf(SD, "SSL"); break; case 0x1a: sprintf(SD, "LA"); break; case 0x1b: sprintf(SD, "!!"); break; /* no 0x1b */ case 0x1c: sprintf(SD, "N0"); break; case 0x1d: sprintf(SD, "N1"); break; case 0x1e: sprintf(SD, "N2"); break; case 0x1f: sprintf(SD, "N3"); break; } } static void decode_DD_table(UINT16 DD, char *SD) { switch (DD) { case 0x0: sprintf(SD, "X0"); break; case 0x1: sprintf(SD, "Y0"); break; case 0x2: sprintf(SD, "X1"); break; case 0x3: sprintf(SD, "Y1"); break; } } static void decode_DDF_table(UINT16 DD, UINT16 F, char *S, char *D) { UINT16 switchVal = (DD << 1) | F; switch (switchVal) { case 0x0: sprintf(S, "X0"); sprintf(D, "A"); break; case 0x1: sprintf(S, "X0"); sprintf(D, "B"); break; case 0x2: sprintf(S, "Y0"); sprintf(D, "A"); break; case 0x3: sprintf(S, "Y0"); sprintf(D, "B"); break; case 0x4: sprintf(S, "X1"); sprintf(D, "A"); break; case 0x5: sprintf(S, "X1"); sprintf(D, "B"); break; case 0x6: sprintf(S, "Y1"); sprintf(D, "A"); break; case 0x7: sprintf(S, "Y1"); sprintf(D, "B"); break; } } static void decode_EE_table(UINT16 EE, char *D) { switch(EE) { case 0x1: sprintf(D, "MR"); break; case 0x3: sprintf(D, "CCR"); break; case 0x2: sprintf(D, "OMR"); break; } } static void decode_F_table(UINT16 F, char *SD) { switch(F) { case 0x0: sprintf(SD, "A"); break; case 0x1: sprintf(SD, "B"); break; } } static void decode_h0hF_table(UINT16 h0h, UINT16 F, char *S, char *D) { UINT16 switchVal = (h0h << 1) | F; switch (switchVal) { case 0x8: sprintf(S, "X0"); sprintf(D, "A"); break; case 0x9: sprintf(S, "X0"); sprintf(D, "B"); break; case 0xa: sprintf(S, "Y0"); sprintf(D, "A"); break; case 0xb: sprintf(S, "Y0"); sprintf(D, "B"); break; case 0x2: sprintf(S, "A") ; sprintf(D, "A"); break; case 0x1: sprintf(S, "A") ; sprintf(D, "B"); break; case 0x0: sprintf(S, "B") ; sprintf(D, "A"); break; case 0x3: sprintf(S, "B") ; sprintf(D, "B"); break; } } static void decode_HH_table(UINT16 HH, char *SD) { switch(HH) { case 0x0: sprintf(SD, "X0"); break; case 0x1: sprintf(SD, "Y0"); break; case 0x2: sprintf(SD, "A") ; break; case 0x3: sprintf(SD, "B") ; break; } } static void decode_HHH_table(UINT16 HHH, char *SD) { switch(HHH) { case 0x0: sprintf(SD, "X0"); break; case 0x1: sprintf(SD, "Y0"); break; case 0x2: sprintf(SD, "X1"); break; case 0x3: sprintf(SD, "Y1"); break; case 0x4: sprintf(SD, "A") ; break; case 0x5: sprintf(SD, "B") ; break; case 0x6: sprintf(SD, "A0"); break; case 0x7: sprintf(SD, "B0"); break; } } static void decode_IIII_table(UINT16 IIII, char *S, char *D) { switch(IIII) { case 0x0: sprintf(S, "X0"); sprintf(D, "^F"); break; case 0x1: sprintf(S, "Y0"); sprintf(D, "^F"); break; case 0x2: sprintf(S, "X1"); sprintf(D, "^F"); break; case 0x3: sprintf(S, "Y1"); sprintf(D, "^F"); break; case 0x4: sprintf(S, "A"); sprintf(D, "X0"); break; case 0x5: sprintf(S, "B"); sprintf(D, "Y0"); break; case 0x6: sprintf(S, "A0"); sprintf(D, "X0"); break; case 0x7: sprintf(S, "B0"); sprintf(D, "Y0"); break; case 0x8: sprintf(S, "F"); sprintf(D, "^F"); break; case 0x9: sprintf(S, "F"); sprintf(D, "^F"); break; case 0xa: sprintf(S, "?"); sprintf(D, "?"); break; case 0xb: sprintf(S, "?"); sprintf(D, "?"); break; case 0xc: sprintf(S, "A"); sprintf(D, "X1"); break; case 0xd: sprintf(S, "B"); sprintf(D, "Y1"); break; case 0xe: sprintf(S, "A0"); sprintf(D, "X1"); break; case 0xf: sprintf(S, "B0"); sprintf(D, "Y1"); break; } } static void decode_JJJF_table(UINT16 JJJ, UINT16 F, char *S, char *D) { UINT16 switchVal = (JJJ << 1) | F; switch(switchVal) { case 0x0: sprintf(S, "B") ; sprintf(D, "A"); break; case 0x1: sprintf(S, "A") ; sprintf(D, "B"); break; case 0x2: sprintf(S, "!") ; sprintf(D, "!"); break; case 0x3: sprintf(S, "!") ; sprintf(D, "!"); break; case 0x4: sprintf(S, "X") ; sprintf(D, "A"); break; case 0x5: sprintf(S, "X") ; sprintf(D, "B"); break; case 0x6: sprintf(S, "Y") ; sprintf(D, "A"); break; case 0x7: sprintf(S, "Y") ; sprintf(D, "B"); break; case 0x8: sprintf(S, "X0"); sprintf(D, "A"); break; case 0x9: sprintf(S, "X0"); sprintf(D, "B"); break; case 0xa: sprintf(S, "Y0"); sprintf(D, "A"); break; case 0xb: sprintf(S, "Y0"); sprintf(D, "B"); break; case 0xc: sprintf(S, "X1"); sprintf(D, "A"); break; case 0xd: sprintf(S, "X1"); sprintf(D, "B"); break; case 0xe: sprintf(S, "Y1"); sprintf(D, "A"); break; case 0xf: sprintf(S, "Y1"); sprintf(D, "B"); break; } } static void decode_JJF_table(UINT16 JJ, UINT16 F, char *S, char *D) { UINT16 switchVal = (JJ << 1) | F; switch (switchVal) { case 0x0: sprintf(S, "X0"); sprintf(D, "A"); break; case 0x1: sprintf(S, "X0"); sprintf(D, "B"); break; case 0x2: sprintf(S, "Y0"); sprintf(D, "A"); break; case 0x3: sprintf(S, "Y0"); sprintf(D, "B"); break; case 0x4: sprintf(S, "X1"); sprintf(D, "A"); break; case 0x5: sprintf(S, "X1"); sprintf(D, "B"); break; case 0x6: sprintf(S, "Y1"); sprintf(D, "A"); break; case 0x7: sprintf(S, "Y1"); sprintf(D, "B"); break; } } static void decode_JF_table(UINT16 J, UINT16 F, char *S, char *D) { UINT16 switchVal = (J << 1) | F; switch(switchVal) { case 0x0: sprintf(S, "X"); sprintf(D, "A"); break; case 0x1: sprintf(S, "X"); sprintf(D, "B"); break; case 0x2: sprintf(S, "Y"); sprintf(D, "A"); break; case 0x3: sprintf(S, "Y"); sprintf(D, "B"); break; } } static void decode_k_table(UINT16 k, char *Dnot) { switch(k) { case 0x0: sprintf(Dnot, "B"); break; case 0x1: sprintf(Dnot, "A"); break; } } static void decode_kSign_table(UINT16 k, char *plusMinus) { switch(k) { case 0x0: sprintf(plusMinus, "+"); break; case 0x1: sprintf(plusMinus, "-"); break; } } static void decode_KKK_table(UINT16 KKK, char *D1, char *D2) { /* TODO: Fix ^Fs */ switch(KKK) { case 0x0: sprintf(D1, "^F"); sprintf(D2, "X0"); break; case 0x1: sprintf(D1, "Y0"); sprintf(D2, "X0"); break; case 0x2: sprintf(D1, "X1"); sprintf(D2, "X0"); break; case 0x3: sprintf(D1, "Y1"); sprintf(D2, "X0"); break; case 0x4: sprintf(D1, "X0"); sprintf(D2, "X1"); break; case 0x5: sprintf(D1, "Y0"); sprintf(D2, "X1"); break; case 0x6: sprintf(D1, "^F"); sprintf(D2, "Y0"); break; case 0x7: sprintf(D1, "Y1"); sprintf(D2, "X1"); break; } } static int decode_NN_table(UINT16 NN) { return NN; } static int decode_TT_table(UINT16 TT) { return TT; } static void decode_QQF_table(UINT16 QQ, UINT16 F, char *S1, char *S2, char *D) { UINT16 switchVal = (QQ << 1) | F; switch(switchVal) { case 0x0: sprintf(S1, "X0"); sprintf(S2, "Y0"); sprintf(D, "A"); break; case 0x1: sprintf(S1, "X0"); sprintf(S2, "Y0"); sprintf(D, "B"); break; case 0x2: sprintf(S1, "X0"); sprintf(S2, "Y1"); sprintf(D, "A"); break; case 0x3: sprintf(S1, "X0"); sprintf(S2, "Y1"); sprintf(D, "B"); break; case 0x4: sprintf(S1, "X1"); sprintf(S2, "Y0"); sprintf(D, "A"); break; case 0x5: sprintf(S1, "X1"); sprintf(S2, "Y0"); sprintf(D, "B"); break; case 0x6: sprintf(S1, "X1"); sprintf(S2, "Y1"); sprintf(D, "A"); break; case 0x7: sprintf(S1, "X1"); sprintf(S2, "Y1"); sprintf(D, "B"); break; } } static void decode_QQF_special_table(UINT16 QQ, UINT16 F, char *S1, char *S2, char *D) { UINT16 switchVal = (QQ << 1) | F; switch(switchVal) { case 0x0: sprintf(S1, "Y0"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0x1: sprintf(S1, "Y0"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0x2: sprintf(S1, "Y1"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0x3: sprintf(S1, "Y1"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0x4: sprintf(S1, "X1"); sprintf(S2, "Y0"); sprintf(D, "A"); break; case 0x5: sprintf(S1, "X1"); sprintf(S2, "Y0"); sprintf(D, "B"); break; case 0x6: sprintf(S1, "X1"); sprintf(S2, "Y1"); sprintf(D, "A"); break; case 0x7: sprintf(S1, "X1"); sprintf(S2, "Y1"); sprintf(D, "B"); break; } } static void decode_QQQF_table(UINT16 QQQ, UINT16 F, char *S1, char *S2, char *D) { UINT16 switchVal = (QQQ << 1) | F; switch(switchVal) { case 0x0: sprintf(S1, "X0"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0x1: sprintf(S1, "X0"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0x2: sprintf(S1, "X1"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0x3: sprintf(S1, "X1"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0x4: sprintf(S1, "A1"); sprintf(S2, "Y0"); sprintf(D, "A"); break; case 0x5: sprintf(S1, "A1"); sprintf(S2, "Y0"); sprintf(D, "B"); break; case 0x6: sprintf(S1, "B1"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0x7: sprintf(S1, "B1"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0x8: sprintf(S1, "Y0"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0x9: sprintf(S1, "Y0"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0xa: sprintf(S1, "Y1"); sprintf(S2, "X0"); sprintf(D, "A"); break; case 0xb: sprintf(S1, "Y1"); sprintf(S2, "X0"); sprintf(D, "B"); break; case 0xc: sprintf(S1, "Y0"); sprintf(S2, "X1"); sprintf(D, "A"); break; case 0xd: sprintf(S1, "Y0"); sprintf(S2, "X1"); sprintf(D, "B"); break; case 0xe: sprintf(S1, "Y1"); sprintf(S2, "X1"); sprintf(D, "A"); break; case 0xf: sprintf(S1, "Y1"); sprintf(S2, "X1"); sprintf(D, "B"); break; } } static int decode_RR_table(UINT16 RR) { return RR; } static int decode_rr_table(UINT16 rr) { if (rr != 0x3) return rr; else return -1; } static void decode_s_table(UINT16 s, char *arithmetic) { switch(s) { case 0x0: sprintf(arithmetic, "su"); break; case 0x1: sprintf(arithmetic, "uu"); break; } } static void decode_ss_table(UINT16 ss, char *arithmetic) { switch(ss) { case 0x0: sprintf(arithmetic, "ss"); break; case 0x1: sprintf(arithmetic, "ss"); break; case 0x2: sprintf(arithmetic, "su"); break; case 0x3: sprintf(arithmetic, "uu"); break; } } static void decode_uuuuF_table(UINT16 uuuu, UINT16 F, char *arg, char *S, char *D) { UINT16 switchVal = (uuuu << 1) | F; /* An invalid uuuuF has been seen in the wild */ sprintf(D, "sub?"); sprintf(S, "add?"); sprintf(arg, "invalid"); switch(switchVal) { case 0x00: sprintf(arg, "add"); sprintf(S, "X0"); sprintf(D, "A"); break; case 0x08: sprintf(arg, "sub"); sprintf(S, "X0"); sprintf(D, "A"); break; case 0x01: sprintf(arg, "add"); sprintf(S, "X0"); sprintf(D, "B"); break; case 0x09: sprintf(arg, "sub"); sprintf(S, "X0"); sprintf(D, "B"); break; case 0x02: sprintf(arg, "add"); sprintf(S, "Y0"); sprintf(D, "A"); break; case 0x0a: sprintf(arg, "sub"); sprintf(S, "Y0"); sprintf(D, "A"); break; case 0x03: sprintf(arg, "add"); sprintf(S, "Y0"); sprintf(D, "B"); break; case 0x0b: sprintf(arg, "sub"); sprintf(S, "Y0"); sprintf(D, "B"); break; case 0x04: sprintf(arg, "add"); sprintf(S, "X1"); sprintf(D, "A"); break; case 0x0c: sprintf(arg, "sub"); sprintf(S, "X1"); sprintf(D, "A"); break; case 0x05: sprintf(arg, "add"); sprintf(S, "X1"); sprintf(D, "B"); break; case 0x0d: sprintf(arg, "sub"); sprintf(S, "X1"); sprintf(D, "B"); break; case 0x06: sprintf(arg, "add"); sprintf(S, "Y1"); sprintf(D, "A"); break; case 0x0e: sprintf(arg, "sub"); sprintf(S, "Y1"); sprintf(D, "A"); break; case 0x07: sprintf(arg, "add"); sprintf(S, "Y1"); sprintf(D, "B"); break; case 0x0f: sprintf(arg, "sub"); sprintf(S, "Y1"); sprintf(D, "B"); break; case 0x18: sprintf(arg, "add"); sprintf(S, "B") ; sprintf(D, "A"); break; case 0x1a: sprintf(arg, "sub"); sprintf(S, "B") ; sprintf(D, "A"); break; case 0x19: sprintf(arg, "add"); sprintf(S, "A") ; sprintf(D, "B"); break; case 0x1b: sprintf(arg, "sub"); sprintf(S, "A") ; sprintf(D, "B"); break; } } static void decode_Z_table(UINT16 Z, char *ea) { /* This is fixed as per the Family Manual errata addendum */ switch(Z) { case 0x1: sprintf(ea, "(A1)"); break; case 0x0: sprintf(ea, "(B1)"); break; } } static void assemble_ea_from_m_table(UINT16 m, int n, char *ea) { switch(m) { case 0x0: sprintf(ea, "(R%d)+",n) ; break; case 0x1: sprintf(ea, "(R%d)+N%d", n, n); break; } } static void assemble_eas_from_m_table(UINT16 mm, int n1, int n2, char *ea1, char *ea2) { switch(mm) { case 0x0: sprintf(ea1, "(R%d)+", n1) ; sprintf(ea2, "(R%d)+", n2) ; break; case 0x1: sprintf(ea1, "(R%d)+", n1) ; sprintf(ea2, "(R%d)+N%d", n2, n2); break; case 0x2: sprintf(ea1, "(R%d)+N%d", n1, n1); sprintf(ea2, "(R%d)+", n2) ; break; case 0x3: sprintf(ea1, "(R%d)+N%d", n1, n1); sprintf(ea2, "(R%d)+N%d", n2, n2); break; } } static void assemble_ea_from_MM_table(UINT16 MM, int n, char *ea) { switch(MM) { case 0x0: sprintf(ea, "(R%d)", n) ; break; case 0x1: sprintf(ea, "(R%d)+", n) ; break; case 0x2: sprintf(ea, "(R%d)-", n) ; break; case 0x3: sprintf(ea, "(R%d)+N%d", n, n); break; } } static void assemble_ea_from_q_table(UINT16 q, int n, char *ea) { switch(q) { case 0x0: sprintf(ea, "(R%d+N%d)", n, n); break; case 0x1: sprintf(ea, "-(R%d)", n) ; break; } } static void assemble_ea_from_t_table(UINT16 t, UINT16 val, char *ea) { switch(t) { /* !!! Looking at page 336 of UM, I'm not sure if 0 is X: or if 0 is just # !!! */ case 0x0: sprintf(ea, "X:%04x", val); break; case 0x1: sprintf(ea, "#%04x", val); break; } } static void assemble_ea_from_z_table(UINT16 z, int n, char *ea) { switch(z) { case 0x0: sprintf(ea, "(R%d)-", n) ; break; case 0x1: sprintf(ea, "(R%d)+N%d", n, n); break; } } static void assemble_D_from_P_table(UINT16 P, UINT16 ppppp, char *D) { char fullAddy[128]; /* Convert Short Absolute Address to full 16-bit */ switch(P) { case 0x0: sprintf(D, "X:%02x", ppppp); break; case 0x1: assemble_address_from_IO_short_address(ppppp, fullAddy); sprintf(D, "X:%02x (%s)", ppppp, fullAddy); break; } } static void assemble_arguments_from_W_table(UINT16 W, char *args, char ma, char *SD, char *ea) { switch(W) { case 0x0: sprintf(args, "%s,%c:%s", SD, ma, ea); break; case 0x1: sprintf(args, "%c:%s,%s", ma, ea, SD); break; } } static void assemble_reg_from_W_table(UINT16 W, char *args, char ma, char *SD, INT8 xx) { /* TODO : xx is said to be signed on page A-139. Nowhere else. Are they all signed? */ switch(W) { case 0x0: sprintf(args, "%s,%c:(R2+%02x)", SD, ma, xx); break; case 0x1: sprintf(args, "%c:(R2+%02x),%s", ma, xx, SD); break; } } static void assemble_address_from_IO_short_address(UINT16 pp, char *ea) { UINT16 fullAddy = 0xffe0; fullAddy |= pp; sprintf(ea, "%.04x", fullAddy); } static INT8 get_6_bit_signed_value(UINT16 bits) { UINT16 fullAddy = bits; if (fullAddy & 0x0020) fullAddy |= 0xffc0; return (INT8)fullAddy; } /********************/ /* HELPER FUNCTIONS */ /********************/ static UINT16 dsp56k_op_mask(UINT16 cur, UINT16 mask) { int i; UINT16 retVal = (cur & mask); UINT16 temp = 0x0000; int offsetCount = 0; /* Shift everything right, eliminating 'whitespace'... */ for (i = 0; i < 16; i++) { if (mask & (0x1<> i) & 0x1) << offsetCount); offsetCount++; } } return temp; } static void pad_string(const int dest_length, char* string) { while (strlen(string) < dest_length) { strcat(string, " "); } }