create derived 6502 type for XaviX because it has at least one custom… (#3154)

* create derived 6502 type for XaviX because it has at least one custom 4-byte opcode that doesn't fit any other type.
treating that opcode as NOP for now.

have a feeling it might be something to do with the other integrated hardware, might be 'execute co-processor code chain at this address' or something similar
It isn't a standard JSL (Jump Subroutine Long)  like the SNES cpu opcode in the same place as this, it seems to point at some code-like structures tho)
could also be a secondary operation mode with different encoding like ARM's Thumb mode tho I guess.

We currently only have a single XaviX based dump (taitons1) but there are more on the way.  I'm going to see if the code flow makes any sense at all with these missing, or if any of it gives a clue as to what they should actually do.

* xavix - let's call these callf and retf then

after further investigation these are some kind of extra 'long jump' subroutine / task handlers, the 0x80 also being a custom opcode was throwing me off trying to identify them before.

looks like they might have been hacking 65816 features into the regular 6502 core?

* prepare for extra address bits (nw)

* better program flow (nw)
This commit is contained in:
David Haywood 2018-02-02 19:34:12 +00:00 committed by R. Belmont
parent f33b1e3619
commit 1e09ab0ceb
11 changed files with 308 additions and 7 deletions

View File

@ -1331,6 +1331,7 @@ end
--@src/devices/cpu/m6502/m740.h,CPUS["M6502"] = true
--@src/devices/cpu/m6502/m3745x.h,CPUS["M6502"] = true
--@src/devices/cpu/m6502/m5074x.h,CPUS["M6502"] = true
--@src/devices/cpu/m6502/xavix.h,CPUS["XAVIX"] = true
--------------------------------------------------
@ -1372,6 +1373,8 @@ if (CPUS["M6502"]~=null) then
MAME_DIR .. "src/devices/cpu/m6502/m3745x.h",
MAME_DIR .. "src/devices/cpu/m6502/m5074x.cpp",
MAME_DIR .. "src/devices/cpu/m6502/m5074x.h",
MAME_DIR .. "src/devices/cpu/m6502/xavix.cpp",
MAME_DIR .. "src/devices/cpu/m6502/xavix.h",
}
custombuildtask {
@ -1385,6 +1388,7 @@ if (CPUS["M6502"]~=null) then
{ MAME_DIR .. "src/devices/cpu/m6502/on2a03.lst", GEN_DIR .. "emu/cpu/m6502/n2a03.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dn2a03.lst" }, {"@echo Generating n2a03 disassembler source file...", PYTHON .. " $(1) s n2a03 $(<) $(2) $(@)" }},
{ MAME_DIR .. "src/devices/cpu/m6502/om740.lst" , GEN_DIR .. "emu/cpu/m6502/m740.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm740.lst" }, {"@echo Generating m740 disassembler source file...", PYTHON .. " $(1) s m740 $(<) $(2) $(@)" }},
{ MAME_DIR .. "src/devices/cpu/m6502/dr65c02.lst", GEN_DIR .. "emu/cpu/m6502/r65c02.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", }, {"@echo Generating r65c02 disassembler source file...", PYTHON .. " $(1) s r65c02 - $(<) $(@)" }},
{ MAME_DIR .. "src/devices/cpu/m6502/oxavix.lst", GEN_DIR .. "emu/cpu/m6502/xavix.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dxavix.lst" }, {"@echo Generating xavix disassembler source file...", PYTHON .. " $(1) s xavix $(<) $(2) $(@)" }},
}
dependency {
@ -1398,6 +1402,7 @@ if (CPUS["M6502"]~=null) then
{ MAME_DIR .. "src/devices/cpu/m6502/n2a03.cpp", GEN_DIR .. "emu/cpu/m6502/n2a03.hxx" },
{ MAME_DIR .. "src/devices/cpu/m6502/r65c02.cpp", GEN_DIR .. "emu/cpu/m6502/r65c02.hxx" },
{ MAME_DIR .. "src/devices/cpu/m6502/m740.cpp", GEN_DIR .. "emu/cpu/m6502/m740.hxx" },
{ MAME_DIR .. "src/devices/cpu/m6502/xavix.cpp", GEN_DIR .. "emu/cpu/m6502/xavix.hxx" },
}
end
@ -1412,7 +1417,8 @@ if (CPUS["M6502"]~=null or _OPTIONS["with-tools"]) then
table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/on2a03.lst", GEN_DIR .. "emu/cpu/m6502/n2a03d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dn2a03.lst" }, {"@echo Generating n2a03 disassembler source file...", PYTHON .. " $(1) d n2a03 $(<) $(2) $(@)" }})
table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om740.lst" , GEN_DIR .. "emu/cpu/m6502/m740d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm740.lst" }, {"@echo Generating m740 disassembler source file...", PYTHON .. " $(1) d m740 $(<) $(2) $(@)" }})
table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/dr65c02.lst", GEN_DIR .. "emu/cpu/m6502/r65c02d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", }, {"@echo Generating r65c02 disassembler source file...", PYTHON .. " $(1) d r65c02 - $(<) $(@)" }})
table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/oxavix.lst", GEN_DIR .. "emu/cpu/m6502/xavixd.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dxavix.lst" }, {"@echo Generating xavix disassembler source file...", PYTHON .. " $(1) d xavix $(<) $(2) $(@)" }})
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/deco16d.cpp", GEN_DIR .. "emu/cpu/m6502/deco16d.hxx" })
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m4510d.cpp", GEN_DIR .. "emu/cpu/m6502/m4510d.hxx" })
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m6502d.cpp", GEN_DIR .. "emu/cpu/m6502/m6502d.hxx" })
@ -1423,6 +1429,7 @@ if (CPUS["M6502"]~=null or _OPTIONS["with-tools"]) then
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/n2a03d.cpp", GEN_DIR .. "emu/cpu/m6502/n2a03d.hxx" })
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/r65c02d.cpp", GEN_DIR .. "emu/cpu/m6502/r65c02d.hxx" })
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m740d.cpp", GEN_DIR .. "emu/cpu/m6502/m740d.hxx" })
table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/xavixd.cpp", GEN_DIR .. "emu/cpu/m6502/xavixd.hxx" })
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/deco16d.cpp")
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/deco16d.h")
@ -1444,6 +1451,8 @@ if (CPUS["M6502"]~=null or _OPTIONS["with-tools"]) then
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/n2a03d.h")
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/r65c02d.cpp")
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/r65c02d.h")
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/xavixd.cpp")
table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/xavixd.h")
end
--------------------------------------------------

View File

@ -0,0 +1,20 @@
# license:BSD-3-Clause
# copyright-holders:David Haywood
# xavix - m6502 with custom opcodes
brk_imp ora_idx kil_non slo_idx nop_zpg ora_zpg asl_zpg slo_zpg php_imp ora_imm asl_acc anc_imm nop_aba ora_aba asl_aba slo_aba
bpl_rel ora_idy kil_non slo_idy nop_zpx ora_zpx asl_zpx slo_zpx clc_imp ora_aby nop_imp slo_aby nop_abx ora_abx asl_abx slo_abx
jsr_adr and_idx callf_xa3 rla_idx bit_zpg and_zpg rol_zpg rla_zpg plp_imp and_imm rol_acc anc_imm bit_aba and_aba rol_aba rla_aba
bmi_rel and_idy kil_non rla_idy nop_zpx and_zpx rol_zpx rla_zpx sec_imp and_aby nop_imp rla_aby nop_abx and_abx rol_abx rla_abx
rti_imp eor_idx kil_non sre_idx nop_zpg eor_zpg lsr_zpg sre_zpg pha_imp eor_imm lsr_acc asr_imm jmp_adr eor_aba lsr_aba sre_aba
bvc_rel eor_idy kil_non sre_idy nop_zpx eor_zpx lsr_zpx sre_zpx cli_imp eor_aby nop_imp sre_aby nop_abx eor_abx lsr_abx sre_abx
rts_imp adc_idx kil_non rra_idx nop_zpg adc_zpg ror_zpg rra_zpg pla_imp adc_imm ror_acc arr_imm jmp_ind adc_aba ror_aba rra_aba
bvs_rel adc_idy kil_non rra_idy nop_zpx adc_zpx ror_zpx rra_zpx sei_imp adc_aby nop_imp rra_aby nop_abx adc_abx ror_abx rra_abx
retf_imp sta_idx nop_imm sax_idx sty_zpg sta_zpg stx_zpg sax_zpg dey_imp nop_imm txa_imp ane_imm sty_aba sta_aba stx_aba sax_aba
bcc_rel sta_idy kil_non sha_idy sty_zpx sta_zpx stx_zpy sax_zpy tya_imp sta_aby txs_imp shs_aby shy_abx sta_abx shx_aby sha_aby
ldy_imm lda_idx ldx_imm lax_idx ldy_zpg lda_zpg ldx_zpg lax_zpg tay_imp lda_imm tax_imp lxa_imm ldy_aba lda_aba ldx_aba lax_aba
bcs_rel lda_idy kil_non lax_idy ldy_zpx lda_zpx ldx_zpy lax_zpy clv_imp lda_aby tsx_imp las_aby ldy_abx lda_abx ldx_aby lax_aby
cpy_imm cmp_idx nop_imm dcp_idx cpy_zpg cmp_zpg dec_zpg dcp_zpg iny_imp cmp_imm dex_imp sbx_imm cpy_aba cmp_aba dec_aba dcp_aba
bne_rel cmp_idy kil_non dcp_idy nop_zpx cmp_zpx dec_zpx dcp_zpx cld_imp cmp_aby nop_imp dcp_aby nop_abx cmp_abx dec_abx dcp_abx
cpx_imm sbc_idx nop_imm isb_idx cpx_zpg sbc_zpg inc_zpg isb_zpg inx_imp sbc_imm nop_imp sbc_imm cpx_aba sbc_aba inc_aba isb_aba
beq_rel sbc_idy kil_non isb_idy nop_zpx sbc_zpx inc_zpx isb_zpx sed_imp sbc_aby nop_imp isb_aby nop_abx sbc_abx inc_abx isb_abx
reset

View File

@ -181,6 +181,11 @@ offs_t m6502_base_disassembler::disassemble(std::ostream &stream, offs_t pc, con
flags |= 1;
break;
case DASM_xa3:
util::stream_format(stream, " #$%02x%02x%02x", params.r8(pc+1), params.r8(pc+3), params.r8(pc+2));
flags |= 4;
break;
default:
fprintf(stderr, "Unhandled dasm mode %d\n", e.mode);
abort();

View File

@ -59,7 +59,8 @@ protected:
DASM_biz, /* bit, zero page (M740) */
DASM_bzr, /* bit, zero page, relative offset (M740) */
DASM_bar, /* bit, accumulator, relative offset (M740) */
DASM_bac /* bit, accumulator (M740) */
DASM_bac, /* bit, accumulator (M740) */
DASM_xa3 /* unknown XaviX opcode, 24-bit ROM pointer? */
};
virtual u32 get_instruction_bank() const;

View File

@ -0,0 +1,30 @@
# license:BSD-3-Clause
# copyright-holders:David Haywood
# xavix opcodes
callf_xa3
TMP2 = read_pc();
TMP = read_pc();
TMP |= (read_pc()<<8);
read(SP);
write(SP, PC>>8);
dec_SP();
write(SP, PC);
dec_SP();
write(SP, m_farbank);
dec_SP();
m_farbank=TMP2;
PC = TMP;
prefetch();
retf_imp
read_pc_noinc();
read(SP);
inc_SP();
TMP2 = read(SP);
inc_SP();
PC = read(SP);
inc_SP();
PC = set_h(PC, read(SP));
m_farbank = TMP2;
prefetch();

View File

@ -0,0 +1,125 @@
// license:BSD-3-Clause
// copyright-holders:David Haywood
/***************************************************************************
xavix.c
6502 with custom opcodes
integrated gfx / sound / coprocessor?
***************************************************************************/
#include "emu.h"
#include "xavix.h"
#include "xavixd.h"
DEFINE_DEVICE_TYPE(XAVIX, xavix_device, "xavix", "XaviX")
xavix_device::xavix_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
m6502_device(mconfig, XAVIX, tag, owner, clock),
XPC(0)
{
program_config.m_addr_width = 24;
program_config.m_logaddr_width = 24;
sprogram_config.m_addr_width = 24;
sprogram_config.m_logaddr_width = 24;
}
util::disasm_interface *xavix_device::create_disassembler()
{
return new xavix_disassembler;
}
void xavix_device::device_start()
{
if(direct_disabled)
mintf = std::make_unique<mi_xavix_nd>(this);
else
mintf = std::make_unique<mi_xavix_normal>(this);
init();
state_add(STATE_GENPC, "GENPC", XPC).callexport().noshow();
state_add(STATE_GENPCBASE, "CURPC", XPC).callexport().noshow();
}
void xavix_device::state_export(const device_state_entry &entry)
{
switch(entry.index()) {
case STATE_GENPC:
case STATE_GENPCBASE:
XPC = adr_with_bank(NPC);
break;
}
}
void xavix_device::device_reset()
{
m_farbank = 0;
XPC = 0;
m6502_device::device_reset();
}
xavix_device::mi_xavix_normal::mi_xavix_normal(xavix_device *_base)
{
base = _base;
}
uint8_t xavix_device::mi_xavix_normal::read(uint16_t adr)
{
if (adr < 0x8000)
return program->read_byte(adr);
else
return program->read_byte(base->adr_with_bank(adr));
}
uint8_t xavix_device::mi_xavix_normal::read_sync(uint16_t adr)
{
if (adr < 0x8000)
return sdirect->read_byte(adr);
else
return sdirect->read_byte(base->adr_with_bank(adr));
}
uint8_t xavix_device::mi_xavix_normal::read_arg(uint16_t adr)
{
if (adr < 0x8000)
return direct->read_byte(adr);
else
return direct->read_byte(base->adr_with_bank(adr));
}
void xavix_device::mi_xavix_normal::write(uint16_t adr, uint8_t val)
{
if (adr < 0x8000)
program->write_byte(adr, val);
else
program->write_byte(base->adr_with_bank(adr), val);
}
xavix_device::mi_xavix_nd::mi_xavix_nd(xavix_device *_base) : mi_xavix_normal(_base)
{
}
uint8_t xavix_device::mi_xavix_nd::read_sync(uint16_t adr)
{
if (adr < 0x8000)
return sprogram->read_byte(adr);
else
return sprogram->read_byte(base->adr_with_bank(adr));
}
uint8_t xavix_device::mi_xavix_nd::read_arg(uint16_t adr)
{
if (adr < 0x8000)
return program->read_byte(adr);
else
return program->read_byte(base->adr_with_bank(adr));
}
#include "cpu/m6502/xavix.hxx"

View File

@ -0,0 +1,70 @@
// license:BSD-3-Clause
// copyright-holders:David Haywood
/***************************************************************************
xavix.h
***************************************************************************/
#ifndef MAME_CPU_M6502_XAVIX_H
#define MAME_CPU_M6502_XAVIX_H
#pragma once
#include "m6502.h"
class xavix_device : public m6502_device {
public:
xavix_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
virtual util::disasm_interface *create_disassembler() override;
virtual void do_exec_full() override;
virtual void do_exec_partial() override;
#define O(o) void o ## _full(); void o ## _partial()
// xaviv opcodes
O(callf_xa3);
O(retf_imp);
#undef O
protected:
class mi_xavix_normal : public memory_interface {
public:
xavix_device *base;
mi_xavix_normal(xavix_device *base);
virtual ~mi_xavix_normal() {}
virtual uint8_t read(uint16_t adr) override;
virtual uint8_t read_sync(uint16_t adr) override;
virtual uint8_t read_arg(uint16_t adr) override;
virtual void write(uint16_t adr, uint8_t val) override;
};
class mi_xavix_nd : public mi_xavix_normal {
public:
mi_xavix_nd(xavix_device *base);
virtual ~mi_xavix_nd() {}
virtual uint8_t read_sync(uint16_t adr) override;
virtual uint8_t read_arg(uint16_t adr) override;
};
uint8_t m_farbank;
uint32_t XPC;
uint8_t farbank_r() { return m_farbank; }
void farbank_w(uint8_t data) { m_farbank = data; }
uint32_t adr_with_bank(uint16_t adr) { return adr | (m_farbank << 16); }
virtual void device_start() override;
virtual void device_reset() override;
virtual void state_export(const device_state_entry &entry) override;
};
DECLARE_DEVICE_TYPE(XAVIX, xavix_device)
#endif // MAME_CPU_M6502_XAVIX_H

View File

@ -0,0 +1,15 @@
// license:BSD-3-Clause
// copyright-holders:David Haywood
/***************************************************************************
xavixd.cpp
***************************************************************************/
#include "emu.h"
#include "xavixd.h"
#include "cpu/m6502/xavixd.hxx"
xavix_disassembler::xavix_disassembler() : m6502_base_disassembler(disasm_entries)
{
}

View File

@ -0,0 +1,26 @@
// license:BSD-3-Clause
// copyright-holders:David Haywood
/***************************************************************************
xavixd.h
***************************************************************************/
#ifndef MAME_CPU_M6502_XAVIXD_H
#define MAME_CPU_M6502_XAVIXD_H
#pragma once
#include "m6502d.h"
class xavix_disassembler : public m6502_base_disassembler
{
public:
xavix_disassembler();
virtual ~xavix_disassembler() = default;
private:
static const disasm_entry disasm_entries[0x100];
};
#endif

View File

@ -45,8 +45,7 @@
#include "emu.h"
#include "cpu/g65816/g65816.h"
#include "cpu/m6502/m6502.h"
#include "cpu/m6502/xavix.h"
//#include "sound/ay8910.h"
#include "screen.h"
#include "speaker.h"
@ -88,8 +87,7 @@ uint32_t xavix_state::screen_update( screen_device &screen, bitmap_ind16 &bitmap
static ADDRESS_MAP_START( xavix_map, AS_PROGRAM, 8, xavix_state )
AM_RANGE(0x000000, 0x0001ff) AM_RAM
AM_RANGE(0x00f000, 0x00ffff) AM_ROM AM_REGION("bios", 0x00f000)
AM_RANGE(0x800000, 0x9fffff) AM_ROM AM_REGION("bios", 0x000000) // wrong
AM_RANGE(0x008000, 0x1fffff) AM_ROM AM_REGION("bios", 0x008000)
ADDRESS_MAP_END
static INPUT_PORTS_START( xavix )
@ -177,7 +175,7 @@ void xavix_state::machine_reset()
MACHINE_CONFIG_START(xavix_state::xavix)
/* basic machine hardware */
MCFG_CPU_ADD("maincpu",G65816,MAIN_CLOCK/4)
MCFG_CPU_ADD("maincpu",XAVIX,MAIN_CLOCK)
MCFG_CPU_PROGRAM_MAP(xavix_map)
/* video hardware */

View File

@ -75,6 +75,7 @@
#include "cpu/m6502/m65c02d.h"
#include "cpu/m6502/m65ce02d.h"
#include "cpu/m6502/m740d.h"
#include "cpu/m6502/xavixd.h"
#include "cpu/m6800/6800dasm.h"
#include "cpu/m68000/m68kdasm.h"
#include "cpu/m6805/6805dasm.h"
@ -466,6 +467,7 @@ static const dasm_table_entry dasm_table[] =
{ "x86_16", le, 0, []() -> util::disasm_interface * { i386_unidasm.mode = 16; return new i386_disassembler(&i386_unidasm); } },
{ "x86_32", le, 0, []() -> util::disasm_interface * { i386_unidasm.mode = 32; return new i386_disassembler(&i386_unidasm); } },
{ "x86_64", le, 0, []() -> util::disasm_interface * { i386_unidasm.mode = 64; return new i386_disassembler(&i386_unidasm); } },
{ "xavix", le, 0, []() -> util::disasm_interface * { return new xavix_disassembler; } },
{ "z180", le, 0, []() -> util::disasm_interface * { return new z180_disassembler; } },
{ "z8", le, 0, []() -> util::disasm_interface * { return new z8_disassembler; } },
{ "z80", le, 0, []() -> util::disasm_interface * { return new z80_disassembler; } },