summaryrefslogtreecommitdiffstatshomepage
path: root/trunk/src/mame/drivers/bfm_sc4h.c
diff options
context:
space:
mode:
Diffstat (limited to 'trunk/src/mame/drivers/bfm_sc4h.c')
-rw-r--r--trunk/src/mame/drivers/bfm_sc4h.c982
1 files changed, 982 insertions, 0 deletions
diff --git a/trunk/src/mame/drivers/bfm_sc4h.c b/trunk/src/mame/drivers/bfm_sc4h.c
new file mode 100644
index 00000000000..5faaf5ad9bd
--- /dev/null
+++ b/trunk/src/mame/drivers/bfm_sc4h.c
@@ -0,0 +1,982 @@
+/*
+
+ Scorpion 4 Hardware Platform (c)1996 Bell Fruit Manufacturing
+
+ Skeleton Driver
+
+ THIS DRIVER IS NOT WORKING
+
+ -----------------
+
+ Scorpion 4:::
+
+ Main CPU is a MC68307FG16, present on Motherboard
+
+ Configuration is SC4 motherboard + game card
+
+ The game card contains the program roms, sound rom and YMZ280B
+
+ Adder 4 video board adds an additional card with a MC68340PV25E (25.175Mhz)
+
+ -------------------------------
+
+ This file contains the hardware emulation, for the supported sets
+ see bfm_sc4.c
+
+ ---
+ note, if game says 'read meters' simply press CTRL then 'B'
+ I think we're stuck in some king of free play test mode so Start 1 will spin and give you credit
+
+*/
+
+
+
+#include "emu.h"
+#include "cpu/m68000/m68000.h"
+#include "includes/bfm_sc45.h"
+#include "sound/ymz280b.h"
+#include "machine/68681.h"
+#include "bfm_sc4.lh"
+#include "machine/bfm_bd1.h"
+#include "video/awpvid.h"
+
+UINT8 read_input_matrix(running_machine &machine, int row)
+{
+
+ static const char *const portnames[16] = { "IN-0", "IN-1", "IN-2", "IN-3", "IN-4", "IN-5", "IN-6", "IN-7", "IN-8", "IN-9", "IN-A", "IN-B" };
+ UINT8 value;
+
+ if (row<4)
+ {
+ value = (machine.root_device().ioport(portnames[row])->read_safe(0x00) & 0x1f) + ((machine.root_device().ioport(portnames[row+8])->read_safe(0x00) & 0x07) << 5);
+ }
+ else
+ {
+ value = (machine.root_device().ioport(portnames[row])->read_safe(0x00) & 0x1f) + ((machine.root_device().ioport(portnames[row+4])->read_safe(0x00) & 0x18) << 2);
+ }
+
+ return value;
+}
+
+READ16_MEMBER(sc4_state::sc4_cs1_r)
+{
+ int pc = cpu_get_pc(&space.device());
+
+ if (offset<0x100000/2)
+ {
+ // allow some sets to boot, should probably return this data on Mbus once we figure out what it is
+ if ((pc == m_chk41addr) && (offset == m_chk41addr>>1))
+ {
+ UINT32 r_A0 = cpu_get_reg(&space.device(), M68K_A0);
+ UINT32 r_A1 = cpu_get_reg(&space.device(), M68K_A1);
+ UINT32 r_D1 = cpu_get_reg(&space.device(), M68K_D1);
+
+ if (r_D1 == 0x7)
+ {
+ bool valid = true;
+ for (int i=0;i<8;i++)
+ {
+ UINT8 code = space.read_byte(r_A0+i);
+ if (code != 0xff) // assume our mbus code just returns 0xff for now..
+ valid = false;
+ }
+
+ if (valid && m_dochk41)
+ {
+ m_dochk41 = false;
+ // the value is actually random.. probably based on other reads
+ // making this a comparison?
+ printf("Ident code? ");
+ for (int i=0;i<8;i++)
+ {
+ UINT8 code = space.read_byte(r_A1+i);
+ printf("%02x",code);
+ space.write_byte(r_A0+i, code);
+ }
+ printf("\n");
+ }
+ }
+ }
+
+
+ return m_cpuregion[offset];
+ }
+ else
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d\n", pc, offset*2, mem_mask, 1);
+
+ return 0x0000;
+}
+
+READ16_MEMBER(sc4_state::sc4_mem_r)
+{
+ int pc = cpu_get_pc(&space.device());
+ int cs = m68307_get_cs(m_maincpu, offset * 2);
+ int base = 0, end = 0, base2 = 0, end2 = 0;
+// if (!(debugger_access())) printf("cs is %d\n", cs);
+ UINT16 retvalue;
+
+
+ switch ( cs )
+ {
+ case 1:
+ return sc4_cs1_r(space,offset,mem_mask);
+
+
+
+ case 2:
+ base = 0x800000/2;
+ end = base + 0x10000 / 2;
+
+ base2 = 0x810000/2;
+ end2 = base2 + 0x10000 / 2;
+
+
+ if ((offset>=base) && (offset<end))
+ {
+ offset-=base;
+ return(m_mainram[offset]);
+ }
+ else if ((offset>=base2) && (offset<end2))
+ {
+ offset-=base2;
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d\n", pc, offset*2, mem_mask, cs);
+ int addr = (offset<<1);
+
+ if (addr < 0x0080)
+ {
+ UINT16 retvalue = 0x0000;
+ if (mem_mask&0xff00)
+ {
+ logerror("mem_mask&0xff00 unhandled\n");
+ }
+
+ if (mem_mask&0x00ff)
+ {
+ retvalue = read_input_matrix(machine(), (addr & 0x00f0)>>4);
+ }
+ return retvalue;
+ }
+ else
+ {
+ switch (addr)
+ {
+ case 0x0240:
+ retvalue = 0x00ff;
+
+ if (mem_mask&0xff00)
+ {
+ retvalue |= (sec.read_data_line() << (6+8));
+ retvalue |= 0xbf00; // coin?
+ //printf("%08x maincpu read access offset %08x mem_mask %04x cs %d (LAMPS etc.)\n", pc, offset*2, mem_mask, cs);
+ }
+ return retvalue;
+
+ case 0x02e0:
+ return 0x0080;//space.machine().rand();;
+
+ case 0x1000:
+ return 0x0000;//space.machine().rand();;
+
+ case 0x1010:
+ return 0x0000;//space.machine().rand();;
+
+ case 0x1020:
+ return 0x0000;//space.machine().rand();;
+
+ case 0x1030:
+ return 0x0000;//space.machine().rand();;
+
+ case 0x1040: // door switch, test switch etc.
+ return 0x0000;//space.machine().rand();;
+
+ case 0x1244:
+ return ymz280b_r(m_ymz,0);
+
+ case 0x1246:
+ return ymz280b_r(m_ymz,1);
+
+ default:
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d (LAMPS etc.)\n", pc, offset*2, mem_mask, cs);
+ }
+ }
+ }
+ else
+ {
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d\n", pc, offset*2, mem_mask, cs);
+ }
+ break;
+
+ case 3:
+ base = 0xc00000/2;
+ end = base + 0x20 / 2;
+
+ if ((offset>=base) && (offset<end))
+ {
+ offset-=base;
+ return duart68681_r(m_duart,offset);
+ }
+ else
+ {
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d\n", pc, offset*2, mem_mask, cs);
+ return 0x0000;
+ }
+
+ break;
+
+ case 4:
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d\n", pc, offset*2, mem_mask, cs);
+ return 0x0000;//0xffff;
+ break;
+
+ default:
+ logerror("%08x maincpu read access offset %08x mem_mask %04x cs %d (invalid?)\n", pc, offset*2, mem_mask, cs);
+
+ }
+
+ return 0x0000;
+}
+
+static WRITE8_HANDLER( bfm_sc4_reel4_w );
+
+WRITE8_MEMBER(sc4_state::mux_output_w)
+{
+ int i;
+ int off = offset<<3;
+
+ for (i=0; i<8; i++)
+ output_set_lamp_value(off+i, ((data & (1 << i)) != 0));
+
+
+ output_set_indexed_value("matrix", off+i, ((data & (1 << i)) != 0));
+}
+
+WRITE8_MEMBER(sc4_state::mux_output2_w)
+{
+ int i;
+ int off = offset<<3;
+
+ // some games use this as a matrix port (luckb etc.)
+ for (i=0; i<8; i++)
+ {
+ output_set_indexed_value("matrix", off+i, ((data & (1 << i)) != 0));
+ }
+
+ // others drive 7-segs with it.. so rendering it there as well in our debug layouts
+
+ // todo: reorder properly!
+ UINT8 bf7segdata = BITSWAP8(data,7,6,5,4,3,2,1,0);
+ output_set_digit_value(offset, bf7segdata);
+}
+
+WRITE16_MEMBER(sc4_state::sc4_mem_w)
+{
+ int pc = cpu_get_pc(&space.device());
+ int cs = m68307_get_cs(m_maincpu, offset * 2);
+ int base = 0, end = 0, base2 = 0, end2 = 0;
+
+ switch ( cs )
+ {
+ case 1:
+ if (offset<0x100000/2)
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d (ROM WRITE?!)\n", pc, offset*2, data, mem_mask, cs);
+ else
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d\n", pc, offset*2, data, mem_mask, cs);
+
+ break;
+
+ case 2:
+ base = 0x800000/2;
+ end = base + 0x10000 / 2;
+ base2 = 0x810000/2;
+ end2 = base2 + 0x10000 / 2;
+
+ if ((offset>=base) && (offset<end))
+ {
+ offset-=base;
+ COMBINE_DATA(&m_mainram[offset]);
+ }
+ else if ((offset>=base2) && (offset<end2))
+ {
+ offset-=base2;
+ int addr = (offset<<1);
+
+ if (addr < 0x0200)
+ {
+
+ if (mem_mask&0xff00)
+ {
+ logerror("lamp write mem_mask&0xff00 unhandled\n");
+ }
+
+ if (mem_mask&0x00ff)
+ { // lamps
+ mux_output_w(space, (addr & 0x01f0)>>4, data);
+ }
+
+ }
+ else if ((addr >= 0x1000) && (addr < 0x1200))
+ {
+ if (mem_mask&0xff00)
+ {
+ logerror("lamp write mem_mask&0xff00 unhandled\n");
+ }
+
+ if (mem_mask&0x00ff)
+ { // lamps
+ mux_output2_w(space, (addr & 0x01f0)>>4, data);
+ }
+ }
+ else
+ {
+ switch (addr)
+ {
+ case 0x0330:
+ logerror("%08x meter write %04x\n",pc, data);
+ //m_meterstatus = (m_meterstatus&0xc0) | (data & 0x3f);
+ sec.write_clock_line(~data&0x20);
+ break;
+
+ case 0x1248:
+ ymz280b_w(m_ymz,0, data & 0xff);
+ break;
+
+ case 0x124a:
+ ymz280b_w(m_ymz,1, data & 0xff);
+ break;
+
+ case 0x1330:
+ bfm_sc4_reel4_w(&space,0,data&0xf);
+ //m_meterstatus = (m_meterstatus&0x3f) | ((data & 0x30) << 2);
+ sec.write_data_line(~data&0x10);
+ break;
+
+ default:
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d (LAMPS etc.)\n", pc, offset*2, data, mem_mask, cs);
+ }
+ }
+ }
+ else
+ {
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d\n", pc, offset*2, data, mem_mask, cs);
+ }
+ break;
+
+ case 3:
+ base = 0xc00000/2;
+ end = base + 0x20 / 2;
+
+ if ((offset>=base) && (offset<end))
+ {
+ offset-=base;
+ duart68681_w(m_duart,offset,data&0x00ff);
+ }
+ else
+ {
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d\n", pc, offset*2, data, mem_mask, cs);
+ }
+
+ break;
+
+ case 4:
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d\n", pc, offset*2, data, mem_mask, cs);
+ break;
+
+ default:
+ logerror("%08x maincpu write access offset %08x data %04x mem_mask %04x cs %d (invalid?)\n", pc, offset*2, data, mem_mask, cs);
+ }
+}
+
+static ADDRESS_MAP_START( sc4_map, AS_PROGRAM, 16, sc4_state )
+ AM_RANGE(0x0000000, 0x0fffff) AM_READ(sc4_cs1_r) // technically we should be going through the cs handler, but this is always set to ROM, and assuming that is a lot faster
+ AM_RANGE(0x0000000, 0xffffff) AM_READWRITE(sc4_mem_r, sc4_mem_w)
+ADDRESS_MAP_END
+
+
+
+
+READ32_MEMBER(sc4_adder4_state::adder4_mem_r)
+{
+ int pc = cpu_get_pc(&space.device());
+ int cs = m68340_get_cs(m_adder4cpu, offset * 4);
+
+ switch ( cs )
+ {
+ case 1:
+ return m_adder4cpuregion[offset];
+
+ case 2:
+ offset &=0x3fff;
+ return m_adder4ram[offset];
+
+ default:
+ logerror("%08x adder4cpu read access offset %08x mem_mask %08x cs %d\n", pc, offset*4, mem_mask, cs);
+
+ }
+
+ return 0x0000;
+}
+
+WRITE32_MEMBER(sc4_adder4_state::adder4_mem_w)
+{
+ int pc = cpu_get_pc(&space.device());
+ int cs = m68340_get_cs(m_adder4cpu, offset * 4);
+
+ switch ( cs )
+ {
+ default:
+ logerror("%08x adder4cpu write access offset %08x data %08x mem_mask %08x cs %d\n", pc, offset*4, data, mem_mask, cs);
+
+ case 2:
+ offset &=0x3fff;
+ COMBINE_DATA(&m_adder4ram[offset]);
+ break;
+
+
+ }
+
+}
+
+static ADDRESS_MAP_START( sc4_adder4_map, AS_PROGRAM, 32, sc4_adder4_state )
+ AM_RANGE(0x00000000, 0xffffffff) AM_READWRITE(adder4_mem_r, adder4_mem_w)
+ADDRESS_MAP_END
+
+
+
+
+
+
+
+
+void bfm_sc4_reset_serial_vfd(running_machine &machine)
+{
+ sc4_state *state = machine.driver_data<sc4_state>();
+
+ BFM_BD1_reset(0);
+ BFM_BD1_draw(0);
+ state->vfd_old_clock = false;
+}
+
+void bfm_sc4_write_serial_vfd(running_machine &machine, bool cs, bool clock, bool data)
+{
+ sc4_state *state = machine.driver_data<sc4_state>();
+
+ // if we're turned on
+ if ( cs )
+ {
+ if ( !state->vfd_enabled )
+ {
+ bfm_sc4_reset_serial_vfd(machine);
+ state->vfd_old_clock = clock;
+ state->vfd_enabled = true;
+ }
+ else
+ {
+ // if the clock line changes
+ if ( clock != state->vfd_old_clock )
+ {
+ if ( !clock )
+ {
+ state->vfd_ser_value <<= 1;
+ if (data) state->vfd_ser_value |= 1;
+
+ state->vfd_ser_count++;
+ if ( state->vfd_ser_count == 8 )
+ {
+ state->vfd_ser_count = 0;
+ BFM_BD1_newdata(0, state->vfd_ser_value);
+ BFM_BD1_draw(0);
+ }
+ }
+ state->vfd_old_clock = clock;
+ }
+ }
+ }
+ else
+ {
+ state->vfd_enabled = false;
+ }
+}
+
+
+void bfm_sc4_68307_porta_w(address_space *space, bool dedicated, UINT8 data, UINT8 line_mask)
+{
+ sc4_state *state = space->machine().driver_data<sc4_state>();
+
+ state->m_reel12_latch = data;
+
+ if ( stepper_update(0, data&0x0f ) ) state->m_reel_changed |= 0x01;
+ if ( stepper_update(1, (data>>4))&0x0f ) state->m_reel_changed |= 0x02;
+
+ if ( stepper_optic_state(0) ) state->m_optic_pattern |= 0x01;
+ else state->m_optic_pattern &= ~0x01;
+ if ( stepper_optic_state(1) ) state->m_optic_pattern |= 0x02;
+ else state->m_optic_pattern &= ~0x02;
+
+ awp_draw_reel(0);
+ awp_draw_reel(1);
+}
+
+static WRITE8_HANDLER( bfm_sc4_reel3_w )
+{
+ sc4_state *state = space->machine().driver_data<sc4_state>();
+
+ state->m_reel3_latch = data;
+
+ if ( stepper_update(2, data&0x0f ) ) state->m_reel_changed |= 0x04;
+
+ if ( stepper_optic_state(2) ) state->m_optic_pattern |= 0x04;
+ else state->m_optic_pattern &= ~0x04;
+
+ awp_draw_reel(2);
+}
+
+static WRITE8_HANDLER( bfm_sc4_reel4_w )
+{
+ sc4_state *state = space->machine().driver_data<sc4_state>();
+
+ state->m_reel4_latch = data;
+
+ if ( stepper_update(3, data&0x0f ) ) state->m_reel_changed |= 0x08;
+
+ if ( stepper_optic_state(3) ) state->m_optic_pattern |= 0x08;
+ else state->m_optic_pattern &= ~0x08;
+
+ awp_draw_reel(3);
+}
+
+void bfm_sc4_68307_portb_w(address_space *space, bool dedicated, UINT16 data, UINT16 line_mask)
+{
+// if (dedicated == false)
+ {
+ int pc = cpu_get_pc(&space->device());
+ //m68ki_cpu_core *m68k = m68k_get_safe_token(&space->device());
+ // serial output to the VFD at least..
+ logerror("%08x bfm_sc4_68307_portb_w %04x %04x\n", pc, data, line_mask);
+
+ bfm_sc4_write_serial_vfd(space->machine(), (data & 0x4000)?1:0, (data & 0x1000)?1:0, !(data & 0x2000)?1:0);
+
+ bfm_sc4_reel3_w(space, 0, (data&0x0f00)>>8);
+ }
+
+}
+UINT8 bfm_sc4_68307_porta_r(address_space *space, bool dedicated, UINT8 line_mask)
+{
+ int pc = cpu_get_pc(&space->device());
+ logerror("%08x bfm_sc4_68307_porta_r\n", pc);
+ return space->machine().rand();
+}
+
+UINT16 bfm_sc4_68307_portb_r(address_space *space, bool dedicated, UINT16 line_mask)
+{
+ if (dedicated==false)
+ {
+ return 0x0000;
+ }
+ else
+ {
+ // generating certain interrupts expecteds the bit 0x8000 to be set here
+ // but it's set ot dedicated i/o, not general purpose, source?
+ return 0x8040;
+ }
+}
+
+static MACHINE_RESET( sc4 )
+{
+ sc4_state *state = machine.driver_data<sc4_state>();
+
+ int pattern =0, i;
+
+ for ( i = 0; i < state->m_reels; i++)
+ {
+ stepper_reset_position(i);
+ if ( stepper_optic_state(i) ) pattern |= 1<<i;
+ }
+
+ state->m_dochk41 = true;
+
+ state->m_optic_pattern = pattern;
+ state->sec.reset();
+}
+
+static NVRAM_HANDLER( bfm_sc4 )
+{
+ sc4_state *state = machine.driver_data<sc4_state>();
+ if ( read_or_write )
+ { // writing
+ file->write(state->m_mainram,0x10000);
+ }
+ else
+ { // reading
+ if ( file )
+ {
+ file->read(state->m_mainram,0x10000);
+ }
+ }
+}
+
+
+
+static MACHINE_START( sc4 )
+{
+ sc4_state *state = machine.driver_data<sc4_state>();
+ state->m_cpuregion = (UINT16*)state->memregion( "maincpu" )->base();
+ state->m_mainram = (UINT16*)auto_alloc_array_clear(machine, UINT16, 0x10000);
+ state->m_duart = machine.device("duart68681");
+ state->m_ymz = machine.device("ymz");
+ m68307_set_port_callbacks(machine.device("maincpu"),
+ bfm_sc4_68307_porta_r,
+ bfm_sc4_68307_porta_w,
+ bfm_sc4_68307_portb_r,
+ bfm_sc4_68307_portb_w );
+ m68307_set_duart68681(machine.device("maincpu"),machine.device("m68307_68681"));
+
+ BFM_BD1_init(0);
+
+ int reels = 6;
+ state->m_reels=reels;
+
+ for ( int n = 0; n < reels; n++ )
+ {
+ if (state->m_reel_setup[n]) stepper_config(machine, n, state->m_reel_setup[n]);
+ }
+}
+
+
+static void bfm_sc4_irqhandler(device_t *device, int state)
+{
+ logerror("YMZ280 is generating an interrupt. State=%08x\n",state);
+}
+
+static const ymz280b_interface ymz280b_config =
+{
+ bfm_sc4_irqhandler
+};
+
+
+
+void bfm_sc4_duart_irq_handler(device_t *device, int state, UINT8 vector)
+{
+ // triggers after reel tests on luckb, at the start on dnd...
+ // not sure this is right, causes some games to crash
+ logerror("bfm_sc4_duart_irq_handler\n");
+ if (state == ASSERT_LINE)
+ {
+ m68307_licr2_interrupt((legacy_cpu_device*)device->machine().device("maincpu"));
+ }
+};
+
+void bfm_sc4_duart_tx(device_t *device, int channel, UINT8 data)
+{
+ logerror("bfm_sc4_duart_tx\n");
+};
+
+
+
+UINT8 bfm_sc4_duart_input_r(device_t *device)
+{
+ sc4_state *state = device->machine().driver_data<sc4_state>();
+// printf("bfm_sc4_duart_input_r\n");
+ return state->m_optic_pattern;
+}
+
+void bfm_sc4_duart_output_w(device_t *device, UINT8 data)
+{
+// logerror("bfm_sc4_duart_output_w\n");
+ sc4_state *state = device->machine().driver_data<sc4_state>();
+
+ state->m_reel56_latch = data;
+
+ if ( stepper_update(4, data&0x0f ) ) state->m_reel_changed |= 0x10;
+ if ( stepper_update(5, (data>>4)&0x0f) ) state->m_reel_changed |= 0x20;
+
+ if ( stepper_optic_state(4) ) state->m_optic_pattern |= 0x10;
+ else state->m_optic_pattern &= ~0x10;
+ if ( stepper_optic_state(5) ) state->m_optic_pattern |= 0x20;
+ else state->m_optic_pattern &= ~0x20;
+
+ awp_draw_reel(4);
+ awp_draw_reel(5);
+}
+
+
+static const duart68681_config bfm_sc4_duart68681_config =
+{
+ bfm_sc4_duart_irq_handler,
+ bfm_sc4_duart_tx,
+ bfm_sc4_duart_input_r,
+ bfm_sc4_duart_output_w
+};
+
+
+
+void m68307_duart_irq_handler(device_t *device, int state, UINT8 vector)
+{
+ logerror("m68307_duart_irq_handler\n");
+ if (state == ASSERT_LINE)
+ {
+ m68307_serial_interrupt((legacy_cpu_device*)device->machine().device("maincpu"), vector);
+ }
+};
+
+void m68307_duart_tx(device_t *device, int channel, UINT8 data)
+{
+ if (channel==0)
+ {
+ logerror("m68307_duart_tx %02x\n",data);
+ }
+ else
+ {
+ printf("(illegal channel 1) m68307_duart_tx %02x\n",data);
+ }
+};
+
+UINT8 m68307_duart_input_r(device_t *device)
+{
+ logerror("m68307_duart_input_r\n");
+ return 0x00;
+}
+
+void m68307_duart_output_w(device_t *device, UINT8 data)
+{
+ logerror("m68307_duart_output_w %02x\n", data);
+}
+
+
+
+static const duart68681_config m68307_duart68681_config =
+{
+ m68307_duart_irq_handler,
+ m68307_duart_tx,
+ m68307_duart_input_r,
+ m68307_duart_output_w
+};
+
+
+
+MACHINE_CONFIG_START( sc4, sc4_state )
+ MCFG_CPU_ADD("maincpu", M68307, 16000000) // 68307! (EC000 core)
+ MCFG_CPU_PROGRAM_MAP(sc4_map)
+
+ // internal duart of the 68307... paired in machine start
+ MCFG_DUART68681_ADD("m68307_68681", 16000000/4, m68307_duart68681_config) // ?? Mhz
+
+ MCFG_MACHINE_START( sc4 )
+ MCFG_MACHINE_RESET( sc4 )
+
+ /* sound hardware */
+ MCFG_SPEAKER_STANDARD_MONO("mono")
+
+ MCFG_NVRAM_HANDLER(bfm_sc4)
+
+ MCFG_DUART68681_ADD("duart68681", 16000000/4, bfm_sc4_duart68681_config) // ?? Mhz
+
+
+ MCFG_DEFAULT_LAYOUT(layout_bfm_sc4)
+
+ MCFG_SOUND_ADD("ymz", YMZ280B, 16000000) // ?? Mhz
+ MCFG_SOUND_CONFIG(ymz280b_config)
+ MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0)
+MACHINE_CONFIG_END
+
+
+
+static MACHINE_START( adder4 )
+{
+ sc4_adder4_state *state = machine.driver_data<sc4_adder4_state>();
+ state->m_adder4cpuregion = (UINT32*)state->memregion( "adder4" )->base();
+ state->m_adder4ram = (UINT32*)auto_alloc_array_clear(machine, UINT32, 0x10000);
+ MACHINE_START_CALL(sc4);
+}
+
+MACHINE_CONFIG_DERIVED_CLASS( sc4_adder4, sc4, sc4_adder4_state )
+ MCFG_CPU_ADD("adder4", M68340, 25175000) // 68340 (CPU32 core)
+ MCFG_CPU_PROGRAM_MAP(sc4_adder4_map)
+
+ MCFG_MACHINE_START( adder4 )
+MACHINE_CONFIG_END
+
+
+INPUT_PORTS_START( sc4_base )
+ PORT_START("IN-0")
+ PORT_DIPNAME( 0x01, 0x00, "IN-0:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-0:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-0:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-0:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-0:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+ PORT_START("IN-1")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 )
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 )
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 )
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_BUTTON4 )
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON5 )
+
+ PORT_START("IN-2")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON6 )
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON7 )
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON8 )
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_BUTTON9 )
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_START1 ) PORT_NAME("Start 1 / P1 Button 1") // also gives you 0.50 credits at the moment, I guess because we're in freeplay?
+
+
+ PORT_START("IN-3")
+ PORT_DIPNAME( 0x01, 0x00, "IN-3:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-3:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-3:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-3:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-3:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+
+ PORT_START("IN-4")
+ PORT_DIPNAME( 0x01, 0x00, "IN-4:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-4:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-4:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-4:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-4:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+
+ PORT_START("IN-5")
+ PORT_BIT( 0x0f, IP_ACTIVE_LOW, IPT_UNUSED ) // Jackpot Key, filled in later
+ PORT_DIPNAME( 0x10, 0x00, "IN-5:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+ PORT_START("IN-6")
+ PORT_DIPNAME( 0x01, 0x00, "IN-6:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-6:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-6:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-6:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-6:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+ PORT_START("IN-7")
+ PORT_DIPNAME( 0x01, 0x00, "IN-7:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-7:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-7:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-7:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-7:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+ PORT_START("IN-8")
+ PORT_DIPNAME( 0x01, 0x00, "IN-8:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-8:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-8:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-8:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-8:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+
+ PORT_START("IN-9")
+ PORT_DIPNAME( 0x01, 0x00, "IN-9:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-9:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-9:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-9:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-9:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+
+ PORT_START("IN-a")
+ PORT_DIPNAME( 0x01, 0x00, "IN-a:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-a:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-a:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-a:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-a:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+
+
+ PORT_START("IN-b")
+ PORT_DIPNAME( 0x01, 0x00, "IN-b:0" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, "IN-b:1" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "IN-b:2" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "IN-b:3" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "IN-b:4" )
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+INPUT_PORTS_END
+
+
+
+