Journey to the RC2014 Mini Driver for MAME

21Mar22

My original attempt at an RC2014 Mini driver started out as pretty much a copy of the gsz80 driver, with a find/replace of ‘gsz80’ with ‘rc2014mini’. But as the MAME team reviewed my pull request, they surfaced a bunch of problems.

Firstly I didn’t have the correct memory map. The RC2014 Mini only has 32K RAM (and of course it needs the corresponding 32K BASIC).

// RC2014 Mini only has 32K RAM
void rc2014mini_state::rc2014mini_mem(address_map &map)
{
	map(0x0000, 0x1fff).rom();
	map(0x8000, 0xffff).ram();
}

Then there was some discussion about how to handle ROMs. Initially I went for the MAME BIOS selection method:

// from https://github.com/RC2014Z80/RC2014/tree/master/ROMs/Factory
// `dd skip=56 count=8 if=R0000009.BIN of=rc2014mini_scm.bin bs=1024`
// `dd count=8 if=R0000009.BIN of=rc2014mini_32k.bin bs=1024`
ROM_START(rc2014mini)
	ROM_REGION(0x2000, "maincpu",0)
	ROM_SYSTEM_BIOS( 0, "scm", "Small Computer Monitor")
	ROMX_LOAD("rc2014mini_scm.bin",  0x0000, 0x2000, CRC(e8745176) SHA1(d71afa985c4dcc25536b6597a099dabc815a8eb2), ROM_BIOS(0))
	ROM_SYSTEM_BIOS( 1, "32k", "32K BASIC")
	ROMX_LOAD("rc2014mini_32k.bin",  0x0000, 0x2000, CRC(850e3ec7) SHA1(7c9613e160b324ee1ed42fc48d98bbc215791e81), ROM_BIOS(1))
ROM_END

But I was persuaded that it was better to implement jumpers for the ROMs, as that’s more authentic to the original hardware:

void rc2014mini_state::machine_start()
{
	m_rombank->configure_entries(0, 8, memregion("maincpu")->base(), 0x2000);
}

// Set ROM bank from machine CONF at Reset
void rc2014mini_state::machine_reset()
{
	m_rombank->set_entry(m_jump_rom->read() & 7);
}

//...

static INPUT_PORTS_START( rc2014mini )
	PORT_START("A13-15")   /* jumpers to select ROM region */
	PORT_CONFNAME( 0x7, 0x0, "ROM Bank" )
	PORT_CONFSETTING( 0x0, "BASIC" )
	PORT_CONFSETTING( 0x1, "EMPTY1" )
	PORT_CONFSETTING( 0x2, "EMPTY2" )
	PORT_CONFSETTING( 0x3, "EMPTY3" )
	PORT_CONFSETTING( 0x4, "EMPTY4" )
	PORT_CONFSETTING( 0x5, "EMPTY5" )
	PORT_CONFSETTING( 0x6, "EMPTY6" )
	PORT_CONFSETTING( 0x7, "SCM" )
INPUT_PORTS_END

//...

ROM_START(rc2014mini)
	ROM_REGION( 0x10000, "maincpu",0 )
	ROM_LOAD( "r0000009.bin",    0x0000, 0x10000, CRC(3fb1ced7) SHA1(40a030b931ebe6cca654ce056c228297f245b057))
ROM_END

Of course that now means defining an INPUT at the end block:

//    YEAR  NAME            PARENT    COMPAT    MACHINE        INPUT          CLASS             INIT           COMPANY           FULLNAME                FLAGS
COMP( 2007, gsz80,          0,        0,        gsz80,         0,             gsz80_state,      empty_init,    "Grant Searle",   "Simple Z-80 Machine",  MACHINE_NO_SOUND_HW )
COMP( 2015, rc2014mini,     gsz80,    0,        rc2014mini,    rc2014mini,    rc2014mini_state, empty_init,    "Z80Kits",        "RC2014 Mini",          MACHINE_NO_SOUND_HW )

Along the way the RC2014 Mini stuff was folded back into the gsz80.cpp driver rather than duplicating it. So it gets its own class:

class rc2014mini_state : public gsz80_state
{
public:
	rc2014mini_state(const machine_config &mconfig, device_type type, const char *tag)
		: gsz80_state(mconfig, type, tag)
		, m_rombank(*this, "rombank")
		, m_jump_rom(*this, "A13-15")
	{ }

	// Different machine config due to different RAM
	void rc2014mini(machine_config &config);

protected:
	// RC2014 Mini only has 32K RAM, so memory map is different
	void rc2014mini_mem(address_map &map);

	virtual void machine_start() override;
	virtual void machine_reset() override;

	required_memory_bank m_rombank;
	required_ioport m_jump_rom;
};

and that needs the implementation for state to make use of the different memory map and the ROM switched into it:

void rc2014mini_state::rc2014mini(machine_config &config)
{
	gsz80(config);
	m_maincpu->set_addrmap(AS_PROGRAM, &rc2014mini_state::rc2014mini_mem);
}

All of this rather stretched my very limited C++ knowledge. I did a Computer Based Training (CBT) course on C++ back in the mid nineties where absolutely nothing sank in (maybe because it spent too much time recapitulating C stuff that I though I already knew). When I started doing Java Enterprise stuff in 2000 classes and objects and inheritance and polymorphism were all new to me. To try to claw things back I ran through the W3 schools C++ Tutorial, which does a good job of covering the basics. If you’re new to C++ but want to try stuff in MAME then it’s probably a good enough place to start. Beyond that, Learn C++ looks pretty comprehensive.



No Responses Yet to “Journey to the RC2014 Mini Driver for MAME”

  1. Leave a Comment

Leave a comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.