From 78857ddc5fc65e5537cce66cf48e318b1f239c30 Mon Sep 17 00:00:00 2001 From: AJR Date: Sat, 28 Oct 2023 20:15:48 -0400 Subject: ks0164: CPU refinements - Force source register to be the same as destination register for max/min instructions. Fixes missing instruments and eventually disappearing music in elfin attract. - Write "tst" instead of "zero |=" in disassembly --- src/devices/cpu/ks0164/ks0164.cpp | 12 ++++++------ src/devices/cpu/ks0164/ks0164d.cpp | 20 ++++++++++++++++---- 2 files changed, 22 insertions(+), 10 deletions(-) diff --git a/src/devices/cpu/ks0164/ks0164.cpp b/src/devices/cpu/ks0164/ks0164.cpp index 194823474d0..87a361d3e8b 100644 --- a/src/devices/cpu/ks0164/ks0164.cpp +++ b/src/devices/cpu/ks0164/ks0164.cpp @@ -335,16 +335,16 @@ void ks0164_cpu_device::execute_run() case 1: { // Min/max with immediate - // 1101 Mrrr Ssss 1000 - u16 v1 = m_r[(opcode >> 4) & 7]; + // 1101 Mrrr S000 1000 + u16 v1 = m_r[(opcode >> 8) & 7]; u16 v2 = m_program_cache.read_word(m_r[R_PC]); m_r[R_PC] += 2; u16 res; switch(bitswap<2>(opcode, 11, 7)) { - case 0: res = v1 > v2 ? v1 : v2; break; - case 1: res = s16(v1) > s16(v2) ? v1 : v2; break; - case 2: res = v1 < v2 ? v1 : v2; break; - case 3: default: res = s16(v1) < s16(v2) ? v1 : v2; break; + case 0: res = std::max(v1, v2); break; + case 1: res = std::max(v1, v2); break; + case 2: res = std::min(v1, v2); break; + case 3: default: res = std::min(v1, v2); break; } m_r[(opcode >> 8) & 7] = res; break; diff --git a/src/devices/cpu/ks0164/ks0164d.cpp b/src/devices/cpu/ks0164/ks0164d.cpp index 192dc7d1221..a7b507e53e1 100644 --- a/src/devices/cpu/ks0164/ks0164d.cpp +++ b/src/devices/cpu/ks0164/ks0164d.cpp @@ -65,6 +65,9 @@ const ks0164_disassembler::instruction ks0164_disassembler::instructions[] { { 0x9804, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= %s.bu", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0x9884, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= %s.bs", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0x980c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= %s", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, + { 0xa704, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst %s.bu", regs[(opcode >> 4) & 7]); return 2; } }, + { 0xa784, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst %s.bs", regs[(opcode >> 4) & 7]); return 2; } }, + { 0xa70c, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst %s", regs[(opcode >> 4) & 7]); return 2; } }, { 0xa004, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= %s.bu", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0xa084, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= %s.bs", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0xa00c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= %s", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, @@ -108,6 +111,9 @@ const ks0164_disassembler::instruction ks0164_disassembler::instructions[] { { 0x9806, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= (%s).bu", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0x9886, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= (%s).bs", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0x980e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= (%s).w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, + { 0xa706, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst (%s).bu", regs[(opcode >> 4) & 7]); return 2; } }, + { 0xa786, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst (%s).bs", regs[(opcode >> 4) & 7]); return 2; } }, + { 0xa70e, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst (%s).w", regs[(opcode >> 4) & 7]); return 2; } }, { 0xa006, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= (%s).bu", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0xa086, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= (%s).bs", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, { 0xa00e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= (%s).w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } }, @@ -133,6 +139,9 @@ const ks0164_disassembler::instruction ks0164_disassembler::instructions[] { { 0x9877, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s &= (%04x).bu", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, { 0x98f7, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s &= (%04x).bs", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, { 0x987f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s &= (%04x).w", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, + { 0xa777, 0xffff, [](P) -> u32 { util::stream_format(stream, "tst (%04x).bu", opcodes.r16(pc+2)); return 4; } }, + { 0xa7f7, 0xffff, [](P) -> u32 { util::stream_format(stream, "tst (%04x).bs", opcodes.r16(pc+2)); return 4; } }, + { 0xa77f, 0xffff, [](P) -> u32 { util::stream_format(stream, "tst (%04x).w", opcodes.r16(pc+2)); return 4; } }, { 0xa077, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s |= (%04x).bu", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, { 0xa0f7, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s |= (%04x).bs", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, { 0xa07f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s |= (%04x).w", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, @@ -158,6 +167,9 @@ const ks0164_disassembler::instruction ks0164_disassembler::instructions[] { { 0x9807, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= (%s%s).bu", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, { 0x9887, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= (%s%s).bs", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, { 0x980f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s &= (%s%s).w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, + { 0xa707, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst (%s%s).bu", regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, + { 0xa787, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst (%s%s).bs", regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, + { 0xa70f, 0xff8f, [](P) -> u32 { util::stream_format(stream, "tst (%s%s).w", regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, { 0xa007, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= (%s%s).bu", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, { 0xa087, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= (%s%s).bs", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, { 0xa00f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s |= (%s%s).w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } }, @@ -186,10 +198,10 @@ const ks0164_disassembler::instruction ks0164_disassembler::instructions[] { { 0xc007, 0xf807, [](P) -> u32 { util::stream_format(stream, "%s <> 8) & 7], (opcode >> 4) & 0xf); return 2; } }, { 0xc807, 0xf807, [](P) -> u32 { util::stream_format(stream, "%s >>c= %x", regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } }, - { 0xd008, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s = maxu(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], opcodes.r16(pc+2)); return 4; } }, - { 0xd808, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s = minu(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], opcodes.r16(pc+2)); return 4; } }, - { 0xd088, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s = maxs(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], opcodes.r16(pc+2)); return 4; } }, - { 0xd888, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s = mins(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], opcodes.r16(pc+2)); return 4; } }, + { 0xd008, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s = maxu(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, + { 0xd808, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s = minu(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, + { 0xd088, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s = maxs(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, + { 0xd888, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s = mins(%s, %04x)", regs[(opcode >> 8) & 7], regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } }, { 0xd001, 0xffff, [](P) -> u32 { util::stream_format(stream, "jmp %04x", opcodes.r16(pc+2)); return 4; } }, { 0xd002, 0xffff, [](P) -> u32 { util::stream_format(stream, "jsr %04x", opcodes.r16(pc+2)); return 4 | STEP_OVER; } }, { 0xd003, 0xffff, [](P) -> u32 { util::stream_format(stream, "rts"); return 2 | STEP_OUT; } }, -- cgit v1.2.3