mirror of
https://github.com/holub/mame
synced 2025-04-24 17:30:55 +03:00
SM511: added instruction clock divider (nw)
This commit is contained in:
parent
710072f572
commit
201d49ba76
@ -23,15 +23,17 @@
|
||||
- KB1013VK1-2/KB1013VK4-2 manual
|
||||
|
||||
TODO:
|
||||
- finish SM500 emulation
|
||||
- proper support for LFSR program counter in debugger
|
||||
- callback for lcd screen as MAME bitmap (when needed)
|
||||
- LCD bs pin blink mode via Y register (0.5s off, 0.5s on)
|
||||
- wake up after CEND doesn't work right
|
||||
- SM510 buzzer control divider bit is mask-programmable?
|
||||
- SM511 undocumented/guessed opcodes:
|
||||
* $01 is guessed as DIV to ACC transfer, unknown which bits
|
||||
* $5d is certainly CEND
|
||||
* $65 is certainly divider reset, but not sure if it behaves same as on SM510
|
||||
* $6036 may be instruction timing? (16KHz vs 8KHz)
|
||||
* $6036 and $6037 may be instruction timing? (16kHz and 8kHz), mnemonics unknown
|
||||
|
||||
*/
|
||||
|
||||
@ -69,7 +71,7 @@ void sm510_base_device::device_start()
|
||||
m_write_segbs.resolve_safe();
|
||||
m_write_segc.resolve_safe();
|
||||
|
||||
// zerofill
|
||||
// init/zerofill
|
||||
memset(m_stack, 0, sizeof(m_stack));
|
||||
m_pc = 0;
|
||||
m_prev_pc = 0;
|
||||
@ -99,6 +101,7 @@ void sm510_base_device::device_start()
|
||||
m_melody_duty_count = 0;
|
||||
m_melody_duty_index = 0;
|
||||
m_melody_address = 0;
|
||||
m_clk_div = 2; // 16kHz
|
||||
|
||||
// register for savestates
|
||||
save_item(NAME(m_stack));
|
||||
@ -130,6 +133,7 @@ void sm510_base_device::device_start()
|
||||
save_item(NAME(m_melody_duty_count));
|
||||
save_item(NAME(m_melody_duty_index));
|
||||
save_item(NAME(m_melody_address));
|
||||
save_item(NAME(m_clk_div));
|
||||
|
||||
// register state for debugger
|
||||
state_add(SM510_PC, "PC", m_pc).formatstr("%04X");
|
||||
@ -174,7 +178,6 @@ void sm510_base_device::device_reset()
|
||||
|
||||
m_r = m_r_out = 0;
|
||||
m_write_r(0, 0, 0xff);
|
||||
m_melody_rd &= ~1;
|
||||
}
|
||||
|
||||
|
||||
|
@ -134,8 +134,8 @@ protected:
|
||||
virtual void device_reset() override;
|
||||
|
||||
// device_execute_interface overrides
|
||||
virtual u64 execute_clocks_to_cycles(u64 clocks) const override { return (clocks + 2 - 1) / 2; } // default 2 cycles per machine cycle
|
||||
virtual u64 execute_cycles_to_clocks(u64 cycles) const override { return (cycles * 2); } // "
|
||||
virtual u64 execute_clocks_to_cycles(u64 clocks) const override { return (clocks + m_clk_div - 1) / m_clk_div; } // default 2 cycles per machine cycle
|
||||
virtual u64 execute_cycles_to_clocks(u64 cycles) const override { return (cycles * m_clk_div); } // "
|
||||
virtual u32 execute_min_cycles() const override { return 1; }
|
||||
virtual u32 execute_max_cycles() const override { return 2; }
|
||||
virtual u32 execute_input_lines() const override { return 1; }
|
||||
@ -177,6 +177,7 @@ protected:
|
||||
u8 m_r, m_r_out;
|
||||
bool m_k_active;
|
||||
bool m_halt;
|
||||
int m_clk_div;
|
||||
|
||||
// lcd driver
|
||||
optional_shared_ptr<u8> m_lcd_ram_a, m_lcd_ram_b, m_lcd_ram_c;
|
||||
@ -295,6 +296,8 @@ protected:
|
||||
virtual void op_idiv();
|
||||
virtual void op_dr();
|
||||
virtual void op_dta();
|
||||
virtual void op_clklo();
|
||||
virtual void op_clkhi();
|
||||
|
||||
void op_illegal();
|
||||
};
|
||||
@ -323,6 +326,9 @@ public:
|
||||
sm511_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, u32 clock, int stack_levels, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data, const char *shortname, const char *source);
|
||||
|
||||
protected:
|
||||
virtual void device_post_load() override { notify_clock_changed(); }
|
||||
virtual void device_reset() override;
|
||||
|
||||
virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override;
|
||||
virtual void execute_one() override;
|
||||
virtual void get_opcode_param() override;
|
||||
|
@ -25,7 +25,7 @@ enum e_mnemonics
|
||||
mTB, mTC, mTAM, mTMI, mTA0, mTABL, mTIS, mTAL, mTF1, mTF4,
|
||||
mRM, mSM,
|
||||
mPRE, mSME, mRME, mTMEL,
|
||||
mSKIP, mCEND, mIDIV, mDR, mDTA,
|
||||
mSKIP, mCEND, mIDIV, mDR, mDTA, mCLKLO, mCLKHI,
|
||||
|
||||
// SM500-specific
|
||||
mCOMCB, mRTN, mRTNS, mSSR, mTR, mTRS,
|
||||
@ -52,7 +52,7 @@ static const char *const s_mnemonics[] =
|
||||
"TB", "TC", "TAM", "TMI", "TA0", "TABL", "TIS", "TAL", "TF1", "TF4",
|
||||
"RM", "SM",
|
||||
"PRE", "SME", "RME", "TMEL",
|
||||
"SKIP", "CEND", "IDIV", "DR", "DTA",
|
||||
"SKIP", "CEND", "IDIV", "DR", "DTA", "CLKLO", "CLKHI",
|
||||
|
||||
//
|
||||
"COMCB", "RTN", "RTNS", "SSR", "TR", "TRS",
|
||||
@ -80,7 +80,7 @@ static const u8 s_bits[] =
|
||||
0, 0, 0, 2, 0, 0, 0, 0, 0, 0,
|
||||
2, 2,
|
||||
8, 0, 0, 0,
|
||||
0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0,
|
||||
|
||||
//
|
||||
0, 0, 0, 4, 6, 6,
|
||||
@ -110,7 +110,7 @@ static const u32 s_flags[] =
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0,
|
||||
0, 0, 0, 0,
|
||||
0, _OVER, 0, 0, 0,
|
||||
0, _OVER, 0, 0, 0, 0, 0,
|
||||
|
||||
//
|
||||
0, _OUT, _OUT, 0, 0, _OVER,
|
||||
@ -253,7 +253,7 @@ static const u8 sm511_mnemonic[0x100] =
|
||||
|
||||
static const u8 sm511_extended[0x10] =
|
||||
{
|
||||
mRME, mSME, mTMEL, mATFC, mBDC, mATBP, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 // 60 3
|
||||
mRME, mSME, mTMEL, mATFC, mBDC, mATBP, mCLKHI,mCLKLO,0, 0, 0, 0, 0, 0, 0, 0 // 60 3
|
||||
};
|
||||
|
||||
CPU_DISASSEMBLE(sm511)
|
||||
|
@ -444,6 +444,20 @@ void sm510_base_device::op_dta()
|
||||
m_acc = m_div >> 11 & 0xf;
|
||||
}
|
||||
|
||||
void sm510_base_device::op_clklo()
|
||||
{
|
||||
// CLKLO*: select 8kHz instruction clock (*unknown mnemonic)
|
||||
m_clk_div = 4;
|
||||
notify_clock_changed();
|
||||
}
|
||||
|
||||
void sm510_base_device::op_clkhi()
|
||||
{
|
||||
// CLKHI*: select 16kHz instruction clock (*unknown mnemonic)
|
||||
m_clk_div = 2;
|
||||
notify_clock_changed();
|
||||
}
|
||||
|
||||
void sm510_base_device::op_illegal()
|
||||
{
|
||||
logerror("%s unknown opcode $%02X at $%04X\n", tag(), m_op, m_prev_pc);
|
||||
|
@ -58,6 +58,21 @@ sm512_device::sm512_device(const machine_config &mconfig, const char *tag, devic
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_reset - device-specific reset
|
||||
//-------------------------------------------------
|
||||
|
||||
void sm511_device::device_reset()
|
||||
{
|
||||
sm510_base_device::device_reset();
|
||||
|
||||
m_melody_rd &= ~1;
|
||||
m_clk_div = 4; // 8kHz
|
||||
notify_clock_changed();
|
||||
}
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// melody controller
|
||||
//-------------------------------------------------
|
||||
@ -179,7 +194,7 @@ void sm511_device::execute_one()
|
||||
switch (m_op)
|
||||
{
|
||||
case 0x00: op_rot(); break;
|
||||
case 0x01: op_dta(); break; // guessed
|
||||
case 0x01: op_dta(); break;
|
||||
case 0x02: op_sbm(); break;
|
||||
case 0x03: op_atpl(); break;
|
||||
case 0x08: op_add(); break;
|
||||
@ -204,7 +219,7 @@ void sm511_device::execute_one()
|
||||
case 0x62: op_wr(); break;
|
||||
case 0x63: op_ws(); break;
|
||||
case 0x64: op_incb(); break;
|
||||
case 0x65: op_dr(); break; // guessed
|
||||
case 0x65: op_dr(); break;
|
||||
case 0x66: op_rc(); break;
|
||||
case 0x67: op_sc(); break;
|
||||
case 0x6c: op_decb(); break;
|
||||
@ -223,6 +238,8 @@ void sm511_device::execute_one()
|
||||
case 0x33: op_atfc(); break;
|
||||
case 0x34: op_bdc(); break;
|
||||
case 0x35: op_atbp(); break;
|
||||
case 0x36: op_clkhi(); break;
|
||||
case 0x37: op_clklo(); break;
|
||||
|
||||
default: op_illegal(); break;
|
||||
}
|
||||
|
@ -150,7 +150,6 @@ static MACHINE_CONFIG_START( sc6, fidelmcs48_state )
|
||||
MCFG_CPU_ADD("maincpu", I8040, XTAL_11MHz)
|
||||
MCFG_CPU_PROGRAM_MAP(sc6_map)
|
||||
MCFG_MCS48_PORT_P2_OUT_CB(WRITE8(fidelmcs48_state, sc6_mux_w))
|
||||
MCFG_MCS48_PORT_P2_IN_CB(CONSTANT(0xff))
|
||||
MCFG_MCS48_PORT_P1_IN_CB(READ8(fidelmcs48_state, sc6_input_r))
|
||||
MCFG_MCS48_PORT_P1_OUT_CB(WRITE8(fidelmcs48_state, sc6_select_w))
|
||||
MCFG_MCS48_PORT_T0_IN_CB(READLINE(fidelmcs48_state, sc6_input6_r))
|
||||
|
@ -1775,7 +1775,6 @@ static MACHINE_CONFIG_START( vbrc, fidelz80_state )
|
||||
MCFG_QUANTUM_PERFECT_CPU("maincpu")
|
||||
|
||||
MCFG_CPU_ADD("mcu", I8041, XTAL_5MHz)
|
||||
MCFG_MCS48_PORT_P1_IN_CB(CONSTANT(0)) // ???
|
||||
MCFG_MCS48_PORT_P1_OUT_CB(WRITE8(fidelz80_state, vbrc_mcu_p1_w))
|
||||
MCFG_MCS48_PORT_P2_IN_CB(READ8(fidelz80_state, vbrc_mcu_p2_r))
|
||||
MCFG_MCS48_PORT_P2_OUT_CB(DEVWRITE8("i8243", i8243_device, p2_w))
|
||||
|
@ -142,8 +142,6 @@ INPUT_CHANGED_MEMBER(novagmcs48_state::octo_cpu_freq)
|
||||
Machine Drivers
|
||||
******************************************************************************/
|
||||
|
||||
// Presto/Octo
|
||||
|
||||
static MACHINE_CONFIG_START( presto, novagmcs48_state )
|
||||
|
||||
/* basic machine hardware */
|
||||
|
Loading…
Reference in New Issue
Block a user