summaryrefslogtreecommitdiffstatshomepage
path: root/src/emu/bus/vic20
diff options
context:
space:
mode:
author Curt Coder <curtcoder@mail.com>2014-10-10 07:00:38 +0000
committer Curt Coder <curtcoder@mail.com>2014-10-10 07:00:38 +0000
commit1327a26a55a355fe79417d846d1ab0439066df15 (patch)
tree37eb00301fe978a22c13e5773eedc5a7007f49b5 /src/emu/bus/vic20
parentd1b8b6739ccf07bb319e38133cf95f3ab6b4b2e8 (diff)
(MESS) vic20: Emulated the Final Expansion 3 cartridge (only RAM/FlashROM supported). [Curt Coder]
Diffstat (limited to 'src/emu/bus/vic20')
-rw-r--r--src/emu/bus/vic20/exp.c2
-rw-r--r--src/emu/bus/vic20/fe3.c638
-rw-r--r--src/emu/bus/vic20/fe3.h97
3 files changed, 737 insertions, 0 deletions
diff --git a/src/emu/bus/vic20/exp.c b/src/emu/bus/vic20/exp.c
index bbc24ed6398..0091f1368f2 100644
--- a/src/emu/bus/vic20/exp.c
+++ b/src/emu/bus/vic20/exp.c
@@ -209,6 +209,7 @@ void vic20_expansion_slot_device::cd_w(address_space &space, offs_t offset, UINT
//-------------------------------------------------
// slot devices
+#include "fe3.h"
#include "megacart.h"
#include "std.h"
#include "vic1010.h"
@@ -222,6 +223,7 @@ SLOT_INTERFACE_START( vic20_expansion_cards )
SLOT_INTERFACE("3k", VIC1210)
SLOT_INTERFACE("8k", VIC1110)
SLOT_INTERFACE("16k", VIC1111)
+ SLOT_INTERFACE("fe3", VIC20_FE3)
// the following need ROMs from the software list
SLOT_INTERFACE_INTERNAL("standard", VIC20_STD)
diff --git a/src/emu/bus/vic20/fe3.c b/src/emu/bus/vic20/fe3.c
new file mode 100644
index 00000000000..55b57733dc3
--- /dev/null
+++ b/src/emu/bus/vic20/fe3.c
@@ -0,0 +1,638 @@
+// license:BSD-3-Clause
+// copyright-holders:Curt Coder
+/**********************************************************************
+
+ Final Expansion v3 cartridge emulation
+
+ Copyright MESS Team.
+ Visit http://mamedev.org for licensing and usage restrictions.
+
+**********************************************************************/
+
+/*
+
+ TODO:
+
+ - fe3diag register error#2 hp=5592 (same error in VICE)
+ - SD card
+ - RTC
+
+*/
+
+#include "fe3.h"
+
+
+
+//**************************************************************************
+// MACROS/CONSTANTS
+//**************************************************************************
+
+#define AM29F040_TAG "am29f040"
+
+#define REG1_BANK \
+ ((m_reg1 & 0x7f) << 15)
+
+#define REG2_BLK0_VISIBLE \
+ (!(m_reg2 & REG2_BLK0))
+
+#define REG2_BLK1_VISIBLE \
+ (!(m_reg2 & REG2_BLK1))
+
+#define REG2_BLK2_VISIBLE \
+ (!(m_reg2 & REG2_BLK2))
+
+#define REG2_BLK3_VISIBLE \
+ (!(m_reg2 & REG2_BLK3))
+
+#define REG2_BLK5_VISIBLE \
+ (!(m_reg2 & REG2_BLK5))
+
+
+
+//**************************************************************************
+// DEVICE DEFINITIONS
+//**************************************************************************
+
+const device_type VIC20_FE3 = &device_creator<vic20_final_expansion_3_t>;
+
+
+//-------------------------------------------------
+// ROM( vic20_fe3 )
+//-------------------------------------------------
+
+ROM_START( vic20_fe3 )
+ ROM_REGION( 0x80000, AM29F040_TAG, 0 )
+ ROM_LOAD( "fe3r022d.bin", 0x00000, 0x80000, CRC(f4ff4aee) SHA1(1a389120159dee09c0f03ecb8fcd51ea2a2d2306) )
+ROM_END
+
+
+//-------------------------------------------------
+// rom_region - device-specific ROM region
+//-------------------------------------------------
+
+const rom_entry *vic20_final_expansion_3_t::device_rom_region() const
+{
+ return ROM_NAME( vic20_fe3 );
+}
+
+
+//-------------------------------------------------
+// MACHINE_DRIVER( vic20_fe3 )
+//-------------------------------------------------
+
+static MACHINE_CONFIG_FRAGMENT( vic20_fe3 )
+ MCFG_AMD_29F040_ADD(AM29F040_TAG)
+MACHINE_CONFIG_END
+
+
+//-------------------------------------------------
+// machine_config_additions - device-specific
+// machine configurations
+//-------------------------------------------------
+
+machine_config_constructor vic20_final_expansion_3_t::device_mconfig_additions() const
+{
+ return MACHINE_CONFIG_NAME( vic20_fe3 );
+}
+
+
+
+//**************************************************************************
+// LIVE DEVICE
+//**************************************************************************
+
+//-------------------------------------------------
+// vic20_final_expansion_3_t - constructor
+//-------------------------------------------------
+
+vic20_final_expansion_3_t::vic20_final_expansion_3_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) :
+ device_t(mconfig, VIC20_FE3, "Final Expansion v3", tag, owner, clock, "vic20_fe3", __FILE__),
+ device_vic20_expansion_card_interface(mconfig, *this),
+ m_flash_rom(*this, AM29F040_TAG),
+ m_ram(*this, "sram")
+{
+}
+
+
+//-------------------------------------------------
+// device_start - device-specific startup
+//-------------------------------------------------
+
+void vic20_final_expansion_3_t::device_start()
+{
+ m_ram.allocate(0x80000);
+
+ // state saving
+ save_item(NAME(m_reg1));
+ save_item(NAME(m_reg2));
+ save_item(NAME(m_lockbit));
+}
+
+
+//-------------------------------------------------
+// device_reset - device-specific reset
+//-------------------------------------------------
+
+void vic20_final_expansion_3_t::device_reset()
+{
+ m_reg1 = 0;
+ m_reg2 = 0;
+ m_lockbit = true;
+}
+
+
+//-------------------------------------------------
+// vic20_cd_r - cartridge data read
+//-------------------------------------------------
+
+UINT8 vic20_final_expansion_3_t::vic20_cd_r(address_space &space, offs_t offset, UINT8 data, int ram1, int ram2, int ram3, int blk1, int blk2, int blk3, int blk5, int io2, int io3)
+{
+ switch (m_reg1 & REG1_MODE_MASK)
+ {
+ case REG1_START:
+ // read from ROM
+ if (!blk5)
+ {
+ data = m_flash_rom->read(get_address(0, 3, offset));
+
+ m_lockbit = true;
+ }
+
+ // read from registers
+ if (!io3 && !m_lockbit && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+
+ case REG1_SUPER_ROM:
+ // read from RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ data = m_ram[get_address(0, 0, offset)];
+ }
+
+ // read from ROM
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 0, offset));
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 1, offset));
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 2, offset));
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 3, offset));
+ }
+
+ // read from registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+
+ case REG1_RAM_1:
+ // read from RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ data = m_ram[get_address(0, 0, offset)];
+ }
+
+ // read from RAM bank 1
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ data = m_ram[get_address(1, 0, offset)];
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ data = m_ram[get_address(1, 1, offset)];
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ data = m_ram[get_address(1, 2, offset)];
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ data = m_ram[get_address(1, 3, offset)];
+ }
+
+ // read from registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+
+ case REG1_RAM_2:
+ // read from RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ data = m_ram[get_address(0, 0, offset)];
+ }
+
+ // read from RAM bank 1 or 2
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ data = m_ram[get_address((m_reg1 & REG1_BLK1) ? 2 : 1, 0, offset)];
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ data = m_ram[get_address((m_reg1 & REG1_BLK2) ? 2 : 1, 1, offset)];
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ data = m_ram[get_address((m_reg1 & REG1_BLK3) ? 2 : 1, 2, offset)];
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ data = m_ram[get_address((m_reg1 & REG1_BLK5) ? 2 : 1, 3, offset)];
+ }
+
+ // read from registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+
+ case REG1_SUPER_RAM:
+ // read from RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ data = m_ram[get_address(0, 0, offset)];
+ }
+
+ // read from any RAM bank
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ data = m_ram[get_address(REG1_BANK, 0, offset)];
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ data = m_ram[get_address(REG1_BANK, 1, offset)];
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ data = m_ram[get_address(REG1_BANK, 2, offset)];
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ data = m_ram[get_address(REG1_BANK, 3, offset)];
+ }
+
+ // read from registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+
+ case REG1_RAM_ROM:
+ // read from RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ data = m_ram[get_address(0, 0, offset)];
+ }
+
+ // read from ROM bank 0 or RAM bank 1
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ data = (m_reg1 & REG1_BLK1) ? m_flash_rom->read(get_address(0, 0, offset)) : m_ram[get_address(1, 0, offset)];
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ data = (m_reg1 & REG1_BLK2) ? m_flash_rom->read(get_address(0, 1, offset)) : m_ram[get_address(1, 1, offset)];
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ data = (m_reg1 & REG1_BLK3) ? m_flash_rom->read(get_address(0, 2, offset)) : m_ram[get_address(1, 2, offset)];
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ data = (m_reg1 & REG1_BLK5) ? m_flash_rom->read(get_address(0, 3, offset)) : m_ram[get_address(1, 3, offset)];
+ }
+
+ // read from registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+
+ case REG1_FLASH:
+ // read from RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ data = m_ram[get_address(0, 0, offset)];
+ }
+
+ // read from ROM
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 0, offset));
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 1, offset));
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 2, offset));
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ data = m_flash_rom->read(get_address(REG1_BANK, 3, offset));
+ }
+
+ // read from registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ data = read_register(BIT(offset, 0));
+ }
+ break;
+ }
+
+ return data;
+}
+
+
+//-------------------------------------------------
+// vic20_cd_w - cartridge data write
+//-------------------------------------------------
+
+void vic20_final_expansion_3_t::vic20_cd_w(address_space &space, offs_t offset, UINT8 data, int ram1, int ram2, int ram3, int blk1, int blk2, int blk3, int blk5, int io2, int io3)
+{
+ offs_t addr = 0;
+
+ switch (m_reg1 & REG1_MODE_MASK)
+ {
+ case REG1_START:
+ // write to RAM bank 1
+ if (!blk5)
+ {
+ m_ram[get_address(1, 3, offset)] = data;
+
+ m_lockbit = false;
+ }
+
+ // write to registers
+ if (!io3 && !m_lockbit && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ break;
+
+ case REG1_SUPER_ROM:
+ addr = 0x8000 | offset;
+
+ // write to RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ m_ram[get_address(0, 0, offset)] = data;
+ }
+
+ // write to RAM bank 1
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ m_ram[get_address(1, 0, offset)] = data;
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ m_ram[get_address(1, 1, offset)] = data;
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ m_ram[get_address(1, 2, offset)] = data;
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ m_ram[get_address(1, 3, offset)] = data;
+ }
+
+ // write to registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ break;
+
+ case REG1_RAM_1:
+ // write to RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE && REG1_BLK0)
+ {
+ m_ram[get_address(0, 0, offset)] = data;
+ }
+
+ // write to RAM bank 1 or 2
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK1) ? 2 : 1, 0, offset)] = data;
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK2) ? 2 : 1, 1, offset)] = data;
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK3) ? 2 : 1, 2, offset)] = data;
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK5) ? 2 : 1, 3, offset)] = data;
+ }
+
+ // write to registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ break;
+
+ case REG1_RAM_2:
+ // write to RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE && REG1_BLK0)
+ {
+ m_ram[get_address(0, 0, offset)] = data;
+ }
+
+ // write to RAM bank 1
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ m_ram[get_address(1, 0, offset)] = data;
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ m_ram[get_address(1, 1, offset)] = data;
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ m_ram[get_address(1, 2, offset)] = data;
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ m_ram[get_address(1, 3, offset)] = data;
+ }
+
+ // write to registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ break;
+
+ case REG1_SUPER_RAM:
+ // write to RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ m_ram[get_address(0, 0, offset)] = data;
+ }
+
+ // write whole RAM
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ m_ram[get_address(REG1_BANK, 0, offset)] = data;
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ m_ram[get_address(REG1_BANK, 1, offset)] = data;
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ m_ram[get_address(REG1_BANK, 2, offset)] = data;
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ m_ram[get_address(REG1_BANK, 3, offset)] = data;
+ }
+
+ // write to registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ break;
+
+ case REG1_RAM_ROM:
+ // write to RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE && REG1_BLK0)
+ {
+ m_ram[get_address(0, 0, offset)] = data;
+ }
+
+ // write to RAM bank 1 or 2
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK1) ? 2 : 1, 0, offset)] = data;
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK2) ? 2 : 1, 1, offset)] = data;
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK3) ? 2 : 1, 2, offset)] = data;
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ m_ram[get_address((m_reg1 & REG1_BLK5) ? 2 : 1, 3, offset)] = data;
+ }
+
+ // write to registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ break;
+
+ case REG1_FLASH:
+ // write to RAM bank 0
+ if ((!ram1 || !ram2 || !ram3) && REG2_BLK0_VISIBLE)
+ {
+ m_ram[get_address(0, 0, offset)] = data;
+ }
+
+ // write to ROM
+ if (!blk1 && REG2_BLK1_VISIBLE)
+ {
+ m_flash_rom->write(get_address(REG1_BANK, 0, offset), data);
+ }
+ if (!blk2 && REG2_BLK2_VISIBLE)
+ {
+ m_flash_rom->write(get_address(REG1_BANK, 1, offset), data);
+ }
+ if (!blk3 && REG2_BLK3_VISIBLE)
+ {
+ m_flash_rom->write(get_address(REG1_BANK, 2, offset), data);
+ }
+ if (!blk5 && REG2_BLK5_VISIBLE)
+ {
+ m_flash_rom->write(get_address(REG1_BANK, 3, offset), data);
+ }
+
+ // write to registers
+ if (!io3 && !(m_reg2 & REG2_IO3) && ((offset & 0x1c02) == 0x1c02))
+ {
+ write_register(BIT(offset, 0), data);
+ }
+ }
+}
+
+
+//-------------------------------------------------
+// get_address -
+//-------------------------------------------------
+
+offs_t vic20_final_expansion_3_t::get_address(int bank, int block, offs_t offset)
+{
+ block ^= (m_reg2 >> 5) & 0x03;
+
+ return bank << 15 | block << 13 | offset;
+}
+
+
+//-------------------------------------------------
+// read_register -
+//-------------------------------------------------
+
+UINT8 vic20_final_expansion_3_t::read_register(offs_t offset)
+{
+ UINT8 data = 0;
+
+ switch (offset)
+ {
+ case 0:
+ data = m_reg1;
+ break;
+
+ case 1:
+ data = m_reg2;
+ break;
+ }
+
+ return data;
+}
+
+
+//-------------------------------------------------
+// write_register -
+//-------------------------------------------------
+
+void vic20_final_expansion_3_t::write_register(offs_t offset, UINT8 data)
+{
+ switch (offset)
+ {
+ case 0:
+ m_reg1 = data;
+ break;
+
+ case 1:
+ m_reg2 = data;
+ break;
+ }
+}
diff --git a/src/emu/bus/vic20/fe3.h b/src/emu/bus/vic20/fe3.h
new file mode 100644
index 00000000000..6ca5fef7a9a
--- /dev/null
+++ b/src/emu/bus/vic20/fe3.h
@@ -0,0 +1,97 @@
+// license:BSD-3-Clause
+// copyright-holders:Curt Coder
+/**********************************************************************
+
+ Final Expansion v3 cartridge emulation
+
+ Copyright MESS Team.
+ Visit http://mamedev.org for licensing and usage restrictions.
+
+**********************************************************************/
+
+#pragma once
+
+#ifndef __VIC20_FE3__
+#define __VIC20_FE3__
+
+#include "emu.h"
+#include "exp.h"
+#include "machine/intelfsh.h"
+
+
+
+//**************************************************************************
+// TYPE DEFINITIONS
+//**************************************************************************
+
+// ======================> vic20_final_expansion_3_t
+
+class vic20_final_expansion_3_t : public device_t,
+ public device_vic20_expansion_card_interface
+{
+public:
+ // construction/destruction
+ vic20_final_expansion_3_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
+
+ // optional information overrides
+ virtual const rom_entry *device_rom_region() const;
+ virtual machine_config_constructor device_mconfig_additions() const;
+
+protected:
+ // device-level overrides
+ virtual void device_start();
+ virtual void device_reset();
+
+ // device_vic20_expansion_card_interface overrides
+ virtual UINT8 vic20_cd_r(address_space &space, offs_t offset, UINT8 data, int ram1, int ram2, int ram3, int blk1, int blk2, int blk3, int blk5, int io2, int io3);
+ virtual void vic20_cd_w(address_space &space, offs_t offset, UINT8 data, int ram1, int ram2, int ram3, int blk1, int blk2, int blk3, int blk5, int io2, int io3);
+
+private:
+ enum
+ {
+ REG1_BLK0 = 0x01,
+ REG1_BLK1 = 0x02,
+ REG1_BLK2 = 0x04,
+ REG1_BLK3 = 0x08,
+ REG1_BLK5 = 0x10,
+ REG1_START = 0x00,
+ REG1_SUPER_ROM = 0x40,
+ REG1_RAM_1 = 0x80,
+ REG1_RAM_2 = 0xc0,
+ REG1_SUPER_RAM = 0xa0,
+ REG1_RAM_ROM = 0x60,
+ REG1_FLASH = 0x20,
+ REG1_MODE_MASK = 0xe0
+ };
+
+ enum
+ {
+ REG2_BLK0 = 0x01,
+ REG2_BLK1 = 0x02,
+ REG2_BLK2 = 0x04,
+ REG2_BLK3 = 0x08,
+ REG2_BLK5 = 0x10,
+ REG2_A13 = 0x20,
+ REG2_A14 = 0x40,
+ REG2_IO3 = 0x80
+ };
+
+ offs_t get_address(int bank, int block, offs_t offset);
+ UINT8 read_register(offs_t offset);
+ void write_register(offs_t offset, UINT8 data);
+
+ required_device<amd_29f040_device> m_flash_rom;
+ optional_shared_ptr<UINT8> m_ram;
+
+ UINT8 m_reg1;
+ UINT8 m_reg2;
+ bool m_lockbit;
+};
+
+
+// device type definition
+extern const device_type VIC20_FE3;
+
+
+
+#endif