diff --git a/Source/Plugins/Plugin_DSP_LLE/Src/DSPInterpreter.cpp b/Source/Plugins/Plugin_DSP_LLE/Src/DSPInterpreter.cpp index 95da543254..2740cec3bd 100644 --- a/Source/Plugins/Plugin_DSP_LLE/Src/DSPInterpreter.cpp +++ b/Source/Plugins/Plugin_DSP_LLE/Src/DSPInterpreter.cpp @@ -589,14 +589,21 @@ void mulc(const UDSPInstruction& opc) Update_SR_Register64(prod); } - +// MULCMVZ +// 110s t01r xxxx xxxx +// (fixed possible bug in duddie's description, s->t) +// Multiply mid part of accumulator register $acS.m by high part $axT.h of +// secondary accumulator $axT (treat them both as signed). Move product +// register before multiplication to accumulator $acR, set low part of +// accumulator $acR.l to zero. void mulcmvz(const UDSPInstruction& opc) { s64 TempProd = dsp_get_long_prod(); // update prod u8 sreg = (opc.hex >> 12) & 0x1; - s64 Prod = (s64)dsp_get_acc_m(sreg) * (s64)dsp_get_acc_h(sreg) * GetMultiplyModifier(); + u8 treg = (opc.hex >> 11) & 0x1; + s64 Prod = (s64)dsp_get_acc_m(sreg) * (s64)dsp_get_ax_h(treg) * GetMultiplyModifier(); dsp_set_long_prod(Prod); // update acc @@ -607,13 +614,19 @@ void mulcmvz(const UDSPInstruction& opc) Update_SR_Register64(acc); } +// MULCMV +// 110s t11r xxxx xxxx +// Multiply mid part of accumulator register $acS.m by high part $axS.h of +// secondary accumulator $axT (treat them both as signed). Move product +// register before multiplication to accumulator $acR. void mulcmv(const UDSPInstruction& opc) { s64 TempProd = dsp_get_long_prod(); // update prod u8 sreg = (opc.hex >> 12) & 0x1; - s64 Prod = (s64)dsp_get_acc_m(sreg) * (s64)dsp_get_acc_h(sreg) * GetMultiplyModifier(); + u8 treg = (opc.hex >> 11) & 0x1; + s64 Prod = (s64)dsp_get_acc_m(sreg) * (s64)dsp_get_ax_h(sreg) * GetMultiplyModifier(); dsp_set_long_prod(Prod); // update acc @@ -623,6 +636,8 @@ void mulcmv(const UDSPInstruction& opc) Update_SR_Register64(TempProd); } +// CMPAR +// Not described by Duddie's doc - at least not as a separate instruction. void cmpar(const UDSPInstruction& opc) { u8 rreg = ((opc.hex >> 12) & 0x1) + 0x1a; @@ -637,6 +652,9 @@ void cmpar(const UDSPInstruction& opc) Update_SR_Register64(ar - rr); } +// CMP +// 1000 0010 xxxx xxxx +// Compares accumulator $ac0 with accumulator $ac1. void cmp(const UDSPInstruction& opc) { s64 acc0 = dsp_get_long_acc(0); @@ -645,6 +663,9 @@ void cmp(const UDSPInstruction& opc) Update_SR_Register64(acc0 - acc1); } +// TST +// 1011 r001 xxxx xxxx +// Test accumulator %acR. void tst(const UDSPInstruction& opc) { tsta((opc.hex >> 11) & 0x1); @@ -679,18 +700,24 @@ void addarn(const UDSPInstruction& opc) g_dsp.r[dreg] += (s16)g_dsp.r[DSP_REG_IX0 + sreg]; } +// MULCAC $acS.m, $axT.h, $acR +// 110s t10r xxxx xxxx +// Multiply mid part of accumulator register $acS.m by high part $axS.h of +// secondary accumulator $axS (treat them both as signed). Add product +// register before multiplication to accumulator $acR. void mulcac(const UDSPInstruction& opc) { s64 TempProd = dsp_get_long_prod(); // update prod u8 sreg = (opc.hex >> 12) & 0x1; - s64 Prod = (s64)dsp_get_acc_m(sreg) * (s64)dsp_get_acc_h(sreg) * GetMultiplyModifier(); + u8 treg = (opc.hex >> 11) & 0x1; + s64 Prod = (s64)dsp_get_acc_m(sreg) * (s64)dsp_get_ax_h(treg) * GetMultiplyModifier(); dsp_set_long_prod(Prod); // update acc u8 rreg = (opc.hex >> 8) & 0x1; - s64 acc = TempProd + g_dsp.r[rreg]; + s64 acc = TempProd + dsp_get_long_acc(rreg); dsp_set_long_acc(rreg, acc); Update_SR_Register64(acc); diff --git a/Source/Plugins/Plugin_DSP_LLE/Src/DSPTables.cpp b/Source/Plugins/Plugin_DSP_LLE/Src/DSPTables.cpp index 971121e6cd..f345a0847c 100644 --- a/Source/Plugins/Plugin_DSP_LLE/Src/DSPTables.cpp +++ b/Source/Plugins/Plugin_DSP_LLE/Src/DSPTables.cpp @@ -275,17 +275,15 @@ DSPOPCTemplate opcodes[] = {"MULXAC", 0xa400, 0xe6ff, DSPInterpreter::mulxac, nop, 1 | P_EXT, 3, {{P_REGM18, 1, 0, 11, 0x1000}, {P_REGM19, 1, 0, 10, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, {"MULXMV", 0xa600, 0xe6ff, DSPInterpreter::mulxmv, nop, 1 | P_EXT, 3, {{P_REGM18, 1, 0, 11, 0x1000}, {P_REGM19, 1, 0, 10, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, - {"MUL", 0x9000, 0xf7ff, DSPInterpreter::mul, nop, 1 | P_EXT, 2, {{P_REG18, 1, 0, 11, 0x0800}, {P_REG1A, 1, 0, 11, 0x0800}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, {"MULMVZ", 0x9200, 0xf6ff, DSPInterpreter::mulmvz, nop, 1 | P_EXT, 3, {{P_REG18, 1, 0, 11, 0x0800}, {P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, {"MULAC", 0x9400, 0xf6ff, DSPInterpreter::mulac, nop, 1 | P_EXT, 3, {{P_REG18, 1, 0, 11, 0x0800}, {P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, {"MULMV", 0x9600, 0xf6ff, DSPInterpreter::mulmv, nop, 1 | P_EXT, 3, {{P_REG18, 1, 0, 11, 0x0800}, {P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, - - {"MULC", 0xc000, 0xe7ff, DSPInterpreter::mulc, nop, 1 | P_EXT, 2, {{P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 12, 0x1000}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, - {"MULCMVZ", 0xc200, 0xe6ff, DSPInterpreter::mulcmvz, nop, 1 | P_EXT, 3, {{P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 12, 0x1000}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, - {"MULCAC", 0xc400, 0xe6ff, DSPInterpreter::mulcac, nop, 1 | P_EXT, 3, {{P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 12, 0x1000}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, - {"MULCMV", 0xc600, 0xe6ff, DSPInterpreter::mulcmv, nop, 1 | P_EXT, 3, {{P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 12, 0x1000}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, + {"MULC", 0xc000, 0xe7ff, DSPInterpreter::mulc, nop, 1 | P_EXT, 2, {{P_ACCM, 1, 0, 12, 0x1000}, {P_REG1A, 1, 0, 11, 0x0800}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, + {"MULCMVZ", 0xc200, 0xe6ff, DSPInterpreter::mulcmvz, nop, 1 | P_EXT, 3, {{P_ACCM, 1, 0, 12, 0x1000}, {P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, + {"MULCAC", 0xc400, 0xe6ff, DSPInterpreter::mulcac, nop, 1 | P_EXT, 3, {{P_ACCM, 1, 0, 12, 0x1000}, {P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, + {"MULCMV", 0xc600, 0xe6ff, DSPInterpreter::mulcmv, nop, 1 | P_EXT, 3, {{P_ACCM, 1, 0, 12, 0x1000}, {P_REG1A, 1, 0, 11, 0x0800}, {P_ACCM, 1, 0, 8, 0x0100}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, {"ADDR", 0x4000, 0xf8ff, DSPInterpreter::addr, nop, 1 | P_EXT, 2, {{P_ACCM, 1, 0, 8, 0x0100}, {P_REG18, 1, 0, 9, 0x0600}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, {"ADDAX", 0x4800, 0xfcff, DSPInterpreter::addax, nop, 1 | P_EXT, 2, {{P_ACCM, 1, 0, 8, 0x0100}, {P_REG18, 1, 0, 9, 0x0200}}, dsp_op_ext_ops_pro, dsp_op_ext_ops_epi}, diff --git a/Source/Plugins/Plugin_DSP_LLE/Src/Tools.cpp b/Source/Plugins/Plugin_DSP_LLE/Src/Tools.cpp index b497eb8e5c..9dcf2c9f46 100644 --- a/Source/Plugins/Plugin_DSP_LLE/Src/Tools.cpp +++ b/Source/Plugins/Plugin_DSP_LLE/Src/Tools.cpp @@ -61,6 +61,12 @@ bool DisasmUCodeDump(u32 crc) if (t != NULL) { gd_globals_t gdg; + memset(&gdg, 0, sizeof(gdg)); + gdg.show_hex = true; + gdg.show_pc = true; + gdg.ext_separator = '\t'; + gdg.decode_names = true; + gdg.decode_registers = true; gd_dis_file(&gdg, binFile, t); fclose(t); return true; @@ -88,7 +94,7 @@ u32 GenerateCRC(const unsigned char* _pBuffer, int _pLength) CRC = (CRC >> 8) ^ Temp; } - return(CRC ^ 0xFFFFFFFF); + return CRC ^ 0xFFFFFFFF; } // TODO make this useful :p diff --git a/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.cpp b/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.cpp index 52746e246f..6cabd4ed2c 100644 --- a/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.cpp +++ b/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.cpp @@ -96,14 +96,14 @@ const pdlabel_t pdlabels[] = pdlabel_t regnames[] = { - {0x00, "R00", "Register 00",}, - {0x01, "R01", "Register 01",}, - {0x02, "R02", "Register 02",}, - {0x03, "R03", "Register 03",}, - {0x04, "R04", "Register 04",}, - {0x05, "R05", "Register 05",}, - {0x06, "R06", "Register 06",}, - {0x07, "R07", "Register 07",}, + {0x00, "AR0", "Register 00",}, + {0x01, "AR1", "Register 01",}, + {0x02, "AR2", "Register 02",}, + {0x03, "AR3", "Register 03",}, + {0x04, "IX0", "Register 04",}, + {0x05, "IX1", "Register 05",}, + {0x06, "IX2", "Register 06",}, + {0x07, "IX3", "Register 07",}, {0x08, "R08", "Register 08",}, {0x09, "R09", "Register 09",}, {0x0a, "R10", "Register 10",}, @@ -112,8 +112,8 @@ pdlabel_t regnames[] = {0x0d, "ST1", "Data stack",}, {0x0e, "ST2", "Loop addr stack",}, {0x0f, "ST3", "Loop counter",}, - {0x00, "ACH0", "Accu High 0",}, - {0x11, "ACH1", "Accu High 1",}, + {0x00, "AC0.H", "Accu High 0",}, + {0x11, "AC1.H", "Accu High 1",}, {0x12, "CR", "Config Register",}, {0x13, "SR", "Special Register",}, {0x14, "PROD.L", "Prod L",}, @@ -250,15 +250,6 @@ char* gd_dis_params(gd_globals_t* gdg, const DSPOPCTemplate* opc, u16 op1, u16 o return strbuf; } - -gd_globals_t* gd_init() -{ - gd_globals_t* gdg = (gd_globals_t*)malloc(sizeof(gd_globals_t)); - memset(gdg, 0, sizeof(gd_globals_t)); - return(gdg); -} - - u16 gd_dis_get_opcode_size(gd_globals_t* gdg) { DSPOPCTemplate* opc = 0; diff --git a/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.h b/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.h index 7d0c47c97c..07e59a95d4 100644 --- a/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.h +++ b/Source/Plugins/Plugin_DSP_LLE/Src/disassemble.h @@ -27,7 +27,7 @@ #include "Common.h" -typedef struct gd_globals_t +struct gd_globals_t { bool print_tabs; bool show_hex; @@ -40,7 +40,7 @@ typedef struct gd_globals_t char* buffer; u16 buffer_size; char ext_separator; -} gd_globals_t; +}; char* gd_dis_opcode(gd_globals_t* gdg); diff --git a/Source/Plugins/Plugin_DSP_LLE/Src/gdsp_interpreter.cpp b/Source/Plugins/Plugin_DSP_LLE/Src/gdsp_interpreter.cpp index 2aa91cc184..029f36111e 100644 --- a/Source/Plugins/Plugin_DSP_LLE/Src/gdsp_interpreter.cpp +++ b/Source/Plugins/Plugin_DSP_LLE/Src/gdsp_interpreter.cpp @@ -371,4 +371,3 @@ void gdsp_stop() { gdsp_running = false; } -