summaryrefslogtreecommitdiffstatshomepage
path: root/src/mess/machine/apple3.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/mess/machine/apple3.c')
-rw-r--r--src/mess/machine/apple3.c738
1 files changed, 738 insertions, 0 deletions
diff --git a/src/mess/machine/apple3.c b/src/mess/machine/apple3.c
new file mode 100644
index 00000000000..e8059f65aa4
--- /dev/null
+++ b/src/mess/machine/apple3.c
@@ -0,0 +1,738 @@
+/***************************************************************************
+
+ machine/apple3.c
+
+ Apple ///
+
+
+ VIA #0 (D VIA)
+ CA1: 1 if a cartridge is inserted, 0 otherwise
+
+ VIA #1 (E VIA)
+ CA2: 1 if key pressed, 0 otherwise
+
+***************************************************************************/
+
+#include "emu.h"
+#include "includes/apple3.h"
+#include "includes/apple2.h"
+#include "cpu/m6502/m6502.h"
+#include "machine/6522via.h"
+#include "machine/ay3600.h"
+#include "machine/applefdc.h"
+#include "devices/appldriv.h"
+#include "machine/6551acia.h"
+#include "machine/ram.h"
+
+
+static void apple3_update_drives(device_t *device);
+
+
+#define LOG_MEMORY 1
+#define LOG_INDXADDR 1
+
+
+
+/* ----------------------------------------------------------------------- */
+
+
+static void apple3_profile_init(void)
+{
+}
+
+
+
+static void apple3_profile_statemachine(void)
+{
+}
+
+
+
+UINT8 apple3_state::apple3_profile_r(offs_t offset)
+{
+ UINT8 result = 0;
+
+ offset %= 4;
+ apple3_profile_statemachine();
+
+ m_profile_lastaddr = offset;
+
+ switch(offset)
+ {
+ case 1:
+ m_profile_gotstrobe = 1;
+ apple3_profile_statemachine();
+ result = m_profile_readdata;
+ break;
+
+ case 2:
+ if (m_profile_busycount > 0)
+ {
+ m_profile_busycount--;
+ result = 0xFF;
+ }
+ else
+ {
+ result = m_profile_busy | m_profile_online;
+ }
+ break;
+ }
+ return result;
+}
+
+
+
+void apple3_state::apple3_profile_w(offs_t offset, UINT8 data)
+{
+ offset %= 4;
+ m_profile_lastaddr = -1;
+
+ switch(offset)
+ {
+ case 0:
+ m_profile_writedata = data;
+ m_profile_gotstrobe = 1;
+ break;
+ }
+ apple3_profile_statemachine();
+}
+
+
+
+/* ----------------------------------------------------------------------- */
+
+READ8_MEMBER(apple3_state::apple3_c0xx_r)
+{
+ acia6551_device *acia = machine().device<acia6551_device>("acia");
+ device_t *fdc = machine().device("fdc");
+ UINT8 result = 0xFF;
+
+ switch(offset)
+ {
+ case 0x00: case 0x01: case 0x02: case 0x03:
+ case 0x04: case 0x05: case 0x06: case 0x07:
+ result = AY3600_keydata_strobe_r(machine());
+ break;
+
+ case 0x08: case 0x09: case 0x0A: case 0x0B:
+ case 0x0C: case 0x0D: case 0x0E: case 0x0F:
+ /* modifier keys */
+ result = 0x7d;
+ break;
+
+ case 0x10: case 0x11: case 0x12: case 0x13:
+ case 0x14: case 0x15: case 0x16: case 0x17:
+ case 0x18: case 0x19: case 0x1A: case 0x1B:
+ case 0x1C: case 0x1D: case 0x1E: case 0x1F:
+ AY3600_anykey_clearstrobe_r(machine());
+ break;
+
+ case 0x50: case 0x51: case 0x52: case 0x53:
+ case 0x54: case 0x55: case 0x56: case 0x57:
+ /* graphics softswitches */
+ if (offset & 1)
+ m_flags |= 1 << ((offset - 0x50) / 2);
+ else
+ m_flags &= ~(1 << ((offset - 0x50) / 2));
+ break;
+
+ case 0x60: case 0x61: case 0x62: case 0x63:
+ case 0x64: case 0x65: case 0x66: case 0x67:
+ case 0x68: case 0x69: case 0x6A: case 0x6B:
+ case 0x6C: case 0x6D: case 0x6E: case 0x6F:
+ /* unsure what these are */
+ result = 0x00;
+ break;
+
+ case 0xC0: case 0xC1: case 0xC2: case 0xC3:
+ case 0xC4: case 0xC5: case 0xC6: case 0xC7:
+ case 0xC8: case 0xC9: case 0xCA: case 0xCB:
+ case 0xCC: case 0xCD: case 0xCE: case 0xCF:
+ /* profile */
+ result = apple3_profile_r(offset);
+ break;
+
+ case 0xD0: case 0xD1: case 0xD2: case 0xD3:
+ case 0xD4: case 0xD5: case 0xD6: case 0xD7:
+ /* external drive stuff */
+ if (offset & 1)
+ m_flags |= VAR_EXTA0 << ((offset - 0xD0) / 2);
+ else
+ m_flags &= ~(VAR_EXTA0 << ((offset - 0xD0) / 2));
+ apple3_update_drives(machine().device("fdc"));
+ result = 0x00;
+ break;
+
+ case 0xDB:
+ apple3_write_charmem(machine());
+ break;
+
+ case 0xE0: case 0xE1: case 0xE2: case 0xE3:
+ case 0xE4: case 0xE5: case 0xE6: case 0xE7:
+ case 0xE8: case 0xE9: case 0xEA: case 0xEB:
+ case 0xEC: case 0xED: case 0xEE: case 0xEF:
+ result = applefdc_r(fdc, offset);
+ break;
+
+ case 0xF0:
+ case 0xF1:
+ case 0xF2:
+ case 0xF3:
+ result = acia->read(space, offset & 0x03);
+ break;
+ }
+ return result;
+}
+
+
+
+WRITE8_MEMBER(apple3_state::apple3_c0xx_w)
+{
+ acia6551_device *acia = machine().device<acia6551_device>("acia");
+ device_t *fdc = machine().device("fdc");
+ switch(offset)
+ {
+ case 0x10: case 0x11: case 0x12: case 0x13:
+ case 0x14: case 0x15: case 0x16: case 0x17:
+ case 0x18: case 0x19: case 0x1A: case 0x1B:
+ case 0x1C: case 0x1D: case 0x1E: case 0x1F:
+ AY3600_anykey_clearstrobe_r(machine());
+ break;
+
+ case 0x50: case 0x51: case 0x52: case 0x53:
+ case 0x54: case 0x55: case 0x56: case 0x57:
+ /* graphics softswitches */
+ if (offset & 1)
+ m_flags |= 1 << ((offset - 0x50) / 2);
+ else
+ m_flags &= ~(1 << ((offset - 0x50) / 2));
+ break;
+
+ case 0xC0: case 0xC1: case 0xC2: case 0xC3:
+ case 0xC4: case 0xC5: case 0xC6: case 0xC7:
+ case 0xC8: case 0xC9: case 0xCA: case 0xCB:
+ case 0xCC: case 0xCD: case 0xCE: case 0xCF:
+ /* profile */
+ apple3_profile_w(offset, data);
+ break;
+
+ case 0xD0: case 0xD1: case 0xD2: case 0xD3:
+ case 0xD4: case 0xD5: case 0xD6: case 0xD7:
+ /* external drive stuff */
+ if (offset & 1)
+ m_flags |= VAR_EXTA0 << ((offset - 0xD0) / 2);
+ else
+ m_flags &= ~(VAR_EXTA0 << ((offset - 0xD0) / 2));
+ apple3_update_drives(machine().device("fdc"));
+ break;
+
+ case 0xDB:
+ apple3_write_charmem(machine());
+ break;
+
+ case 0xE0: case 0xE1: case 0xE2: case 0xE3:
+ case 0xE4: case 0xE5: case 0xE6: case 0xE7:
+ case 0xE8: case 0xE9: case 0xEA: case 0xEB:
+ case 0xEC: case 0xED: case 0xEE: case 0xEF:
+ applefdc_w(fdc, offset, data);
+ break;
+
+ case 0xF0:
+ case 0xF1:
+ case 0xF2:
+ case 0xF3:
+ acia->write(space, offset & 0x03, data);
+ break;
+ }
+}
+
+INTERRUPT_GEN( apple3_interrupt )
+{
+ via6522_device *via_1 = device->machine().device<via6522_device>("via6522_1");
+
+ via_1->write_ca2((AY3600_keydata_strobe_r(device->machine()) & 0x80) ? 1 : 0);
+ via_1->write_cb1(device->machine().primary_screen->vblank());
+ via_1->write_cb2(device->machine().primary_screen->vblank());
+}
+
+
+
+static UINT8 *apple3_bankaddr(running_machine &machine,UINT16 bank, offs_t offset)
+{
+ if (bank != (UINT16) ~0)
+ {
+ bank %= machine.device<ram_device>(RAM_TAG)->size() / 0x8000;
+ if ((bank + 1) == (machine.device<ram_device>(RAM_TAG)->size() / 0x8000))
+ bank = 0x02;
+ }
+ offset += ((offs_t) bank) * 0x8000;
+ offset %= machine.device<ram_device>(RAM_TAG)->size();
+ return &machine.device<ram_device>(RAM_TAG)->pointer()[offset];
+}
+
+
+
+static void apple3_setbank(running_machine &machine,const char *mame_bank, UINT16 bank, offs_t offset)
+{
+ UINT8 *ptr;
+ apple3_state *state = machine.driver_data<apple3_state>();
+ ptr = apple3_bankaddr(machine,bank, offset);
+ state->membank(mame_bank)->set_base(ptr);
+
+ #if 0
+ if (LOG_MEMORY)
+ {
+ #ifdef PTR64
+ //logerror("\tbank %s --> %02x/%04x [0x%08lx]\n", mame_bank, (unsigned) bank, (unsigned)offset, ptr - machine.device<ram_device>(RAM_TAG)->pointer());
+ #else
+ logerror("\tbank %s --> %02x/%04x [0x%08lx]\n", mame_bank, (unsigned) bank, (unsigned)offset, ptr - machine.device<ram_device>(RAM_TAG)->pointer());
+ #endif
+ }
+ #endif
+}
+
+
+
+static UINT8 *apple3_get_zpa_addr(running_machine &machine,offs_t offset)
+{
+ apple3_state *state = machine.driver_data<apple3_state>();
+ state->m_zpa = (((offs_t) state->m_via_0_b) * 0x100) + offset;
+
+ if (state->m_via_0_b < 0x20)
+ return apple3_bankaddr(machine,~0, state->m_zpa);
+ else if (state->m_via_0_b > 0x9F)
+ return apple3_bankaddr(machine,~0, state->m_zpa - 0x8000);
+ else
+ return apple3_bankaddr(machine,state->m_via_1_a, state->m_zpa - 0x2000);
+}
+
+
+
+READ8_MEMBER(apple3_state::apple3_00xx_r)
+{
+ return *apple3_get_zpa_addr(machine(),offset);
+}
+
+
+
+WRITE8_MEMBER(apple3_state::apple3_00xx_w)
+{
+ *apple3_get_zpa_addr(machine(),offset) = data;
+}
+
+
+
+static void apple3_update_memory(running_machine &machine)
+{
+ apple3_state *state = machine.driver_data<apple3_state>();
+ UINT16 bank;
+ UINT8 page;
+ address_space* space = machine.device("maincpu")->memory().space(AS_PROGRAM);
+
+ if (LOG_MEMORY)
+ {
+ logerror("apple3_update_memory(): via_0_b=0x%02x via_1_a=0x0x%02x\n", state->m_via_0_b, state->m_via_1_a);
+ }
+
+ machine.device("maincpu")->set_unscaled_clock((state->m_via_0_a & 0x80) ? 1000000 : 2000000);
+
+ /* bank 2 (0100-01FF) */
+ if (!(state->m_via_0_a & 0x04))
+ {
+ if (state->m_via_0_b < 0x20)
+ {
+ bank = ~0; /* system bank */
+ page = state->m_via_0_b ^ 0x01;
+ }
+ else if (state->m_via_0_b >= 0xA0)
+ {
+ bank = ~0; /* system bank */
+ page = (state->m_via_0_b ^ 0x01) - 0x80;
+ }
+ else
+ {
+ bank = state->m_via_1_a;
+ page = (state->m_via_0_b ^ 0x01) - 0x20;
+ }
+ }
+ else
+ {
+ bank = ~0;
+ page = 0x01;
+ }
+ apple3_setbank(machine,"bank2", bank, ((offs_t) page) * 0x100);
+
+ /* bank 3 (0200-1FFF) */
+ apple3_setbank(machine,"bank3", ~0, 0x0200);
+
+ /* bank 4 (2000-9FFF) */
+ apple3_setbank(machine,"bank4", state->m_via_1_a, 0x0000);
+
+ /* bank 5 (A000-BFFF) */
+ apple3_setbank(machine,"bank5", ~0, 0x2000);
+
+ /* install bank 8 (C000-CFFF) */
+ if (state->m_via_0_a & 0x40)
+ {
+ space->install_read_handler(0xC000, 0xC0FF, read8_delegate(FUNC(apple3_state::apple3_c0xx_r),state));
+ space->install_write_handler(0xC000, 0xC0FF, write8_delegate(FUNC(apple3_state::apple3_c0xx_w),state));
+ }
+ else
+ {
+ space->install_read_bank(0xC000, 0xC0FF, "bank8");
+ if (state->m_via_0_a & 0x08)
+ space->unmap_write(0xC000, 0xC0FF);
+ else
+ space->install_write_bank(0xC000, 0xC0FF, "bank8");
+ apple3_setbank(machine,"bank8", ~0, 0x4000);
+ }
+
+ /* install bank 9 (C100-C4FF) */
+ if (state->m_via_0_a & 0x40)
+ {
+ space->nop_readwrite(0xC100, 0xC4FF);
+ }
+ else
+ {
+ space->install_read_bank(0xC100, 0xC4FF, "bank9");
+ if (state->m_via_0_a & 0x08)
+ space->unmap_write(0xC100, 0xC4FF);
+ else
+ space->install_write_bank(0xC100, 0xC4FF, "bank9");
+ apple3_setbank(machine,"bank9", ~0, 0x4100);
+ }
+
+ /* install bank 10 (C500-C7FF) */
+ space->install_read_bank(0xC500, 0xC7FF, "bank10");
+ if (state->m_via_0_a & 0x08)
+ space->unmap_write(0xC500, 0xC7FF);
+ else
+ space->install_write_bank(0xC500, 0xC7FF, "bank10");
+ apple3_setbank(machine,"bank10", ~0, 0x4500);
+
+ /* install bank 11 (C800-CFFF) */
+ if (state->m_via_0_a & 0x40)
+ {
+ space->nop_readwrite(0xC800, 0xCFFF);
+ }
+ else
+ {
+ space->install_read_bank(0xC800, 0xCFFF, "bank11");
+ if (state->m_via_0_a & 0x08)
+ space->unmap_write(0xC800, 0xCFFF);
+ else
+ space->install_write_bank(0xC800, 0xCFFF, "bank11");
+ apple3_setbank(machine,"bank11", ~0, 0x4800);
+ }
+
+ /* install bank 6 (D000-EFFF) */
+ space->install_read_bank(0xD000, 0xEFFF, "bank6");
+ if (state->m_via_0_a & 0x08)
+ space->unmap_write(0xD000, 0xEFFF);
+ else
+ space->install_write_bank(0xD000, 0xEFFF, "bank6");
+ apple3_setbank(machine,"bank6", ~0, 0x5000);
+
+ /* install bank 7 (F000-FFFF) */
+ space->install_read_bank(0xF000, 0xFFFF, "bank7");
+ if (state->m_via_0_a & 0x09)
+ space->unmap_write(0xF000, 0xFFFF);
+ else
+ space->install_write_bank(0xF000, 0xFFFF, "bank7");
+ if (state->m_via_0_a & 0x01)
+ state->membank("bank7")->set_base(machine.root_device().memregion("maincpu")->base());
+ else
+ apple3_setbank(machine,"bank7", ~0, 0x7000);
+
+ /* reinstall VIA handlers */
+ {
+ via6522_device *via_0 = space->machine().device<via6522_device>("via6522_0");
+ via6522_device *via_1 = space->machine().device<via6522_device>("via6522_1");
+
+ space->install_readwrite_handler(0xFFD0, 0xFFDF, 0, 0, read8_delegate(FUNC(via6522_device::read),via_0), write8_delegate(FUNC(via6522_device::write),via_0));
+ space->install_readwrite_handler(0xFFE0, 0xFFEF, 0, 0, read8_delegate(FUNC(via6522_device::read),via_1), write8_delegate(FUNC(via6522_device::write),via_1));
+ }
+}
+
+
+
+static void apple3_via_out(running_machine &machine, UINT8 *var, UINT8 data)
+{
+ if (*var != data)
+ {
+ *var = data;
+ apple3_update_memory(machine);
+ }
+}
+
+
+/* these are here to appease the Apple /// confidence tests */
+static READ8_DEVICE_HANDLER(apple3_via_1_in_a) { return ~0; }
+static READ8_DEVICE_HANDLER(apple3_via_1_in_b) { return ~0; }
+
+static WRITE8_DEVICE_HANDLER(apple3_via_0_out_a)
+{
+ apple3_state *state = device->machine().driver_data<apple3_state>();
+ apple3_via_out(device->machine(), &state->m_via_0_a, data);
+}
+
+static WRITE8_DEVICE_HANDLER(apple3_via_0_out_b)
+{
+ apple3_state *state = device->machine().driver_data<apple3_state>();
+ apple3_via_out(device->machine(), &state->m_via_0_b, data);
+}
+
+static WRITE8_DEVICE_HANDLER(apple3_via_1_out_a)
+{
+ apple3_state *state = device->machine().driver_data<apple3_state>();
+ apple3_via_out(device->machine(), &state->m_via_1_a, data);
+}
+
+static WRITE8_DEVICE_HANDLER(apple3_via_1_out_b)
+{
+ apple3_state *state = device->machine().driver_data<apple3_state>();
+ apple3_via_out(device->machine(), &state->m_via_1_b, data);
+}
+
+static void apple2_via_1_irq_func(device_t *device, int state)
+{
+ apple3_state *drvstate = device->machine().driver_data<apple3_state>();
+ if (!drvstate->m_via_1_irq && state)
+ {
+ cputag_set_input_line(device->machine(), "maincpu", M6502_IRQ_LINE, ASSERT_LINE);
+ cputag_set_input_line(device->machine(), "maincpu", M6502_IRQ_LINE, CLEAR_LINE);
+ }
+ drvstate->m_via_1_irq = state;
+}
+
+const via6522_interface apple3_via_0_intf =
+{
+ DEVCB_NULL, /* in_a_func */
+ DEVCB_NULL, /* in_b_func */
+ DEVCB_NULL, /* in_ca1_func */
+ DEVCB_NULL, /* in_cb1_func */
+ DEVCB_NULL, /* in_ca2_func */
+ DEVCB_NULL, /* in_cb2_func */
+ DEVCB_HANDLER(apple3_via_0_out_a), /* out_a_func */
+ DEVCB_HANDLER(apple3_via_0_out_b), /* out_b_func */
+ DEVCB_NULL, /* out_ca1_func */
+ DEVCB_NULL, /* out_cb1_func */
+ DEVCB_NULL, /* out_ca2_func */
+ DEVCB_NULL, /* out_cb2_func */
+ DEVCB_NULL /* irq_func */
+};
+
+const via6522_interface apple3_via_1_intf =
+{
+ DEVCB_HANDLER(apple3_via_1_in_a), /* in_a_func */
+ DEVCB_HANDLER(apple3_via_1_in_b), /* in_b_func */
+ DEVCB_NULL, /* in_ca1_func */
+ DEVCB_NULL, /* in_cb1_func */
+ DEVCB_NULL, /* in_ca2_func */
+ DEVCB_NULL, /* in_cb2_func */
+ DEVCB_HANDLER(apple3_via_1_out_a), /* out_a_func */
+ DEVCB_HANDLER(apple3_via_1_out_b), /* out_b_func */
+ DEVCB_NULL, /* out_ca1_func */
+ DEVCB_NULL, /* out_cb1_func */
+ DEVCB_NULL, /* out_ca2_func */
+ DEVCB_NULL, /* out_cb2_func */
+ DEVCB_LINE(apple2_via_1_irq_func) /* irq_func */
+};
+
+
+
+MACHINE_RESET( apple3 )
+{
+}
+
+
+
+static UINT8 *apple3_get_indexed_addr(running_machine &machine,offs_t offset)
+{
+ apple3_state *state = machine.driver_data<apple3_state>();
+ UINT8 n;
+ UINT8 *result = NULL;
+
+ if ((state->m_via_0_b >= 0x18) && (state->m_via_0_b <= 0x1F))
+ {
+ n = *apple3_bankaddr(machine,~0, state->m_zpa ^ 0x0C00);
+
+ if (LOG_INDXADDR)
+ {
+ if (state->m_last_n != n)
+ {
+ logerror("indxaddr: zpa=0x%04x n=0x%02x\n", state->m_zpa, n);
+ state->m_last_n = n;
+ }
+ }
+
+ if (n == 0x8F)
+ {
+ /* get at that special ram under the VIAs */
+ if ((offset >= 0xFFD0) && (offset <= 0xFFEF))
+ result = apple3_bankaddr(machine,~0, offset & 0x7FFF);
+ else if (offset < 0x2000)
+ result = apple3_bankaddr(machine,~0, offset - 0x2000);
+ else if (offset > 0x9FFF)
+ result = apple3_bankaddr(machine,~0, offset - 0x8000);
+ else
+ result = &machine.device<ram_device>(RAM_TAG)->pointer()[offset - 0x2000];
+ }
+ else if ((n >= 0x80) && (n <= 0x8E))
+ {
+ if (offset < 0x0100)
+ result = apple3_bankaddr(machine,~0, ((offs_t) state->m_via_0_b) * 0x100 + offset);
+ else
+ result = apple3_bankaddr(machine,n, offset);
+ }
+ else if (n == 0xFF)
+ {
+ if (offset < 0x2000)
+ result = apple3_bankaddr(machine,~0, offset - 0x2000);
+ else if (offset < 0xA000)
+ result = apple3_bankaddr(machine,state->m_via_1_a, offset - 0x2000);
+ else if (offset < 0xC000)
+ result = apple3_bankaddr(machine,~0, offset - 0x8000);
+ else if (offset < 0xD000)
+ result = NULL;
+ else if (offset < 0xF000)
+ result = apple3_bankaddr(machine,~0, offset - 0x8000);
+ else
+ result = (UINT8 *) ~0;
+ }
+ else if (offset < 0x0100)
+ {
+ result = apple3_bankaddr(machine,~0, ((offs_t) state->m_via_0_b) * 0x100 + offset);
+ }
+ }
+ else if ((offset >= 0xF000) && (state->m_via_0_a & 0x01))
+ {
+#if 0
+ /* The Apple /// Diagnostics seems to expect that indexed writes
+ * always write to RAM. That image jumps to an address that is
+ * undefined unless this code is enabled. However, the Sara
+ * emulator does not have corresponding code here, though Chris
+ * Smolinski does not rule out the possibility
+ */
+ result = apple3_bankaddr(machine,~0, offset - 0x8000);
+#endif
+ }
+
+ return result;
+}
+
+
+
+READ8_MEMBER(apple3_state::apple3_indexed_read)
+{
+ UINT8 result;
+ UINT8 *addr;
+
+ addr = apple3_get_indexed_addr(machine(),offset);
+ if (!addr)
+ result = space.read_byte(offset);
+ else if (addr != (UINT8 *) ~0)
+ result = *addr;
+ else
+ result = memregion("maincpu")->base()[offset % memregion("maincpu")->bytes()];
+ return result;
+}
+
+
+
+WRITE8_MEMBER(apple3_state::apple3_indexed_write)
+{
+ UINT8 *addr;
+
+ addr = apple3_get_indexed_addr(machine(),offset);
+ if (!addr)
+ space.write_byte(offset, data);
+ else if (addr != (UINT8 *) ~0)
+ *addr = data;
+}
+
+
+
+DIRECT_UPDATE_MEMBER(apple3_state::apple3_opbase)
+{
+ UINT8 *opptr;
+
+ if ((address & 0xFF00) == 0x0000)
+ {
+ opptr = apple3_get_zpa_addr(machine(),address);
+ direct.explicit_configure(address, address, ~0, opptr - address);
+ address = ~0;
+ }
+ return address;
+}
+
+
+
+static void apple3_update_drives(device_t *device)
+{
+ apple3_state *state = device->machine().driver_data<apple3_state>();
+ int enable_mask = 0x00;
+
+ if (state->m_enable_mask & 0x01)
+ enable_mask |= 0x01;
+
+ if (state->m_enable_mask & 0x02)
+ {
+ switch(state->m_flags & (VAR_EXTA0 | VAR_EXTA1))
+ {
+ case VAR_EXTA0:
+ enable_mask |= 0x02;
+ break;
+ case VAR_EXTA1:
+ enable_mask |= 0x04;
+ break;
+ case VAR_EXTA1|VAR_EXTA0:
+ enable_mask |= 0x08;
+ break;
+ }
+ }
+
+ apple525_set_enable_lines(device,enable_mask);
+}
+
+
+
+static void apple3_set_enable_lines(device_t *device,int enable_mask)
+{
+ apple3_state *state = device->machine().driver_data<apple3_state>();
+ state->m_enable_mask = enable_mask;
+ apple3_update_drives(device);
+}
+
+
+
+const applefdc_interface apple3_fdc_interface =
+{
+ apple525_set_lines,
+ apple3_set_enable_lines,
+ apple525_read_data,
+ apple525_write_data
+};
+
+
+
+DRIVER_INIT_MEMBER(apple3_state,apple3)
+{
+ /* hack to get around VIA problem */
+ memregion("maincpu")->base()[0x0685] = 0x00;
+
+ m_enable_mask = 0;
+ apple3_update_drives(machine().device("fdc"));
+
+ AY3600_init(machine());
+
+ apple3_profile_init();
+
+ m_flags = 0;
+ m_via_0_a = ~0;
+ m_via_1_a = ~0;
+ m_via_1_irq = 0;
+ apple3_update_memory(machine());
+
+ machine().device("maincpu")->memory().space(AS_PROGRAM)->set_direct_update_handler(direct_update_delegate(FUNC(apple3_state::apple3_opbase), this));
+}