diff --git a/src/emu/cpu/amis2000/amis2000.c b/src/emu/cpu/amis2000/amis2000.c index 0e8dae3b8b9..1d0f923a59e 100644 --- a/src/emu/cpu/amis2000/amis2000.c +++ b/src/emu/cpu/amis2000/amis2000.c @@ -16,7 +16,7 @@ // S2000 is the most basic one, 64 nibbles internal RAM and 1KB internal ROM // S2150 increased RAM to 80 nibbles and ROM to 1.5KB -// high-voltage output versions of these chips (S2000C and S2150C) are identical overall +// high-voltage output versions of these chips (S2000A and S2150A) are identical overall const device_type AMI_S2000 = &device_creator; const device_type AMI_S2150 = &device_creator; @@ -48,7 +48,8 @@ amis2000_device::amis2000_device(const machine_config &mconfig, const char *tag, m_program_config("program", ENDIANNESS_BIG, 8, 13, 0, ADDRESS_MAP_NAME(program_1k)), m_data_config("data", ENDIANNESS_BIG, 8, 6, 0, ADDRESS_MAP_NAME(data_64x4)), m_bu_bits(2), - m_stack_bits(10), + m_callstack_bits(10), + m_callstack_depth(3), m_read_k(*this), m_read_i(*this), m_read_d(*this), @@ -57,12 +58,13 @@ amis2000_device::amis2000_device(const machine_config &mconfig, const char *tag, { } -amis2000_device::amis2000_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, UINT8 bu_bits, UINT8 stack_bits, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data, const char *shortname, const char *source) +amis2000_device::amis2000_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, UINT8 bu_bits, UINT8 callstack_bits, UINT8 callstack_depth, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data, const char *shortname, const char *source) : cpu_device(mconfig, type, name, tag, owner, clock, shortname, source), m_program_config("program", ENDIANNESS_BIG, 8, prgwidth, 0, program), m_data_config("data", ENDIANNESS_BIG, 8, datawidth, 0, data), m_bu_bits(bu_bits), - m_stack_bits(stack_bits), + m_callstack_bits(callstack_bits), + m_callstack_depth(callstack_depth), m_read_k(*this), m_read_i(*this), m_read_d(*this), @@ -72,7 +74,7 @@ amis2000_device::amis2000_device(const machine_config &mconfig, device_type type } amis2150_device::amis2150_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) - : amis2000_device(mconfig, AMI_S2150, "AMI S2150", tag, owner, clock, 3, 11, 13, ADDRESS_MAP_NAME(program_1_5k), 7, ADDRESS_MAP_NAME(data_80x4), "amis2150", __FILE__) + : amis2000_device(mconfig, AMI_S2150, "AMI S2150", tag, owner, clock, 3, 11, 3, 13, ADDRESS_MAP_NAME(program_1_5k), 7, ADDRESS_MAP_NAME(data_80x4), "amis2150", __FILE__) { } @@ -112,7 +114,7 @@ offs_t amis2000_device::disasm_disassemble(char *buffer, offs_t pc, const UINT8 enum { S2000_PC=1, S2000_BL, S2000_BU, - S2000_A, S2000_E + S2000_ACC, S2000_E }; void amis2000_device::device_start() @@ -127,34 +129,34 @@ void amis2000_device::device_start() m_write_a.resolve_safe(); m_bu_mask = (1 << m_bu_bits) - 1; - m_stack_mask = (1 << m_stack_bits) - 1; + m_callstack_mask = (1 << m_callstack_bits) - 1; // zerofill - m_stack[0] = m_stack[1] = m_stack[2] = 0; + memset(m_callstack, 0, sizeof(m_callstack)); m_pc = 0; m_op = 0; m_f = 0; m_bl = 0; m_bu = 0; - m_a = 0; + m_acc = 0; m_e = 0; // register for savestates - save_item(NAME(m_stack)); + save_item(NAME(m_callstack)); save_item(NAME(m_pc)); save_item(NAME(m_op)); save_item(NAME(m_f)); save_item(NAME(m_bl)); save_item(NAME(m_bu)); - save_item(NAME(m_a)); + save_item(NAME(m_acc)); save_item(NAME(m_e)); // register state for debugger state_add(S2000_PC, "PC", m_pc ).formatstr("%04X"); state_add(S2000_BL, "BL", m_bl ).formatstr("%01X"); state_add(S2000_BU, "BU", m_bu ).formatstr("%01X"); - state_add(S2000_A, "A", m_a ).formatstr("%01X"); - state_add(S2000_E, "E", m_a ).formatstr("%01X"); + state_add(S2000_ACC, "ACC", m_acc ).formatstr("%01X"); + state_add(S2000_E, "E", m_e ).formatstr("%01X"); state_add(STATE_GENPC, "curpc", m_pc).formatstr("%04X").noshow(); state_add(STATE_GENFLAGS, "GENFLAGS", m_f).formatstr("%6s").noshow(); @@ -183,7 +185,7 @@ void amis2000_device::device_reset() void amis2000_device::execute_run() { - do + while (m_icount > 0) { m_icount--; @@ -191,10 +193,76 @@ void amis2000_device::execute_run() m_op = m_program->read_byte(m_pc); m_pc = (m_pc + 1) & 0x1fff; - switch (m_op) + switch (m_op & 0xf0) { - default: break; - } + case 0x50: op_adis(); break; + case 0x60: op_pp(); break; + case 0x70: op_lai(); break; - } while (m_icount > 0); + case 0x80: case 0x90: case 0xa0: case 0xb0: op_jms(); break; + case 0xc0: case 0xd0: case 0xe0: case 0xf0: op_jmp(); break; + + default: + switch (m_op) + { + case 0x00: op_nop(); break; + case 0x01: op_illegal(); break; // reserved for devkit-use + case 0x02: op_rt(); break; + case 0x03: op_rts(); break; + case 0x04: op_psh(); break; + case 0x05: op_psl(); break; + case 0x06: op_and(); break; + case 0x07: op_sos(); break; + case 0x08: op_sbe(); break; + case 0x09: op_szc(); break; + case 0x0a: op_stc(); break; + case 0x0b: op_rsc(); break; + case 0x0c: op_lae(); break; + case 0x0d: op_xae(); break; + case 0x0e: op_inp(); break; + case 0x0f: op_eur(); break; + case 0x10: op_cma(); break; + case 0x11: op_xabu(); break; + case 0x12: op_lab(); break; + case 0x13: op_xab(); break; + case 0x14: op_adcs(); break; + case 0x15: op_xor(); break; + case 0x16: op_add(); break; + case 0x17: op_sam(); break; + case 0x18: op_disb(); break; + case 0x19: op_mvs(); break; + case 0x1a: op_out(); break; + case 0x1b: op_disn(); break; + + case 0x28: op_szk(); break; + case 0x29: op_szi(); break; + case 0x2a: op_rf1(); break; + case 0x2b: op_sf1(); break; + case 0x2c: op_rf2(); break; + case 0x2d: op_sf2(); break; + case 0x2e: op_tf1(); break; + case 0x2f: op_tf2(); break; + + default: + switch (m_op & 0xfc) + { + case 0x1c: op_szm(); break; + case 0x20: op_stm(); break; + case 0x24: op_rsm(); break; + + case 0x30: op_xci(); break; + case 0x34: op_xcd(); break; + case 0x38: op_xc(); break; + case 0x3c: op_lam(); break; + case 0x40: op_lbz(); break; + case 0x44: op_lbf(); break; + case 0x48: op_lbe(); break; + case 0x4c: op_lbep(); break; + } + break; + + } + break; + } // big switch + } } diff --git a/src/emu/cpu/amis2000/amis2000.h b/src/emu/cpu/amis2000/amis2000.h index 8bcefd65804..5cf7761c27e 100644 --- a/src/emu/cpu/amis2000/amis2000.h +++ b/src/emu/cpu/amis2000/amis2000.h @@ -36,7 +36,7 @@ class amis2000_device : public cpu_device public: // construction/destruction amis2000_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); - amis2000_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, UINT8 bu_bits, UINT8 stack_bits, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data, const char *shortname, const char *source); + amis2000_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, UINT8 bu_bits, UINT8 callstack_bits, UINT8 callstack_depth, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data, const char *shortname, const char *source); // static configuration helpers template static devcb_base &set_read_k_callback(device_t &device, _Object object) { return downcast(device).m_read_k.set_callback(object); } @@ -72,16 +72,17 @@ protected: UINT8 m_bu_bits; UINT16 m_bu_mask; - UINT8 m_stack_bits; - UINT16 m_stack_mask; - UINT16 m_stack[3]; + UINT8 m_callstack_bits; + UINT16 m_callstack_mask; + UINT8 m_callstack_depth; // callstack levels: 3 on 2000/2150, 5 on 2200/2400 + UINT16 m_callstack[5]; // max 5 UINT16 m_pc; UINT8 m_op; - UINT8 m_f; - UINT8 m_bl; - UINT8 m_bu; - UINT8 m_a; + UINT8 m_f; // generic flags: 2 on 2000/2150, 6 on 2200/2400 + UINT8 m_bl; // 4-bit ram index x + UINT8 m_bu; // 2/3-bit ram index y + UINT8 m_acc; UINT8 m_e; devcb_read8 m_read_k; @@ -91,6 +92,65 @@ protected: devcb_write16 m_write_a; int m_icount; + + void op_illegal(); + + void op_lai(); + void op_lab(); + void op_lae(); + void op_xab(); + void op_xabu(); + void op_xae(); + void op_lbe(); + void op_lbep(); + void op_lbz(); + void op_lbf(); + + void op_lam(); + void op_xc(); + void op_xci(); + void op_xcd(); + void op_stm(); + void op_rsm(); + + void op_inp(); + void op_out(); + void op_disb(); + void op_disn(); + void op_mvs(); + void op_psh(); + void op_psl(); + void op_eur(); + + void op_pp(); + void op_jmp(); + void op_jms(); + void op_rt(); + void op_rts(); + void op_nop(); + + void op_szc(); + void op_szm(); + void op_szi(); + void op_szk(); + void op_sbe(); + void op_sam(); + void op_sos(); + void op_tf1(); + void op_tf2(); + + void op_adcs(); + void op_adis(); + void op_add(); + void op_and(); + void op_xor(); + void op_stc(); + void op_rsc(); + void op_cma(); + void op_sf1(); + void op_rf1(); + void op_sf2(); + void op_rf2(); }; diff --git a/src/emu/cpu/amis2000/amis2000op.inc b/src/emu/cpu/amis2000/amis2000op.inc index 0113dcdad8e..a0b219dbd72 100644 --- a/src/emu/cpu/amis2000/amis2000op.inc +++ b/src/emu/cpu/amis2000/amis2000op.inc @@ -1 +1,331 @@ // AMI S2000 opcode handlers + +// internal helpers + +void amis2000_device::op_illegal() +{ + logerror("%s unknown opcode $%02X at $%04X\n", tag(), m_op, m_pc); +} + + +// Register Instructions + +void amis2000_device::op_lai() +{ + // LAI X: load ACC with X, select I and K inputs + op_illegal(); +} + +void amis2000_device::op_lab() +{ + // LAB: load ACC with BL + op_illegal(); +} + +void amis2000_device::op_lae() +{ + // LAE: load ACC with E + op_illegal(); +} + +void amis2000_device::op_xab() +{ + // XAB: exchange ACC with BL + op_illegal(); +} + +void amis2000_device::op_xabu() +{ + // XABU: exchange ACC with BU + op_illegal(); +} + +void amis2000_device::op_xae() +{ + // XAE: exchange ACC with E + op_illegal(); +} + +void amis2000_device::op_lbe() +{ + // LBE Y: load BU with Y, load BL with E + op_illegal(); +} + +void amis2000_device::op_lbep() +{ + // LBEP Y: load BU with Y, load BL with E+1 + op_illegal(); +} + +void amis2000_device::op_lbz() +{ + // LBZ Y: load BU with Y, load BL with 0 + op_illegal(); +} + +void amis2000_device::op_lbf() +{ + // LBF Y: load BU with Y, load BL with 15 + op_illegal(); +} + + +// RAM Instructions + +void amis2000_device::op_lam() +{ + // LAM _Y: load ACC with RAM, xor BU with _Y + op_illegal(); +} + +void amis2000_device::op_xc() +{ + // XC _Y: exchange ACC with RAM, xor BU with _Y + op_illegal(); +} + +void amis2000_device::op_xci() +{ + // XCI _Y: exchange ACC with RAM, increment BL(skip next on carry), xor BU with _Y + op_illegal(); +} + +void amis2000_device::op_xcd() +{ + // XCD _Y: exchange ACC with RAM, decrement BL(skip next on carry), xor BU with _Y + op_illegal(); +} + +void amis2000_device::op_stm() +{ + // STM Z: set RAM bit Z + op_illegal(); +} + +void amis2000_device::op_rsm() +{ + // RSM Z: reset RAM bit Z + op_illegal(); +} + + +// Input/Output Instructions + +void amis2000_device::op_inp() +{ + // INP: input D-pins to ACC and RAM + op_illegal(); +} + +void amis2000_device::op_out() +{ + // OUT: pulse output ACC and RAM to D-pins + op_illegal(); +} + +void amis2000_device::op_disb() +{ + // DISB: set D-latch to ACC and RAM directly + op_illegal(); +} + +void amis2000_device::op_disn() +{ + // DISN: set D-latch to ACC+carry via segment decoder + op_illegal(); +} + +void amis2000_device::op_mvs() +{ + // MVS: output master strobe latch to A-pins + op_illegal(); +} + +void amis2000_device::op_psh() +{ + // PSH: preset high(BL) master strobe latch + op_illegal(); +} + +void amis2000_device::op_psl() +{ + // PSL: preset low(BL) master strobe latch + op_illegal(); +} + +void amis2000_device::op_eur() +{ + // EUR: set timer frequency(European) and D-latch polarity + op_illegal(); +} + + +// Program Control Instructions + +void amis2000_device::op_pp() +{ + // PP _X: prepare page/bank with _X + op_illegal(); +} + +void amis2000_device::op_jmp() +{ + // JMP X: jump to X(+PP) + op_illegal(); +} + +void amis2000_device::op_jms() +{ + // JMS X: call to X(+PP) + op_illegal(); +} + +void amis2000_device::op_rt() +{ + // RT: return from subroutine + op_illegal(); +} + +void amis2000_device::op_rts() +{ + // RTS: return from subroutine and skip next + op_illegal(); +} + +void amis2000_device::op_nop() +{ + // NOP: no operation +} + + +// Skip Instructions + +void amis2000_device::op_szc() +{ + // SZC: skip next on zero(no) carry + op_illegal(); +} + +void amis2000_device::op_szm() +{ + // SZM Z: skip next on zero RAM bit Z + op_illegal(); +} + +void amis2000_device::op_szi() +{ + // SZI: skip next on zero I pin(s) + op_illegal(); +} + +void amis2000_device::op_szk() +{ + // SZK: skip next on zero K pin(s) + op_illegal(); +} + +void amis2000_device::op_sbe() +{ + // SBE: skip next on BL equ E + op_illegal(); +} + +void amis2000_device::op_sam() +{ + // SAM: skip next on ACC equ RAM + op_illegal(); +} + +void amis2000_device::op_sos() +{ + // SOS: skip next on SF(timer output), clear SF + op_illegal(); +} + +void amis2000_device::op_tf1() +{ + // TF1: skip next on flag 1 + op_illegal(); +} + +void amis2000_device::op_tf2() +{ + // TF2: skip next on flag 2 + op_illegal(); +} + + +// Arithmetic and Logical Instructions + +void amis2000_device::op_adcs() +{ + // ADCS: add RAM to ACC+carry, skip next on no carry + op_illegal(); +} + +void amis2000_device::op_adis() +{ + // ADIS X: add X to ACC, skip next on no carry + op_illegal(); +} + +void amis2000_device::op_add() +{ + // ADD: add RAM to ACC + op_illegal(); +} + +void amis2000_device::op_and() +{ + // AND: and ACC with RAM + op_illegal(); +} + +void amis2000_device::op_xor() +{ + // XOR: xor ACC with RAM + op_illegal(); +} + +void amis2000_device::op_stc() +{ + // STC: set carry + op_illegal(); +} + +void amis2000_device::op_rsc() +{ + // RSC: reset carry + op_illegal(); +} + +void amis2000_device::op_cma() +{ + // CMA: complement ACC + op_illegal(); +} + +void amis2000_device::op_sf1() +{ + // SF1: set flag 1 + op_illegal(); +} + +void amis2000_device::op_rf1() +{ + // RF1: reset flag 1 + op_illegal(); +} + +void amis2000_device::op_sf2() +{ + // SF2: set flag 2 + op_illegal(); +} + +void amis2000_device::op_rf2() +{ + // RF2: reset flag 2 + op_illegal(); +} diff --git a/src/mess/drivers/wildfire.c b/src/mess/drivers/wildfire.c index b846a89c039..c4dce72cc1a 100644 --- a/src/mess/drivers/wildfire.c +++ b/src/mess/drivers/wildfire.c @@ -14,7 +14,8 @@ #include "wildfire.lh" -// master clock is MCU internal, default frequency of 850kHz +// master clock is a single stage RC oscillator: R=?K, C=?pf, +// S2150 default frequency is 850kHz #define MASTER_CLOCK (850000)