summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
author Angelo Salese <angelosa@users.noreply.github.com>2011-06-19 19:02:23 +0000
committer Angelo Salese <angelosa@users.noreply.github.com>2011-06-19 19:02:23 +0000
commita8c80b5a5f5df38c8080bb369c4a7c0e9f2b4b57 (patch)
tree2106f872807eba51f6b26c4cf21e48ab2e76dd95
parent79cb0586fba69b487127d41a8a6bfecc6e997e2b (diff)
Fixed NAR timing in OKIM6376 to match datasheet figures. [J. Wallace]
Fixed behaviour for OKIM6376 samples latched while their respective channel is playing (fixes missing audio in New Magic Card 'Skill Game' when won on first loop), and MPU4 sound test [J. Wallace] Audio interface fix for MPU4. [J. Wallace] Lamping fixes for MPU4 small extender. [J. Wallace] Added support for access of separate LED segments in MPU4. (indexed as 'mpu4ledXXX', where the first display unit takes 0-7, the second 8-15 and so on). [J. Wallace] Various updates on the AWP drivers for JPM IMPACT and Maygay M1 [J. Wallace] Various changes for letting Mating Game boot and run, but there are still issues with timing. [J. Wallace]
-rw-r--r--src/emu/sound/okim6376.c251
-rw-r--r--src/emu/sound/okim6376.h2
-rw-r--r--src/mame/drivers/jpmimpct.c386
-rw-r--r--src/mame/drivers/maygay1b.c8
-rw-r--r--src/mame/drivers/mpu4.c454
-rw-r--r--src/mame/drivers/mpu4drvr.c294
-rw-r--r--src/mame/includes/jpmimpct.h6
7 files changed, 957 insertions, 444 deletions
diff --git a/src/emu/sound/okim6376.c b/src/emu/sound/okim6376.c
index 4387e1c953a..87aa1c1d354 100644
--- a/src/emu/sound/okim6376.c
+++ b/src/emu/sound/okim6376.c
@@ -5,9 +5,8 @@
*
* TODO:
* add BEEP tone generator
- * add echo - done, but not tested due to lack of supporting software
- * add proper NAR handling - this varies with clock rate, and is ideally done
- * off a second timer triggered by ST
+ * confirm echo
+ * sample divisor in ROM table not implemented (no documentation)
* modernise
**********************************************************************************************/
@@ -21,7 +20,6 @@
#define OKIVERBOSE 0
#define MSM6376LOG(x) do { if (OKIVERBOSE) logerror x; } while (0)
-
/* struct describing a single playing ADPCM voice */
struct ADPCMVoice
{
@@ -43,12 +41,14 @@ struct _okim6376_state
struct ADPCMVoice voice[OKIM6376_VOICES];
INT32 command[OKIM6376_VOICES];
INT32 latch; /* Command data is held before transferring to either channel */
+ UINT8 stage[OKIM6376_VOICES];/* If a sample is playing, flag that we have a command staged */
UINT8 *region_base; /* pointer to the base of the region */
sound_stream *stream; /* which stream are we playing on? */
UINT32 master_clock; /* master clock frequency */
UINT8 divisor; /* can be 8,10,16, and is read out of ROM data */
UINT8 channel;
UINT8 nar; /* Next Address Ready */
+ UINT8 nartimer;
UINT8 busy;
UINT8 ch2; /* 2CH pin - enables Channel 2 operation */
UINT8 st; /* STart */
@@ -75,8 +75,7 @@ static const int volume_table[3] =
/* divisor lookup table. When an individual word is selected, it can be assigned one of three different 'rates'.
These are implemented as clock divisors, and are looked up in the ROM header. More often than not, this value is 0,
- relating to a division by 8, or nominally 8KHz sampling.
- channel*/
+ relating to a division by 8, or nominally 8KHz sampling (based on the datasheet exampleof a 64KHz clock).*/
static const int divisor_table[3] =
{
8,
@@ -185,6 +184,72 @@ static INT16 clock_adpcm(struct ADPCMVoice *voice, UINT8 nibble)
}
+static void oki_process(okim6376_state *info, int channel, int command)
+{
+ /* if a command is pending, process the second half */
+ if ((command != -1) && (command != 0)) //process silence separately
+ {
+ int start;
+ unsigned char *base/*, *base_end*/;
+ /* update the stream */
+ info->stream->update();
+
+ /* determine which voice(s) (voice is set by the state of 2CH) */
+ {
+ struct ADPCMVoice *voice = &info->voice[channel];
+
+ /* determine the start position, max address space is 16Mbit */
+ base = &info->region_base[info->command[channel] * 4];
+ //base_end = &info->region_base[(MAX_WORDS+1) * 4];
+ start = ((base[0] << 16) + (base[1] << 8) + base[2]) & 0x1fffff;
+
+ if (start == 0)
+ {
+ voice->playing = 0;
+ }
+ else
+ {
+ /* set up the voice to play this sample */
+ if (!voice->playing)
+ {
+ voice->playing = 1;
+ voice->base_offset = start;
+ voice->sample = 0;
+ voice->count = 0;
+
+ /* also reset the ADPCM parameters */
+ reset_adpcm(voice);
+ /* FIX: no attenuation for now, handle for channel 2 separately */
+ voice->volume = volume_table[0];
+ }
+ else
+ {
+ if (((info->nar)&&(channel == 0))||(channel == 1))//Store the request, for later processing (channel 2 ignores NAR)
+ {
+ info->stage[channel] = 1;
+ }
+ }
+ }
+ }
+ }
+ /* otherwise, see if this is a silence command */
+ else
+ {
+ /* update the stream, then turn it off */
+ info->stream->update();
+
+ if (command ==0)
+ {
+ int i;
+ for (i = 0; i < OKIM6376_VOICES; i++)
+ {
+ struct ADPCMVoice *voice = &info->voice[i];
+ voice->playing = 0;
+ }
+ }
+ }
+}
+
/**********************************************************************************************
@@ -192,7 +257,7 @@ static INT16 clock_adpcm(struct ADPCMVoice *voice, UINT8 nibble)
***********************************************************************************************/
-static void generate_adpcm(okim6376_state *chip, struct ADPCMVoice *voice, INT16 *buffer, int samples)
+static void generate_adpcm(okim6376_state *chip, struct ADPCMVoice *voice, INT16 *buffer, int samples,int channel)
{
/* if this voice is active */
if (voice->playing)
@@ -244,6 +309,12 @@ static void generate_adpcm(okim6376_state *chip, struct ADPCMVoice *voice, INT16
/* fill the rest with silence */
while (samples--)
*buffer++ = 0;
+
+ if ((!voice->playing)&&(chip->stage[channel]))//end of samples, load anything staged in
+ {
+ chip->stage[channel] = 0;
+ oki_process(chip,channel,chip->command[channel]);
+ }
}
@@ -267,6 +338,17 @@ static STREAM_UPDATE( okim6376_update )
stream_sample_t *buffer = outputs[0];
INT16 sample_data[MAX_SAMPLE_CHUNK];
int remaining = samples;
+ if (i == 0) //channel 1 is the only channel to affect NAR
+ {
+ if (chip->nartimer > 0)
+ {
+ chip->nartimer--;
+ if (!chip->nartimer)
+ {
+ chip->nar =1;
+ }
+ }
+ }
/* loop while we have samples remaining */
while (remaining)
@@ -274,7 +356,7 @@ static STREAM_UPDATE( okim6376_update )
int samples = (remaining > MAX_SAMPLE_CHUNK) ? MAX_SAMPLE_CHUNK : remaining;
int samp;
- generate_adpcm(chip, voice, sample_data, samples);
+ generate_adpcm(chip, voice, sample_data, samples,i);
for (samp = 0; samp < samples; samp++)
*buffer++ += sample_data[samp];
@@ -313,77 +395,6 @@ static void okim6376_state_save_register(okim6376_state *info, device_t *device)
device->save_item(NAME(info->command[1]));
}
-static void oki_process(device_t *device, int channel, int command)
-{
- okim6376_state *info = get_safe_token(device);
-
- /* if a command is pending, process the second half */
- if ((command != -1) && (command != 0)) //process silence separately
- {
- int start;
- unsigned char *base/*, *base_end*/;
- info->nar = 0;//processing
- /* update the stream */
- info->stream->update();
-
- /* determine which voice(s) (voice is set by the state of 2CH) */
- {
- struct ADPCMVoice *voice = &info->voice[channel];
-
- /* determine the start position, max address space is 16Mbit */
- base = &info->region_base[info->command[channel] * 4];
- //base_end = &info->region_base[(MAX_WORDS+1) * 4];
- start = ((base[0] << 16) + (base[1] << 8) + base[2]) & 0x1fffff;
-
- if (start == 0)
- {
- voice->playing = 0;
- MSM6376LOG(("OKIM6376:'%s' Stopping %x\n",device->tag(),channel));
- }
- else
- {
- /* set up the voice to play this sample */
- if (!voice->playing)
- {
- voice->playing = 1;
- voice->base_offset = start;
- voice->sample = 0;
- voice->count = 0;
-
- /* also reset the ADPCM parameters */
- reset_adpcm(voice);
- /* Channel 1 cannot be attenuated, only Channel 2. We handle that separately */
- voice->volume = volume_table[0];
- MSM6376LOG(("OKIM6376:'%s' Playing %x\n",device->tag(),voice->base_offset));
- }
- else
- {
- MSM6376LOG(("OKIM6376:'%s' requested to play sample %02x on non-stopped voice\n",device->tag(),info->command[channel]));
- }
- }
- info->nar = 1;
- }
- }
- /* otherwise, see if this is a silence command */
- else
- {
- info->nar = 0;
- /* update the stream, then turn it off */
- info->stream->update();
-
- if (command ==0)
- {
- int i;
- for (i = 0; i < OKIM6376_VOICES; i++)
- {
- struct ADPCMVoice *voice = &info->voice[i];
- voice->playing = 0;
- }
- info->nar = 1;
- }
- }
-}
-
/**********************************************************************************************
DEVICE_START( okim6376 ) -- start emulation of an OKIM6376-compatible chip
@@ -394,23 +405,26 @@ static DEVICE_START( okim6376 )
{
okim6376_state *info = get_safe_token(device);
int voice;
-
compute_tables();
info->command[0] = -1;
info->command[1] = -1;
+ info->stage[0] = 0;
+ info->stage[1] = 0;
info->latch = 0;
info->divisor = divisor_table[0];
info->region_base = *device->region();
info->master_clock = device->clock();
info->nar = 1;
+ info->nartimer = 0;
info->busy = 1;
info->st = 1;
+ info->ch2 = 1;
info->st_update = 0;
info->ch2_update = 0;
info->st_pulses = 0;
/* generate the name and create the stream */
- info->stream = device->machine().sound().stream_alloc(*device, 0, 1, info->master_clock / info->divisor, info, okim6376_update);
+ info->stream = device->machine().sound().stream_alloc(*device, 0, 1, device->clock()/ info->divisor, info, okim6376_update);
/* initialize the voices */
for (voice = 0; voice < OKIM6376_VOICES; voice++)
@@ -456,42 +470,22 @@ static DEVICE_RESET( okim6376 )
***********************************************************************************************/
-READ8_DEVICE_HANDLER( okim6376_r )
+READ_LINE_DEVICE_HANDLER( okim6376_busy_r )
{
okim6376_state *info = get_safe_token(device);
- int i, result;
- result = 0xff;
+ struct ADPCMVoice *voice0 = &info->voice[0];
+ struct ADPCMVoice *voice1 = &info->voice[1];
- /* set the bit to 1 if something is playing on a given channel */
- info->stream->update();
- for (i = 0; i < OKIM6376_VOICES; i++)
+ /* set the bit low if it's playing */
+ if ((voice0->playing)||(voice1->playing))
{
- struct ADPCMVoice *voice = &info->voice[i];
-
- /* set the bit if it's playing */
- if (!voice->playing)
- result ^= 1 << i;
+ return 0;
}
-
- return result;
-}
-
-
-READ_LINE_DEVICE_HANDLER( okim6376_busy_r )
-{
- okim6376_state *info = get_safe_token(device);
- int i,result=1;
-
- for (i = 0; i < OKIM6376_VOICES; i++)
+ else
{
- struct ADPCMVoice *voice = &info->voice[i];
-
- /* set the bit low if it's playing */
- if (voice->playing)
- result = 0;
+ return 1;
}
- return result;
}
READ_LINE_DEVICE_HANDLER( okim6376_nar_r )
@@ -512,31 +506,29 @@ WRITE_LINE_DEVICE_HANDLER( okim6376_ch2_w )
info->ch2 = state;
info->ch2_update = 1;
}
-
if((!info->ch2)&&(info->ch2_update))
{
+ info->st_pulses = 0;
struct ADPCMVoice *voice0 = &info->voice[0];
struct ADPCMVoice *voice1 = &info->voice[1];
- //Echo functions when Channel 1 is playing, and ST is still high
+ // We set to channel 2
+ MSM6376LOG(("OKIM6376:'%s' Channel 1\n",device->tag()));
+ info->channel = 1;
+
if ((voice0->playing)&&(info->st))
{
+ //Echo functions when Channel 1 is playing, and ST is still high
info->command[1] = info->command[0];//copy sample over
voice1->volume = volume_table[1]; //echo is 6dB attenuated
- }
- else
- {// Process as a proper channel
- info->channel = 1;
- if (info->command[1] != info->latch)
- {
- info->command[1] = info->latch;
- }
}
}
if((info->ch2)&&(info->ch2_update))
{
+ info->stage[1]=0;
+ oki_process(info, 1, info->command[1]);
+ MSM6376LOG(("OKIM6376:'%s' Channel 0\n",device->tag()));
info->channel = 0;
- oki_process(device, 0, info->command[1]);
}
}
@@ -546,7 +538,6 @@ WRITE_LINE_DEVICE_HANDLER( okim6376_st_w )
//As in STart, presumably, this triggers everything
okim6376_state *info = get_safe_token(device);
-
info->st_update = 0;//Clear flag
MSM6376LOG(("OKIM6376:'%s' ST %x\n",device->tag(),state));
@@ -567,18 +558,19 @@ WRITE_LINE_DEVICE_HANDLER( okim6376_st_w )
info->st_pulses = 3; //undocumented behaviour beyond 3 pulses
}
- MSM6376LOG(("OKIM6376:'%s' Attenuation %x\n",device->tag(),info->st_pulses));
- voice->volume = volume_table[info->st_pulses];
+ voice->volume = volume_table[info->st_pulses - 1];
}
}
if (info->st && info->st_update)
{
info->command[info->channel] = info->latch;
- MSM6376LOG(("OKIM6376:'%s' Latching %x into %x\n",device->tag(),info->latch,info->channel));
-
- if (info->channel ==0)
+ if (info->channel ==0 && info->nar)
{
- oki_process(device, 0, info->command[0]);
+ info->stage[info->channel]=0;
+ oki_process(info, 0, info->command[0]);
+ info->nar = 0;
+ info->nartimer = 4;
+ /*According to datasheet, NAR timing is ~375 us at 8KHz, and is inversely proportional to sample rate, effectively 6 stream updates. */
}
}
}
@@ -596,8 +588,9 @@ WRITE8_DEVICE_HANDLER( okim6376_w )
okim6376_state *info = get_safe_token(device);
info->latch = data & 0x7f;
- // FIX: The maximum adpcm words supported are 111, there are another 8 commands to generate BEEP tone, like beep.c (0x70 to 0x77),
- // and others for internal testing, that the manual explicitly says not to use (0x78 to 0x7f).
+ // FIX: maximum adpcm words are 111, there are other 8 commands to generate BEEP tone (0x70 to 0x77),
+ // and others for internal testing, that manual explicitly says not to use (0x78 to 0x7f)
+ // We aren't doing anything with the BEEP at the moment, as we'd need to mix the ADPCM stream with beep.c
}
diff --git a/src/emu/sound/okim6376.h b/src/emu/sound/okim6376.h
index 540c4a0a004..222ee7e47a8 100644
--- a/src/emu/sound/okim6376.h
+++ b/src/emu/sound/okim6376.h
@@ -5,7 +5,7 @@
#include "devlegcy.h"
-/* an interface for the OKIM6376 and similar chips */
+/* an interface for the OKIM6376 and similar chips (CPU interface only) */
READ8_DEVICE_HANDLER( okim6376_r );
WRITE8_DEVICE_HANDLER( okim6376_w );
diff --git a/src/mame/drivers/jpmimpct.c b/src/mame/drivers/jpmimpct.c
index a3dbfb1beab..a84df411905 100644
--- a/src/mame/drivers/jpmimpct.c
+++ b/src/mame/drivers/jpmimpct.c
@@ -39,7 +39,7 @@
480000-48001F R/W -------- xxxxxxxx MC68681 DUART 1
480020-480033 R -------- xxxxxxxx Inputs
480041 R -xxxxxxx xxxxxxxx Reel optos
- 480060-480067 R/W -------- xxxxxxxx D71055C? PPI?
+ 480060-480067 R/W -------- xxxxxxxx uPD71055C (NEC clone of 8255 PPI)
480080-480081 W -------- xxxxxxxx uPD7559 communications
480082-480083 W -------- xxxxxxxx Sound control
-------- -------x (uPD7759 reset)
@@ -1028,16 +1028,21 @@ GAME( 1999, coronatn, 0, jpmimpct, coronatn, 0, ROT0, "JPM", "Coronation St
/**************************************************************************
- Mechanical IMPACT Games
- AGEMAME driver
+Mechanical IMPACT Games
+
+IMPACT apparently stands for Interactive Moving Picture Amusment Control
+Technology, and is intended as a replacement for the JPM System 5 board.
+Large sections of the processing were moved to two identical custom ASICs
+(U1 and U2), only half of each is used.
+
+Thanks to Tony Friery and JPeMU for I/O routines and documentation.
- This is mostly based on old documentation, and needs a proper look.
***************************************************************************/
#include "video/awpvid.h"
#include "machine/steppers.h"
#include "machine/roc10937.h"
-#include "machine/8255ppi.h"
+#include "machine/i8255.h"
/*************************************
*
@@ -1047,43 +1052,114 @@ GAME( 1999, coronatn, 0, jpmimpct, coronatn, 0, ROT0, "JPM", "Coronation St
static READ8_DEVICE_HANDLER( hopper_b_r )
{
- //?
- return 0;
+ jpmimpct_state *state = device->machine().driver_data<jpmimpct_state>();
+
+ int retval;
+ // B0 = £1 Hopper Out Verif
+ // B1 = Hopper High
+ // B2 = Hopper Low
+ // B3 = 20p Hopper Opto
+
+ // Always return hoppers full
+ retval=0xed; // 1110 1101
+
+ if (!state->m_hopinhibit)//if inhibited, we don't change these flags
+ {
+ if (state->m_hopper[0] && state->m_motor[0]) //&& ((state->m_hopflag1 & 0x20)==0x20))
+ {//100p
+ retval &= ~0x01;
+ }
+ if (((state->m_hopper[1] && state->m_motor[1]) || (state->m_hopper[2] && state->m_slidesout))) //&& ((state->m_hopflag2 & 0x20)==0x20))
+ {
+ retval &= ~0x08;
+ }
+ }
+
+ return retval;
}
static READ8_DEVICE_HANDLER( hopper_c_r )
{
- //?
- return 0;
+ jpmimpct_state *state = device->machine().driver_data<jpmimpct_state>();
+
+ int retval;
+ // C0-C2 = Alpha
+ // C3
+ // C4 = 20p Hopper Detect
+ // C5 = Hopper Top-Up
+ // C6 = £1 Hopper Detect
+ // C7 = Payout Verif (Slides)
+
+ retval=0xf0; //1111 0000
+
+// if (StatBtns & 0x20) // Top Up switch
+// retval &= ~0x20;
+
+ // Which hoppers are present
+ if (state->m_hopper[0])
+ {
+ retval &= ~0x40;
+ }
+ if (state->m_hopper[1])
+ {
+ retval &= ~0x10;
+ }
+
+ if (!state->m_hopinhibit)
+ {
+ if ((state->m_slidesout==1) && ((state->m_hopper[2]==0)))
+ {
+ state->m_slidesout=0;
+ retval &= ~0x80;
+ }
+ }
+
+ return retval;
}
static WRITE8_DEVICE_HANDLER( payen_a_w )
{
jpmimpct_state *state = device->machine().driver_data<jpmimpct_state>();
- if ( data )
- {
- if ( data & 0x10 )
- state->m_payen = 1;
- else
- state->m_payen = 0;
- }
+
+ state->m_motor[0] = (data & 0x01);
+ state->m_payen = (data & 0x10);
+ state->m_slidesout = (data & 0x10);
+ state->m_motor[1] = (data & 0x40);
+ state->m_hopinhibit = (data & 0x80);
}
static WRITE8_DEVICE_HANDLER( display_c_w )
{
+ jpmimpct_state *state = device->machine().driver_data<jpmimpct_state>();
+
+ if(data & 0x04)
+ {
+ state->m_alpha_data_line = ((data >> 1) & 1);
+ if (state->m_alpha_clock != (data & 1))
+ {
+ if (!state->m_alpha_clock)//falling edge
+ {
+ ROC10937_shift_data(0, state->m_alpha_data_line?0:1);
+ }
+ }
+ state->m_alpha_clock = (data & 1);
+ }
+ else
+ {
+ ROC10937_reset(0);
+ }
+ ROC10937_draw_16seg(0);
//?
}
-static const ppi8255_interface ppi8255_intf[1] =
+static I8255_INTERFACE (ppi8255_intf)
{
- {
- DEVCB_NULL,
- DEVCB_HANDLER(hopper_b_r),
- DEVCB_HANDLER(hopper_c_r),
- DEVCB_HANDLER(payen_a_w),
- DEVCB_NULL,
- DEVCB_HANDLER(display_c_w)
- }
+ DEVCB_NULL,
+ DEVCB_HANDLER(payen_a_w),
+ DEVCB_HANDLER(hopper_b_r),
+ DEVCB_NULL,
+ DEVCB_HANDLER(hopper_c_r),
+ DEVCB_HANDLER(display_c_w)
};
static MACHINE_START( impctawp )
@@ -1115,7 +1191,7 @@ static MACHINE_RESET( impctawp )
/* Reset states */
state->m_duart_1_irq = 0;
- ROC10937_init(0, MSC1937,0);
+ ROC10937_init(0, MSC1937,1);//Reversed
ROC10937_reset(0); /* reset display1 */
}
/*************************************
@@ -1139,6 +1215,63 @@ static MACHINE_RESET( impctawp )
* 8: Payslides
* 9: Coin mechanism
*/
+static READ16_HANDLER( inputs1awp_r )
+{
+ UINT16 val = 0x00;
+
+ {
+ switch (offset)
+ {
+ case 0:
+ {
+ val = input_port_read(space->machine(), "DSW");
+ break;
+ }
+ case 1:
+ {
+ val = input_port_read(space->machine(), "PERCENT");
+ break;
+ }
+ case 2:
+ {
+ val = input_port_read(space->machine(), "KEYS");
+ break;
+ }
+ case 3:
+ {
+ val = input_port_read(space->machine(), "SW2");
+ break;
+ }
+ case 4:
+ {
+ val = input_port_read(space->machine(), "SW1");
+ break;
+ }
+ case 5:
+ {
+ val = (input_port_read(space->machine(), "SW3") );
+ break;
+ }
+ case 6:
+ {
+ val = (input_port_read(space->machine(), "SW4") );
+ break;
+ }
+ case 7://5
+ {
+ val = (input_port_read(space->machine(), "SW5") );
+ break;
+ }
+ case 9:
+ {
+ val = input_port_read(space->machine(), "COINS");
+ break;
+ }
+ }
+ return val & 0xff00;
+ }
+}
+
static READ16_HANDLER( optos_r )
{
jpmimpct_state *state = space->machine().driver_data<jpmimpct_state>();
@@ -1152,16 +1285,15 @@ static READ16_HANDLER( optos_r )
return state->m_optic_pattern;
}
-/*************************************
- *
- * Mysterious stuff
- *
- *************************************/
+static READ16_HANDLER( prot_1_r )
+{
+ return 0x01;
+}
static WRITE16_HANDLER( jpmioawp_w )
{
jpmimpct_state *state = space->machine().driver_data<jpmimpct_state>();
- int i;
+ int i,metno;
switch (offset)
{
case 0x00:
@@ -1177,6 +1309,7 @@ static WRITE16_HANDLER( jpmioawp_w )
for (i=0; i<4; i++)
{
stepper_update(i, (data >> i)& 0x0F );
+ awp_draw_reel(i);
}
break;
}
@@ -1185,26 +1318,46 @@ static WRITE16_HANDLER( jpmioawp_w )
for (i=0; i<2; i++)
{
stepper_update(i+4, (data >> (i + 4)& 0x0F ));
+ awp_draw_reel(i+4);
}
break;
}
case 0x06:
{
- if ( data & 0x10 )
- { // PAYEN ?
- if ( data & 0xf )
- {
- // slide = 1;
- }
- else
+ //Slides
+ if ((data & 0xff)!=0x00)
+ {
+ state->m_slidesout=2;
+ }
+ if (((data & 0xff)==0x00) && (state->m_slidesout==2))
+ {
+ state->m_slidesout=1;
+ }
+ // Meters
+ metno=(data >>8) & 0xff;
+ {
+ switch (metno)
{
- // slide = 0;
+ case 0x00:
+ {
+ for (i=0; i<5; i++)
+ {
+ MechMtr_update(i, 0);
+ }
+ break;
+ }
+ default:
+ {
+ MechMtr_update(((metno <<2) - 1), 1);
+ }
+ break;
}
}
- else
-// slide = 0;
- MechMtr_update(0, data >> 10);
- if ( data )
+ int combined_meter = MechMtr_GetActivity(0) | MechMtr_GetActivity(1) |
+ MechMtr_GetActivity(2) | MechMtr_GetActivity(3) |
+ MechMtr_GetActivity(4);
+
+ if(combined_meter)
{
state->m_duart_1.IP &= ~0x10;
}
@@ -1252,25 +1405,151 @@ static ADDRESS_MAP_START( awp68k_program_map, AS_PROGRAM, 16 )
AM_RANGE(0x00100000, 0x001fffff) AM_ROM
AM_RANGE(0x00400000, 0x00403fff) AM_RAM AM_SHARE("nvram")
AM_RANGE(0x00480000, 0x0048001f) AM_READWRITE(duart_1_r, duart_1_w)
- AM_RANGE(0x00480020, 0x00480033) AM_READ(inputs1_r)
+ AM_RANGE(0x00480020, 0x00480033) AM_READ(inputs1awp_r)
AM_RANGE(0x00480034, 0x00480035) AM_READ(ump_r)
AM_RANGE(0x00480040, 0x00480041) AM_READ(optos_r)
- AM_RANGE(0x00480060, 0x00480067) AM_DEVREADWRITE8("ppi8255_0", ppi8255_r, ppi8255_w, 0xff00)
- AM_RANGE(0x004800a0, 0x004800af) AM_READWRITE(jpmio_r, jpmioawp_w)
- AM_RANGE(0x004800e0, 0x004800e1) AM_WRITE(unk_w)
- AM_RANGE(0x004801dc, 0x004801dd) AM_READ(unk_r)
- AM_RANGE(0x004801de, 0x004801df) AM_READ(unk_r)
+ AM_RANGE(0x00480060, 0x00480067) AM_DEVREADWRITE8_MODERN("ppi8255", i8255_device, read, write,0x00ff)
AM_RANGE(0x00480080, 0x00480081) AM_DEVWRITE("upd", upd7759_w)
AM_RANGE(0x00480082, 0x00480083) AM_DEVWRITE("upd",volume_w)
AM_RANGE(0x00480084, 0x00480085) AM_DEVREAD("upd", upd7759_r)
+ AM_RANGE(0x00480086, 0x0048009f) AM_READ(prot_1_r)
+ AM_RANGE(0x004800a0, 0x004800af) AM_READWRITE(jpmio_r, jpmioawp_w)
+// AM_RANGE(0x004800b0, 0x004800df) AM_READ(prot_1_r)
+// AM_RANGE(0x004800e0, 0x004800e1) AM_WRITE(unk_w)
+// AM_RANGE(0x00480086, 0x006576ff) AM_READ(prot_1_r)
+ AM_RANGE(0x004801dc, 0x004801dd) AM_READ(prot_1_r)
+
+// AM_RANGE(0x004801dc, 0x004801dd) AM_READ(unk_r)
+// AM_RANGE(0x004801de, 0x004801df) AM_READ(unk_r)
+// AM_RANGE(0x00657600, 0x00657601) AM_READ(prot_0_r)
+ //AM_RANGE(0x00657602, 0x00bfffff) AM_READ(prot_1_r)
// AM_RANGE(0x004801e0, 0x004801ff) AM_READWRITE(duart_2_r, duart_2_w)
-// AM_RANGE(0x00800000, 0x00800007) AM_READWRITE(m68k_tms_r, m68k_tms_w)
AM_RANGE(0x00c00000, 0x00cfffff) AM_ROM
AM_RANGE(0x00d00000, 0x00dfffff) AM_ROM
AM_RANGE(0x00e00000, 0x00efffff) AM_ROM
AM_RANGE(0x00f00000, 0x00ffffff) AM_ROM
ADDRESS_MAP_END
+static INPUT_PORTS_START( tbirds )
+ PORT_START("DSW")
+ PORT_DIPNAME( 0x01, 0x01, "DSW 0 (toggle to stop alarm)")
+ PORT_DIPSETTING( 0x01, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x02, "DSW 1")
+ PORT_DIPSETTING( 0x02, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x04, "DSW 2")
+ PORT_DIPSETTING( 0x04, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x08, "DSW 3")
+ PORT_DIPSETTING( 0x08, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x10, "DSW 4")
+ PORT_DIPSETTING( 0x10, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x20, 0x20, "DSW 5")
+ PORT_DIPSETTING( 0x20, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x40, 0x40, "DSW 6")
+ PORT_DIPSETTING( 0x40, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+ PORT_DIPNAME( 0x80, 0x80, "DSW 7")
+ PORT_DIPSETTING( 0x80, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x00, DEF_STR( On ) )
+
+ PORT_START("PERCENT")
+ PORT_CONFNAME( 0x0F, 0x00, "Percentage Key" )
+ PORT_CONFSETTING( 0x00, "Not fitted / 68% (Invalid for UK Games)" )
+ PORT_CONFSETTING( 0x01, "70" )
+ PORT_CONFSETTING( 0x02, "72" )
+ PORT_CONFSETTING( 0x03, "74" )
+ PORT_CONFSETTING( 0x04, "76" )
+ PORT_CONFSETTING( 0x05, "78" )
+ PORT_CONFSETTING( 0x06, "80" )
+ PORT_CONFSETTING( 0x07, "82" )
+ PORT_CONFSETTING( 0x08, "84" )
+ PORT_CONFSETTING( 0x09, "86" )
+ PORT_CONFSETTING( 0x0A, "88" )
+ PORT_CONFSETTING( 0x0B, "90" )
+ PORT_CONFSETTING( 0x0C, "92" )
+ PORT_CONFSETTING( 0x0D, "94" )
+ PORT_CONFSETTING( 0x0E, "96" )
+ PORT_CONFSETTING( 0x0F, "98" )
+
+ PORT_START("KEYS")
+ PORT_CONFNAME( 0x0F, 0x0F, "Jackpot / Prize Key" )
+ PORT_CONFSETTING( 0x0F, "Not fitted" )
+ PORT_CONFSETTING( 0x0E, "3 GBP" )
+ PORT_CONFSETTING( 0x0D, "4 GBP" )
+ PORT_CONFSETTING( 0x0C, "5 GBP" )
+ PORT_CONFSETTING( 0x0B, "6 GBP" )
+ PORT_CONFSETTING( 0x0A, "6 GBP Token" )
+ PORT_CONFSETTING( 0x09, "8 GBP" )
+ PORT_CONFSETTING( 0x08, "8 GBP Token" )
+ PORT_CONFSETTING( 0x07, "10 GBP" )
+ PORT_CONFSETTING( 0x06, "15 GBP" )
+ PORT_CONFSETTING( 0x05, "25 GBP" )
+ PORT_CONFSETTING( 0x04, "25 GBP (Licensed Betting Office Profile)" )
+ PORT_CONFSETTING( 0x03, "35 GBP" )
+ PORT_CONFSETTING( 0x02, "70 GBP" )
+ PORT_CONFSETTING( 0x01, "Reserved" )
+ PORT_CONFSETTING( 0x00, "Reserved" )
+
+ PORT_CONFNAME( 0xF0, 0x00, "Stake Key" )
+ PORT_CONFSETTING( 0x00, "Not fitted / 5p" )
+ PORT_CONFSETTING( 0x80, "10p" )
+ PORT_CONFSETTING( 0x40, "20p" )
+ PORT_CONFSETTING( 0xC0, "25p" )
+ PORT_CONFSETTING( 0x20, "30p" )
+// PORT_CONFSETTING( 0x20, "40p" )
+ PORT_CONFSETTING( 0x60, "50p" )
+ PORT_CONFSETTING( 0xE0, "1 GBP" )
+
+ PORT_START("SW5")
+ PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "Collect" )
+ PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME( "'3'" )
+ PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME( "'2'" )
+ PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME( "'1'" )
+
+ PORT_START("SW4")
+ PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "Collect" )
+ PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME( "'3'" )
+ PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME( "'2'" )
+ PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME( "'1'" )
+
+ PORT_START("SW3")
+ PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "Collect" )
+ PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME( "'3'" )
+ PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME( "'2'" )
+ PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME( "'1'" )
+
+ PORT_START("SW2")
+ PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "Collect" )
+ PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME( "'3'" )
+ PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME( "'2'" )
+ PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME( "'1'" )
+
+ PORT_START("SW1")
+ PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_TOGGLE PORT_NAME( "Back Door" )
+ PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_SERVICE2 ) PORT_TOGGLE PORT_NAME( "Cash Door" )
+ PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SERVICE3 ) PORT_TOGGLE PORT_NAME( "Refill Key" )
+
+ PORT_START("TEST/DEMO")
+ PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_SERVICE4 ) PORT_NAME( "Test/Demo" )
+
+ PORT_START("COINS")
+ PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(1) PORT_NAME( "Coin: 1 pound" )
+ PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(1) PORT_NAME( "Coin: 50p" )
+ PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_COIN3 ) PORT_IMPULSE(1) PORT_NAME( "Coin: 20p" )
+ PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN4 ) PORT_IMPULSE(1) PORT_NAME( "Coin: 10p" )
+ PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_COIN5 ) PORT_IMPULSE(1) PORT_NAME( "Token: 20" )
+ PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_COIN6 ) PORT_IMPULSE(1) PORT_NAME( "Coin: 5p" )
+ PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN )
+ PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN )
+
+INPUT_PORTS_END
+
+
/*************************************
*
* Machine driver
@@ -1287,8 +1566,7 @@ static MACHINE_CONFIG_START( impctawp, jpmimpct_state )
MCFG_MACHINE_RESET(impctawp)
MCFG_NVRAM_ADD_0FILL("nvram")
- MCFG_PPI8255_ADD( "ppi8255_0", ppi8255_intf[0] )
-
+ MCFG_I8255_ADD( "ppi8255", ppi8255_intf )
MCFG_TIMER_ADD( "duart_1_timer", duart_1_timer_event)
MCFG_SPEAKER_STANDARD_MONO("mono")
@@ -1320,4 +1598,4 @@ ROM_END
*
*************************************/
-GAME( 199?, m_tbirds, 0, impctawp, trivialp, 0, ROT0, "JPM", "Thunderbirds", GAME_NOT_WORKING )
+GAME( 199?, m_tbirds, 0, impctawp, tbirds, 0, ROT0, "JPM", "Thunderbirds", GAME_NOT_WORKING )
diff --git a/src/mame/drivers/maygay1b.c b/src/mame/drivers/maygay1b.c
index d3ba20dd475..2fb4077e4c4 100644
--- a/src/mame/drivers/maygay1b.c
+++ b/src/mame/drivers/maygay1b.c
@@ -758,7 +758,12 @@ static WRITE8_HANDLER( m1_latch_w )
}
}
-
+static WRITE8_HANDLER( latch_ch2_w )
+{
+ device_t *msm6376 = space->machine().device("msm6376");
+ okim6376_w(msm6376, 0, data&0x7f);
+ okim6376_ch2_w(msm6376,data&0x80);
+}
static ADDRESS_MAP_START( m1_memmap, AS_PROGRAM, 8 )
AM_RANGE(0x0000, 0x1fff) AM_RAM AM_SHARE("nvram")
@@ -781,6 +786,7 @@ static ADDRESS_MAP_START( m1_memmap, AS_PROGRAM, 8 )
AM_RANGE(0x20C0, 0x20C7) AM_WRITE(m1_latch_w)
AM_RANGE(0x2400, 0x2401) AM_DEVWRITE( "ymsnd", ym2413_w )
+ AM_RANGE(0x2420, 0x2421) AM_WRITE( latch_ch2_w )
AM_RANGE(0x2800, 0xffff) AM_ROM
ADDRESS_MAP_END
diff --git a/src/mame/drivers/mpu4.c b/src/mame/drivers/mpu4.c
index 2e2e2c96890..4494044ee35 100644
--- a/src/mame/drivers/mpu4.c
+++ b/src/mame/drivers/mpu4.c
@@ -4,7 +4,11 @@
This is the core driver, no video specific stuff should go in here.
This driver holds all the mechanical games.
- 05-2011: Add better OKI emulation - clock rate may be wrong but samples sound good now.
+ 06-2011: Fixed boneheaded interface glitch that was causing samples to not be cancelled correctly.
+ Added the ability to read each segment of an LED display separately, this may be necessary for some
+ games that use them as surrogate lamp lines.
+ New persistence 'hack' to stop light flicker for the small extender.
+ 05-2011: Add better OKI emulation
04-2011: More accurate gamball code, fixed ROM banking (Project Amber), added BwB CHR simulator (Amber)
This is still a hard coded system, but significantly different to Barcrest's version.
Started adding support for the Crystal Gaming program card, and the link keys for setting parameters.
@@ -69,7 +73,7 @@ In addition there are two auxiliary ports that can be accessed separately to the
-----------+---+-----------------+--------------------------------------------------------------------------
0850 ? | W | ??????????????? | page latch (NV)
-----------+---+-----------------+--------------------------------------------------------------------------
- 0880 |R/W| D D D D D D D D | PIA6821 on soundboard (Oki MSM6376 clocked by 6840)
+ 0880 |R/W| D D D D D D D D | PIA6821 on soundboard (Oki MSM6376 clocked by 6840 (8C0))
| | | port A = ??
| | | port B (882)
| | | b7 = NAR
@@ -215,9 +219,10 @@ TODO: - Distinguish door switches using manual
- Complete stubs for hoppers (needs slightly better 68681 emulation, and new 'hoppers' device emulation)
- It seems that the MPU4 core program relies on some degree of persistence when switching strobes and handling
writes to the various hardware ports. This explains the occasional lamping/LED blackout and switching bugs
- For now, we're ignoring any extra writes to strobes, as the alternative is to assign a timer to *everything*
- - Flo's move in Great Escape gives spin alarms - need a different opto setting for reverse spin reels?
+ For now, we're ignoring any extra writes to strobes, as the alternative is to assign a timer to *everything* and
+ start modelling the individual hysteresis curves of filament lamps.
- Fix BwB characteriser, need to be able to calculate stabiliser bytes. Anyone fancy reading 6809 source?
+ - Strange bug in Andy's Great Escape - Mystery nudge sound effect is not played, mpu4 latches in silence instead (?)
***********************************************************************************************************/
#include "emu.h"
#include "machine/6821pia.h"
@@ -352,6 +357,8 @@ public:
int m_input_strobe;
UINT8 m_lamp_strobe;
UINT8 m_lamp_strobe2;
+ UINT8 m_lamp_strobe_ext;
+ UINT8 m_lamp_strobe_ext_persistence;
UINT8 m_led_strobe;
UINT8 m_ay_data;
int m_optic_pattern;
@@ -456,81 +463,57 @@ with settings like this in the majority of cases.
8 display enables (pins 10 - 17)
*/
-static void lamp_extend_small(int data)
+static void lamp_extend_small(mpu4_state *state, int data)
{
- int lamp_strobe_ext,column,i;
+ int lamp_ext_data,column,i;
column = data & 0x07;
- lamp_strobe_ext = 0x1f - ((data & 0xf8) >> 3);
- if ( lamp_strobe_ext )
+ lamp_ext_data = 0x1f - ((data & 0xf8) >> 3);//remove the mux lines from the data
+
+ if ((state->m_lamp_strobe_ext_persistence == 0))
+ //One write to reset the drive lines, one with the data, one to clear the lines, so only the 2nd write does anything
+ //Once again, lamp persistences would take care of this, but we can't do that
{
for (i = 0; i < 5; i++)
{
- output_set_lamp_value((5*column)+i+128,((lamp_strobe_ext & (1 << i)) != 0));
+ output_set_lamp_value((8*column)+i+128,((lamp_ext_data & (1 << i)) != 0));
}
- }
-}
-
-static void lamp_extend_largea(mpu4_state *state, int data,int column,int active)
-{
- int lampbase,i,byte7;
-
- state->m_lamp_sense = 0;
- byte7 = data & 0x80;
- if ( byte7 != state->m_last_b7 )
+ }
+ state->m_lamp_strobe_ext_persistence ++;
+ if ((state->m_lamp_strobe_ext_persistence == 3)||(state->m_lamp_strobe_ext!=column))
{
- if ( byte7 )
- {
- lampbase = 128 + column * 8;
- }
- else
- {
- lampbase = 192 + column * 8;
- }
- if ( data & 0x3f )
- {
- state->m_lamp_sense = 1;
- }
- if ( active )
- {
- for (i = 0; i < 6; i++)
- {
- output_set_lamp_value(lampbase+i,(data & (1 << i)) != 0);
- }
- }
- }
- state->m_last_b7 = byte7;
+ state->m_lamp_strobe_ext_persistence = 0;
+ state->m_lamp_strobe_ext=column;
+ }
}
-static void lamp_extend_largebc(mpu4_state *state, int data,int column,int active)
+static void lamp_extend_large(mpu4_state *state, int data,int column,int active)
{
- int lampbase,i,byte7;
+ int lampbase,i,bit7;
state->m_lamp_sense = 0;
- byte7 = data & 0x80;
- if ( byte7 != state->m_last_b7 )
+ bit7 = data & 0x80;
+ if ( bit7 != state->m_last_b7 )
{
state->m_card_live = 1;
- if ( byte7 )
- {
- lampbase = 128 + column * 8;
- }
- else
- {
- lampbase = 192 + column * 8;
- }
+ //depending on bit 7, we can access one of two 'blocks' of 64 lamps
+ lampbase = bit7 ? 0 : 64;
if ( data & 0x3f )
{
state->m_lamp_sense = 1;
}
if ( active )
{
- for (i = 0; i < 6; i++)
+ if (state->m_lamp_strobe_ext != column)
{
- output_set_lamp_value(lampbase+i,(data & (1 << i)) != 0);
+ for (i = 0; i < 8; i++)
+ {//CHECK, this includes bit 7
+ output_set_lamp_value((8*column)+i+128+lampbase ,(data & (1 << i)) != 0);
+ }
+ state->m_lamp_strobe_ext = column;
}
}
- state->m_last_b7 = byte7;
+ state->m_last_b7 = bit7;
}
else
{
@@ -540,20 +523,24 @@ static void lamp_extend_largebc(mpu4_state *state, int data,int column,int activ
static void led_write_latch(mpu4_state *state, int latch, int data, int column)
{
- int diff,i;
+ int diff,i,j;
diff = (latch ^ state->m_last_latch) & latch;
column = 7 - column; // like main board, these are wired up in reverse
- data = ~data;//inverted?
+ data = ~data;//inverted drive lines?
for(i=0; i<5; i++)
{
if (diff & (1<<i))
{
- column += (i*8);
+ column += i;
}
}
- output_set_digit_value(column, data);
+ for(j=0; j<8; j++)
+ {
+ output_set_indexed_value("mpu4led",(8*column)+j,(data & (1 << j)) !=0);
+ }
+ output_set_digit_value(column * 8, data);
state->m_last_latch = diff;
}
@@ -645,6 +632,8 @@ static MACHINE_RESET( mpu4 )
state->m_lamp_strobe = 0;
state->m_lamp_strobe2 = 0;
state->m_led_strobe = 0;
+ state->m_mmtr_data = 0;
+ state->m_remote_meter = 0;
state->m_IC23GC = 0;
state->m_IC23GB = 0;
@@ -949,6 +938,7 @@ static TIMER_CALLBACK( ic24_timeout )
/* IC4, 7 seg leds, 50Hz timer reel sensors, current sensors */
static WRITE8_DEVICE_HANDLER( pia_ic4_porta_w )
{
+ int i;
mpu4_state *state = device->machine().driver_data<mpu4_state>();
if(state->m_ic23_active)
{
@@ -956,6 +946,10 @@ static WRITE8_DEVICE_HANDLER( pia_ic4_porta_w )
{
if(state->m_led_strobe != state->m_input_strobe)
{
+ for(i=0; i<8; i++)
+ {
+ output_set_indexed_value("mpu4led",((7 - state->m_input_strobe) * 8) +i,(data & (1 << i)) !=0);
+ }
output_set_digit_value(7 - state->m_input_strobe,data);
}
state->m_led_strobe = state->m_input_strobe;
@@ -1105,6 +1099,7 @@ static READ8_DEVICE_HANDLER( pia_ic5_porta_r )
static WRITE8_DEVICE_HANDLER( pia_ic5_porta_w )
{
+ int i;
mpu4_state *state = device->machine().driver_data<mpu4_state>();
pia6821_device *pia_ic4 = device->machine().device<pia6821_device>("pia_ic4");
if (state->m_hopper == HOPPER_NONDUART_A)
@@ -1120,27 +1115,35 @@ static WRITE8_DEVICE_HANDLER( pia_ic5_porta_w )
}
else if ((state->m_led_extender != CARD_A)||(state->m_led_extender != NO_EXTENDER))
{
+ for(i=0; i<8; i++)
+ {
+ output_set_indexed_value("mpu4led",((state->m_input_strobe + 8) * 8) +i,(data & (1 << i)) !=0);
+ }
output_set_digit_value((state->m_input_strobe+8),data);
}
break;
case SMALL_CARD:
if(state->m_ic23_active)
{
- lamp_extend_small(data);
+ lamp_extend_small(state,data);
}
break;
case LARGE_CARD_A:
- lamp_extend_largea(state,data,state->m_input_strobe,state->m_ic23_active);
+ lamp_extend_large(state,data,state->m_input_strobe,state->m_ic23_active);
break;
case LARGE_CARD_B:
- lamp_extend_largebc(state,data,state->m_input_strobe,state->m_ic23_active);
+ lamp_extend_large(state,data,state->m_input_strobe,state->m_ic23_active);
if ((state->m_ic23_active) && state->m_card_live)
{
+ for(i=0; i<8; i++)
+ {
+ output_set_indexed_value("mpu4led",(((8*(state->m_last_b7 >>7))+ state->m_input_strobe) * 8) +i,(~data & (1 << i)) !=0);
+ }
output_set_digit_value(((8*(state->m_last_b7 >>7))+state->m_input_strobe),~data);
}
break;
case LARGE_CARD_C:
- lamp_extend_largebc(state,data,state->m_input_strobe,state->m_ic23_active);
+ lamp_extend_large(state,data,state->m_input_strobe,state->m_ic23_active);
break;
}
if (state->m_reel_mux == SIX_REEL_5TO8)
@@ -1676,9 +1679,10 @@ static WRITE8_DEVICE_HANDLER( pia_gb_portb_w )
device_t *msm6376 = device->machine().device("msm6376");
okim6376_device *msm = device->machine().device<okim6376_device>("ymsnd");
+
int changed = state->m_expansion_latch^data;
- LOG_SS(("%s: GAMEBOARD: PIA Port A Set to %2x\n", device->machine().describe_context(),data));
+ LOG_SS(("%s: GAMEBOARD: PIA Port B Set to %2x\n", device->machine().describe_context(),data));
state->m_expansion_latch = data;
@@ -1698,9 +1702,7 @@ static WRITE8_DEVICE_HANDLER( pia_gb_portb_w )
{
float percent = (32-state->m_global_volume)/32.0; //volume_override?1.0:(32-state->m_global_volume)/32.0;
msm->set_output_gain(0, percent);
- // msm6376->stream->set_output_gain(1, percent);
-
- // LOG(("GAMEBOARD: OKI volume %f \n",percent));
+ msm->set_output_gain(1, percent);
}
}
}
@@ -1714,16 +1716,16 @@ static READ8_DEVICE_HANDLER( pia_gb_portb_r )
mpu4_state *state = device->machine().driver_data<mpu4_state>();
LOG_SS(("%s: GAMEBOARD: PIA Read of Port B\n",device->machine().describe_context()));
int data=0;
- //
- // b7, 1 = OKI ready, 0 = OKI busy
+ // b7 NAR - we can load another address into Channel 1
+ // b6, 1 = OKI ready, 0 = OKI busy
// b5, vol clock
// b4, 1 = Vol down, 0 = Vol up
//
- if ( okim6376_busy_r(msm6376) ) data |= 0x80;
+ if ( okim6376_nar_r(msm6376) ) data |= 0x80;
else data &= ~0x80;
- if ( okim6376_nar_r(msm6376) ) data |= 0x40;
+ if ( okim6376_busy_r(msm6376) ) data |= 0x40;
else data &= ~0x40;
return ( data | state->m_expansion_latch );
@@ -1774,8 +1776,6 @@ freq = (1720000/((t3L+1)(t3H+1)))*[(t3H(T3L+1)+1)/(2(t1+1))]
where [] means rounded up integer,
t3L is the LSB of Clock 3,
t3H is the MSB of Clock 3,
-
-The sample speed divisor is f/300
and t1 is the initial value in clock 1.
*/
@@ -1794,7 +1794,7 @@ static WRITE8_DEVICE_HANDLER( ic3ss_o2_callback )//Generates 'beep' tone
static WRITE8_DEVICE_HANDLER( ic3ss_o3_callback )
{
- downcast<ptm6840_device *>(device)->set_g1(data); /* this output is the clock for timer1 */
+ //downcast<ptm6840_device *>(device)->set_g1(data); /* this output is the clock for timer1 */
}
/* This is a bit of a cheat - since we don't clock into the OKI chip directly, we need to
@@ -1822,10 +1822,10 @@ static WRITE8_HANDLER( ic3ss_w )
float num = (1720000/((state->m_t3l + 1)*(state->m_t3h + 1)));
float denom1 = ((state->m_t3h *(state->m_t3l + 1)+ 1)/(2*(state->m_t1 + 1)));
-
+
int denom2 = denom1 +0.5;//need to round up, this gives same precision as chip
- int freq=num*denom2;
-
+ int freq=num*denom2;
+
if (freq)
{
okim6376_set_frequency(msm6376, freq);
@@ -1918,56 +1918,61 @@ static INPUT_PORTS_START( mpu4 )
PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_START1)
PORT_START("DIL1")
- PORT_DIPNAME( 0x80, 0x00, "DIL101" ) PORT_DIPLOCATION("DIL1:01")
- PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x80, DEF_STR( On ) )
- PORT_DIPNAME( 0x40, 0x00, "DIL102" ) PORT_DIPLOCATION("DIL1:02")
+ PORT_DIPNAME( 0x01, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:01")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x40, DEF_STR( On ) )
- PORT_DIPNAME( 0x20, 0x00, "DIL103" ) PORT_DIPLOCATION("DIL1:03")
- PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x20, DEF_STR( On ) )
- PORT_DIPNAME( 0x10, 0x00, "DIL104" ) PORT_DIPLOCATION("DIL1:04")
- PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x10, DEF_STR( On ) )
- PORT_DIPNAME( 0x08, 0x00, "DIL105" ) PORT_DIPLOCATION("DIL1:05")
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:02")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x08, DEF_STR( On ) )
- PORT_DIPNAME( 0x04, 0x00, "DIL106" ) PORT_DIPLOCATION("DIL1:06")
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:03")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
PORT_DIPSETTING( 0x04, DEF_STR( On ) )
- PORT_DIPNAME( 0x02, 0x00, "DIL107" ) PORT_DIPLOCATION("DIL1:07")
- PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x02, DEF_STR( On ) )
- PORT_DIPNAME( 0x01, 0x00, "DIL108" ) PORT_DIPLOCATION("DIL1:08")
+ PORT_DIPNAME( 0x08, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:04")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0xF0, 0x00, "Target Percentage (if key not fitted)" )PORT_DIPLOCATION("DIL1:05,06,07,08")
+ PORT_DIPSETTING( 0x00, "Unset (Program Optimum)" )
+ PORT_DIPSETTING( 0x10, "70" )
+ PORT_DIPSETTING( 0x20, "72" )
+ PORT_DIPSETTING( 0x30, "74" )
+ PORT_DIPSETTING( 0x40, "76" )
+ PORT_DIPSETTING( 0x50, "78" )
+ PORT_DIPSETTING( 0x60, "80" )
+ PORT_DIPSETTING( 0x70, "82" )
+ PORT_DIPSETTING( 0x80, "84" )
+ PORT_DIPSETTING( 0x90, "86" )
+ PORT_DIPSETTING( 0xA0, "88" )
+ PORT_DIPSETTING( 0xB0, "90" )
+ PORT_DIPSETTING( 0xC0, "92" )
+ PORT_DIPSETTING( 0xD0, "94" )
+ PORT_DIPSETTING( 0xE0, "96" )
+ PORT_DIPSETTING( 0xF0, "98" )
PORT_START("DIL2")
- PORT_DIPNAME( 0x80, 0x00, "DIL201" ) PORT_DIPLOCATION("DIL2:01")
+ PORT_DIPNAME( 0x01, 0x00, "Token Lockout when full" ) PORT_DIPLOCATION("DIL2:01")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x80, DEF_STR( On ) )
- PORT_DIPNAME( 0x40, 0x00, "DIL202" ) PORT_DIPLOCATION("DIL2:02")
- PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x40, DEF_STR( On ) )
- PORT_DIPNAME( 0x20, 0x00, "DIL203" ) PORT_DIPLOCATION("DIL2:03")
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, DEF_STR( Unused )) PORT_DIPLOCATION("DIL2:02")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x20, DEF_STR( On ) )
- PORT_DIPNAME( 0x10, 0x00, "DIL204" ) PORT_DIPLOCATION("DIL2:04")
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "Scottish Coin Handling" ) PORT_DIPLOCATION("DIL2:03")//20p payout
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x10, DEF_STR( On ) )
- PORT_DIPNAME( 0x08, 0x00, "DIL205" ) PORT_DIPLOCATION("DIL2:05")
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "Out of Credit Display Inhibit" ) PORT_DIPLOCATION("DIL2:04")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
PORT_DIPSETTING( 0x08, DEF_STR( On ) )
- PORT_DIPNAME( 0x04, 0x00, "DIL206" ) PORT_DIPLOCATION("DIL2:06")
+ PORT_DIPNAME( 0x10, 0x00, "OCD Audio Enable" ) PORT_DIPLOCATION("DIL2:05")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x04, DEF_STR( On ) )
- PORT_DIPNAME( 0x02, 0x00, "DIL207" ) PORT_DIPLOCATION("DIL2:07")
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+ PORT_DIPNAME( 0x20, 0x00, "Coin Alarm Inhibit" ) PORT_DIPLOCATION("DIL2:06")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x02, DEF_STR( On ) )
- PORT_DIPNAME( 0x01, 0x00, "DIL208" ) PORT_DIPLOCATION("DIL2:08")
+ PORT_DIPSETTING( 0x20, DEF_STR( On ) )
+ PORT_DIPNAME( 0x40, 0x00, "Token Refill Level Inhibit" ) PORT_DIPLOCATION("DIL2:07")
PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
- PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPSETTING( 0x40, DEF_STR( On ) )
+ PORT_DIPNAME( 0x80, 0x00, "Single Credit Entry" ) PORT_DIPLOCATION("DIL2:08")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x80, DEF_STR( On ) )
PORT_START("AUX1")
PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("0")
@@ -2107,24 +2112,57 @@ INPUT_PORTS_END
static INPUT_PORTS_START( gamball )
PORT_START("ORANGE1")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("00")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("01")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("02")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("03")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("04")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("05")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("06")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("07")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("00")// 20p level
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("01")// 100p level
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("02")// Token 1 level
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("03")// Token 2 level
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("04")
+ PORT_CONFNAME( 0xE0, 0x00, "Stake Key" )
+ PORT_CONFSETTING( 0x00, "Not fitted / 5p" )
+ PORT_CONFSETTING( 0x20, "10p" )
+ PORT_CONFSETTING( 0x40, "20p" )
+ PORT_CONFSETTING( 0x60, "25p" )
+ PORT_CONFSETTING( 0x80, "30p" )
+ PORT_CONFSETTING( 0xA0, "40p" )
+ PORT_CONFSETTING( 0xC0, "50p" )
+ PORT_CONFSETTING( 0xE0, "1 GBP" )
PORT_START("ORANGE2")
- PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("08")
- PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("09")
- PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("10")
- PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("11")
- PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("12")
- PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("13")
- PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("14")
- PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("15")
+ PORT_CONFNAME( 0x0F, 0x00, "Jackpot / Prize Key" )
+ PORT_CONFSETTING( 0x00, "Not fitted" )
+ PORT_CONFSETTING( 0x01, "3 GBP" )
+ PORT_CONFSETTING( 0x02, "4 GBP" )
+ PORT_CONFSETTING( 0x08, "5 GBP" )
+ PORT_CONFSETTING( 0x03, "6 GBP" )
+ PORT_CONFSETTING( 0x04, "6 GBP Token" )
+ PORT_CONFSETTING( 0x05, "8 GBP" )
+ PORT_CONFSETTING( 0x06, "8 GBP Token" )
+ PORT_CONFSETTING( 0x07, "10 GBP" )
+ PORT_CONFSETTING( 0x09, "15 GBP" )
+ PORT_CONFSETTING( 0x0A, "25 GBP" )
+ PORT_CONFSETTING( 0x0B, "25 GBP (Licensed Betting Office Profile)" )
+ PORT_CONFSETTING( 0x0C, "35 GBP" )
+ PORT_CONFSETTING( 0x0D, "70 GBP" )
+ PORT_CONFSETTING( 0x0E, "Reserved" )
+ PORT_CONFSETTING( 0x0F, "Reserved" )
+
+ PORT_CONFNAME( 0xF0, 0x00, "Percentage Key" )
+ PORT_CONFSETTING( 0x00, "As Option Switches" )
+ PORT_CONFSETTING( 0x10, "70" )
+ PORT_CONFSETTING( 0x20, "72" )
+ PORT_CONFSETTING( 0x30, "74" )
+ PORT_CONFSETTING( 0x40, "76" )
+ PORT_CONFSETTING( 0x50, "78" )
+ PORT_CONFSETTING( 0x60, "80" )
+ PORT_CONFSETTING( 0x70, "82" )
+ PORT_CONFSETTING( 0x80, "84" )
+ PORT_CONFSETTING( 0x90, "86" )
+ PORT_CONFSETTING( 0xA0, "88" )
+ PORT_CONFSETTING( 0xB0, "90" )
+ PORT_CONFSETTING( 0xC0, "92" )
+ PORT_CONFSETTING( 0xD0, "94" )
+ PORT_CONFSETTING( 0xE0, "96" )
+ PORT_CONFSETTING( 0xF0, "98" )
PORT_START("BLACK1")
PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_BUTTON1) PORT_NAME("Hi")
@@ -2212,6 +2250,158 @@ static INPUT_PORTS_START( gamball )
PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_COIN4) PORT_NAME("100p")PORT_IMPULSE(5)
INPUT_PORTS_END
+static INPUT_PORTS_START( grtecp )
+ PORT_START("ORANGE1")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("00")// 20p level
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("01")// 100p level
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("02")// Token 1 level
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("03")// Token 2 level
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("04")
+ PORT_CONFNAME( 0xE0, 0x00, "Stake Key" )
+ PORT_CONFSETTING( 0x00, "Not fitted / 5p" )
+ PORT_CONFSETTING( 0x20, "10p" )
+ PORT_CONFSETTING( 0x40, "20p" )
+ PORT_CONFSETTING( 0x60, "25p" )
+ PORT_CONFSETTING( 0x80, "30p" )
+ PORT_CONFSETTING( 0xA0, "40p" )
+ PORT_CONFSETTING( 0xC0, "50p" )
+ PORT_CONFSETTING( 0xE0, "1 GBP" )
+
+ PORT_START("ORANGE2")
+ PORT_CONFNAME( 0x0F, 0x00, "Jackpot / Prize Key" )
+ PORT_CONFSETTING( 0x00, "Not fitted" )
+ PORT_CONFSETTING( 0x01, "3 GBP" )
+ PORT_CONFSETTING( 0x02, "4 GBP" )
+ PORT_CONFSETTING( 0x08, "5 GBP" )
+ PORT_CONFSETTING( 0x03, "6 GBP" )
+ PORT_CONFSETTING( 0x04, "6 GBP Token" )
+ PORT_CONFSETTING( 0x05, "8 GBP" )
+ PORT_CONFSETTING( 0x06, "8 GBP Token" )
+ PORT_CONFSETTING( 0x07, "10 GBP" )
+ PORT_CONFSETTING( 0x09, "15 GBP" )
+ PORT_CONFSETTING( 0x0A, "25 GBP" )
+ PORT_CONFSETTING( 0x0B, "25 GBP (Licensed Betting Office Profile)" )
+ PORT_CONFSETTING( 0x0C, "35 GBP" )
+ PORT_CONFSETTING( 0x0D, "70 GBP" )
+ PORT_CONFSETTING( 0x0E, "Reserved" )
+ PORT_CONFSETTING( 0x0F, "Reserved" )
+
+ PORT_CONFNAME( 0xF0, 0x00, "Percentage Key" )
+ PORT_CONFSETTING( 0x00, "As Option Switches" )
+ PORT_CONFSETTING( 0x10, "70" )
+ PORT_CONFSETTING( 0x20, "72" )
+ PORT_CONFSETTING( 0x30, "74" )
+ PORT_CONFSETTING( 0x40, "76" )
+ PORT_CONFSETTING( 0x50, "78" )
+ PORT_CONFSETTING( 0x60, "80" )
+ PORT_CONFSETTING( 0x70, "82" )
+ PORT_CONFSETTING( 0x80, "84" )
+ PORT_CONFSETTING( 0x90, "86" )
+ PORT_CONFSETTING( 0xA0, "88" )
+ PORT_CONFSETTING( 0xB0, "90" )
+ PORT_CONFSETTING( 0xC0, "92" )
+ PORT_CONFSETTING( 0xD0, "94" )
+ PORT_CONFSETTING( 0xE0, "96" )
+ PORT_CONFSETTING( 0xF0, "98" )
+
+ PORT_START("BLACK1")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("Test Button") PORT_CODE(KEYCODE_W)
+ PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("Refill Key") PORT_CODE(KEYCODE_R) PORT_TOGGLE
+ PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_INTERLOCK) PORT_NAME("Cashbox (Back) Door") PORT_CODE(KEYCODE_Q) PORT_TOGGLE
+
+ PORT_START("BLACK2")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_BUTTON1) PORT_NAME("Collect/Cancel")
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_BUTTON2) PORT_NAME("Hold 1")
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_BUTTON3) PORT_NAME("Hold 2")
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_BUTTON4) PORT_NAME("Hold 3")
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_BUTTON5) PORT_NAME("Hi")
+ PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_BUTTON6) PORT_NAME("Lo")
+ PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_BUTTON7) PORT_NAME("Exchange")
+ PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_START1)
+
+ PORT_START("DIL1")
+ PORT_DIPNAME( 0x01, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:01")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:02")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:03")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, DEF_STR( Unused ) ) PORT_DIPLOCATION("DIL1:04")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0xF0, 0x00, "Target Percentage (if key not fitted)" )PORT_DIPLOCATION("DIL1:05,06,07,08")
+ PORT_DIPSETTING( 0x00, "Unset (Program Optimum)" )
+ PORT_DIPSETTING( 0x10, "70" )
+ PORT_DIPSETTING( 0x20, "72" )
+ PORT_DIPSETTING( 0x30, "74" )
+ PORT_DIPSETTING( 0x40, "76" )
+ PORT_DIPSETTING( 0x50, "78" )
+ PORT_DIPSETTING( 0x60, "80" )
+ PORT_DIPSETTING( 0x70, "82" )
+ PORT_DIPSETTING( 0x80, "84" )
+ PORT_DIPSETTING( 0x90, "86" )
+ PORT_DIPSETTING( 0xA0, "88" )
+ PORT_DIPSETTING( 0xB0, "90" )
+ PORT_DIPSETTING( 0xC0, "92" )
+ PORT_DIPSETTING( 0xD0, "94" )
+ PORT_DIPSETTING( 0xE0, "96" )
+ PORT_DIPSETTING( 0xF0, "98" )
+
+ PORT_START("DIL2")
+ PORT_DIPNAME( 0x01, 0x00, "Token Lockout when full" ) PORT_DIPLOCATION("DIL2:01")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x01, DEF_STR( On ) )
+ PORT_DIPNAME( 0x02, 0x00, DEF_STR( Unused )) PORT_DIPLOCATION("DIL2:02")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x02, DEF_STR( On ) )
+ PORT_DIPNAME( 0x04, 0x00, "Scottish Coin Handling" ) PORT_DIPLOCATION("DIL2:03")//20p payout
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x04, DEF_STR( On ) )
+ PORT_DIPNAME( 0x08, 0x00, "Out of Credit Display Inhibit" ) PORT_DIPLOCATION("DIL2:04")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x08, DEF_STR( On ) )
+ PORT_DIPNAME( 0x10, 0x00, "OCD Audio Enable" ) PORT_DIPLOCATION("DIL2:05")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x10, DEF_STR( On ) )
+ PORT_DIPNAME( 0x20, 0x00, "Coin Alarm Inhibit" ) PORT_DIPLOCATION("DIL2:06")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x20, DEF_STR( On ) )
+ PORT_DIPNAME( 0x40, 0x00, "Token Refill Level Inhibit" ) PORT_DIPLOCATION("DIL2:07")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x40, DEF_STR( On ) )
+ PORT_DIPNAME( 0x80, 0x00, "Single Credit Entry" ) PORT_DIPLOCATION("DIL2:08")
+ PORT_DIPSETTING( 0x00, DEF_STR( Off ) )
+ PORT_DIPSETTING( 0x80, DEF_STR( On ) )
+
+ PORT_START("AUX1")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("0")
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("1")
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("2")
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("3")
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("4")
+ PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("5")
+ PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("6")
+ PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("7")
+
+ PORT_START("AUX2")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_SPECIAL)
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_SPECIAL)
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_SPECIAL)
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_SPECIAL)
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_COIN1) PORT_NAME("10p")PORT_IMPULSE(5)
+ PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_COIN2) PORT_NAME("20p")PORT_IMPULSE(5)
+ PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_COIN3) PORT_NAME("50p")PORT_IMPULSE(5)
+ PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_COIN4) PORT_NAME("100p")PORT_IMPULSE(5)
+INPUT_PORTS_END
+
static const stepper_interface barcrest_reel_interface =
{
BARCREST_48STEP_REEL,
@@ -2266,6 +2456,7 @@ static void mpu4_config_common(running_machine &machine)
{
mpu4_state *state = machine.driver_data<mpu4_state>();
state->m_ic24_timer = machine.scheduler().timer_alloc(FUNC(ic24_timeout));
+ state->m_lamp_strobe_ext_persistence = 0;
}
static void mpu4_config_common_reels(running_machine &machine,int reels)
@@ -2789,7 +2980,6 @@ static ADDRESS_MAP_START( mod4_oki_map, AS_PROGRAM, 8 )
AM_RANGE(0x0880, 0x0883) AM_DEVREADWRITE_MODERN("pia_ic4ss", pia6821_device, read, write) // PIA6821 on sampled sound board
-// AM_RANGE(0x08c0, 0x08c7) AM_DEVREADWRITE_MODERN("ptm_ic3ss", ptm6840_device, read, write) // 6840PTM on sampled sound board
AM_RANGE(0x08c0, 0x08c7) AM_DEVREAD_MODERN("ptm_ic3ss", ptm6840_device, read) // 6840PTM on sampled sound board
AM_RANGE(0x08c0, 0x08c7) AM_WRITE(ic3ss_w) // 6840PTM on sampled sound board
@@ -2816,12 +3006,12 @@ static ADDRESS_MAP_START( mpu4_bwb_map, AS_PROGRAM, 8 )
AM_RANGE(0x0858, 0x0858) AM_WRITE(bankswitch_w) // write bank (rom page select)
AM_RANGE(0x0878, 0x0878) AM_WRITE(bankset_w) // write bank (rom page select)
+ AM_RANGE(0x0880, 0x0883) AM_DEVREADWRITE_MODERN("pia_ic4ss", pia6821_device, read, write) // PIA6821 on sampled sound board
+
// AM_RANGE(0x08c0, 0x08c7) AM_DEVREADWRITE_MODERN("ptm_ic3ss", ptm6840_device, read, write) // 6840PTM on sampled sound board
AM_RANGE(0x08c0, 0x08c7) AM_DEVREAD_MODERN("ptm_ic3ss", ptm6840_device, read) // 6840PTM on sampled sound board
AM_RANGE(0x08c0, 0x08c7) AM_WRITE(ic3ss_w) // 6840PTM on sampled sound board
- AM_RANGE(0x08c0, 0x08c7) AM_DEVREADWRITE_MODERN("ptm_ic3ss", ptm6840_device, read, write) // 6840PTM on sampled sound board
-
// AM_RANGE(0x08e0, 0x08e7) AM_READWRITE(68681_duart_r,68681_duart_w) //Runs hoppers
AM_RANGE(0x0900, 0x0907) AM_DEVREADWRITE_MODERN("ptm_ic2", ptm6840_device, read, write)/* PTM6840 IC2 */
@@ -3036,7 +3226,7 @@ ROM_END
GAME( 198?, m_oldtmr,0, mpu4dutch,mpu4, m_oldtmr, ROT0, "Barcrest", "Old Timer", GAME_NOT_WORKING|GAME_NO_SOUND|GAME_REQUIRES_ARTWORK )
GAME( 198?, m_ccelbr,0, mpu4mod2, mpu4, m_ccelbr, ROT0, "Barcrest", "Club Celebration", GAME_NOT_WORKING|GAME_REQUIRES_ARTWORK )
GAMEL(198?, m_gmball,0, mod4yam, gamball, m_gmball, ROT0, "Barcrest", "Gamball", GAME_REQUIRES_ARTWORK|GAME_MECHANICAL,layout_gamball )//Mechanical ball launcher
-GAMEL(198?, m_grtecp,0, mod4oki, mpu4, m_grtecp, ROT0, "Barcrest", "Andy's Great Escape", GAME_NOT_WORKING|GAME_REQUIRES_ARTWORK,layout_mpu4ext )//5 reel meter mux
+GAMEL(198?, m_grtecp,0, mod4oki, grtecp, m_grtecp, ROT0, "Barcrest", "Andy's Great Escape", GAME_NOT_WORKING|GAME_REQUIRES_ARTWORK,layout_mpu4ext )//5 reel meter mux
GAME(199?, m_blsbys,0, bwboki, mpu4, m_blsbys, ROT0, "Barcrest", "Blues Boys (Version 6)", GAME_NOT_WORKING|GAME_REQUIRES_ARTWORK )
GAME(199?, m_frkstn,0, mpu4crys, mpu4, m_frkstn, ROT0, "Crystal Gaming","Frank 'n' Stein (unencrypted)", GAME_NOT_WORKING|GAME_REQUIRES_ARTWORK|GAME_NO_SOUND )//hardware not connected
diff --git a/src/mame/drivers/mpu4drvr.c b/src/mame/drivers/mpu4drvr.c
index 1feae52afb1..1945d8a0c72 100644
--- a/src/mame/drivers/mpu4drvr.c
+++ b/src/mame/drivers/mpu4drvr.c
@@ -5,7 +5,6 @@ Barcrest MPU4 Extension driver by J.Wallace, and Anonymous.
For the Barcrest MPU4 Video system, the GAME CARD (cartridge) contains the MPU4 video bios in the usual ROM
space (occupying 16k), an interface card to connect an additional Video board, and a 6850 serial IO to
communicate with said board.
-This version of the game card does not have the OKI chip, or the characteriser.
The VIDEO BOARD is driven by a 10mhz 68000 processor, and contains a 6840PTM, 6850 serial IO
(the other end of the communications), an SAA1099 for stereo sound and SCN2674 gfx chip.
@@ -166,11 +165,8 @@ timer driven, the video is capable of various raster effects etc.)
TODO:
- Correctly implement characteriser protection for each game.
- - Hook up trackball control for The Crystal Maze and The Mating Game - done, but game response is v. slow
- - Fix meter sense error when coining up in Team Challenge - different cabinet
- - Improve AVDC implementation, adding split-screen interrupts (needed for mid-screen palette changes)
- - Hook up OKIM6376 sound in The Mating Game
- - Get the BwB games running
+ - Mating Game animation and screen still slower than it should be, AVDC timing/IRQs?
+ - Get the BwB games running
* They have a slightly different 68k memory map. The 6850 is at e00000 and the 6840 is at e01000
They appear to hang on the handshake with the MPU4 board
- Find out what causes the games to reset in service mode (see jump taken at CPU1:c8e8)
@@ -193,6 +189,7 @@ TODO:
#endif
#define LOGSTUFF(x) do { if (MPU4VIDVERBOSE) logerror x; } while (0)
+#define LOG2674(x) do { if (MPU4VIDVERBOSE) logerror x; } while (0)
#define VIDEO_MASTER_CLOCK XTAL_10MHz
@@ -663,9 +660,9 @@ static void scn2674_write_command(running_machine &machine, UINT8 data)
/* master reset, configures registers */
LOGSTUFF(("master reset\n"));
state->m_scn2675_IR_pointer=0;
- state->m_scn2674_irq_register = 0x20;
- state->m_scn2674_status_register = 0x20;
- state->m_scn2674_irq_mask = 0x20;
+ state->m_scn2674_irq_register = 0x00;
+ state->m_scn2674_status_register = 0x20;//RDFLG activated
+ state->m_scn2674_irq_mask = 0x00;
state->m_scn2674_gfx_enabled = 0;
state->m_scn2674_display_enabled = 0;
state->m_scn2674_cursor_enabled = 0;
@@ -756,15 +753,20 @@ static void scn2674_write_command(running_machine &machine, UINT8 data)
state->m_scn2674_status_register &= ((data & 0x1f)^0x1f);
state->m_scn2674_irq_state = 0;
- if (state->m_scn2674_irq_register)
+
+ for (i = 0; i < 5; i++)
{
- state->m_scn2674_irq_state = 1;
+ if ((state->m_scn2674_irq_register>>i&1)&(state->m_scn2674_irq_mask>>i&1))
+ {
+ state->m_scn2674_irq_state = 1;
+ }
}
update_mpu68_interrupts(machine);
+
}
if ((data&0xe0)==0x80)
{
- /* Disable Interrupt */
+ /* Disable Interrupt mask*/
oprand = data & 0x1f;
LOGSTUFF(("disable interrupt %02x\n",data));
LOGSTUFF(("Split 2 IRQ: %d Disabled\n",(data>>0)&1));
@@ -776,23 +778,12 @@ static void scn2674_write_command(running_machine &machine, UINT8 data)
/* state->m_scn2674_irq_mask &= ((data & 0x1f)^0x1f); disables.. doesn't enable? */
state->m_scn2674_irq_mask &= ~(data & 0x1f);
-
- state->m_scn2674_irq_state = 0;
-
- for (i = 0; i < 5; i++)
- {
- if ((state->m_scn2674_irq_register>>i&1)&(state->m_scn2674_irq_mask>>i&1))
- {
- state->m_scn2674_irq_state = 1;
- }
- }
- update_mpu68_interrupts(machine);
-
+ //mask changes, but bit can ONLY be cleared by reset
}
if ((data&0xe0)==0x60)
{
- /* Enable Interrupt */
+ /* Enable Interrupt mask*/
LOGSTUFF(("enable interrupt %02x\n",data));
LOGSTUFF(("Split 2 IRQ: %d Enabled\n",(data>>0)&1));
LOGSTUFF(("Ready IRQ: %d Enabled\n",(data>>1)&1));
@@ -801,20 +792,11 @@ static void scn2674_write_command(running_machine &machine, UINT8 data)
LOGSTUFF(("V-Blank IRQ: %d Enabled\n",(data>>4)&1));
state->m_scn2674_irq_mask |= (data & 0x1f); /* enables .. doesn't disable? */
-
- state->m_scn2674_irq_state = 0;
-
- for (i = 0; i < 5; i++)
- {
- if ((state->m_scn2674_irq_register>>i&1)&(state->m_scn2674_irq_mask>>i&1))
- {
- state->m_scn2674_irq_state = 1;
- }
- }
- update_mpu68_interrupts(machine);
+ //mask changes, but IRQ can ONLY be triggered by the next event, according to datasheet
}
/* Delayed Commands */
+ /* These set 0x20 in status register when done */
if (data == 0xa4)
{
@@ -1190,6 +1172,80 @@ static const pia6821_interface pia_ic5t_intf =
DEVCB_LINE(cpu0_irq) /* IRQB */
};
+//Sampled sound timer
+/*
+For the video card, it appears that the standard MPU4 program card is interfaced to
+the video board. Since this uses the E clock, our formula changes to
+
+MSM6376 clock frequency:-
+freq = (1000000/((t3L+1)(t3H+1)))*[(t3H(T3L+1)+1)/(2(t1+1))]
+where [] means rounded up integer,
+t3L is the LSB of Clock 3,
+t3H is the MSB of Clock 3,
+and t1 is the initial value in clock 1.
+*/
+
+//O3 -> G1 O1 -> c2 o2 -> c1
+static WRITE8_DEVICE_HANDLER( ic3ss_vid_o1_callback )
+{
+ downcast<ptm6840_device *>(device)->set_c2(data);
+}
+
+
+static WRITE8_DEVICE_HANDLER( ic3ss_vid_o2_callback )//Generates 'beep' tone
+{
+ downcast<ptm6840_device *>(device)->set_c1(data); /* this output is the clock for timer1 */
+}
+
+
+static WRITE8_DEVICE_HANDLER( ic3ss_vid_o3_callback )
+{
+ downcast<ptm6840_device *>(device)->set_g1(data); /* this output is the clock for timer1 */
+}
+
+static WRITE8_HANDLER( ic3ss_vid_w )
+{
+ //This would seem to be right, needs checking against a PCB
+ device_t *ic3ssv = space->machine().device("ptm_ic3ss_vid");
+ mpu4_state *state = space->machine().driver_data<mpu4_state>();
+ downcast<ptm6840_device *>(ic3ssv)->write(offset,data);//can speed things up if this is disabled
+ device_t *msm6376 = space->machine().device("msm6376");
+
+ if (offset == 3)
+ {
+ state->m_t1 = data;
+ }
+ if (offset == 6)
+ {
+ state->m_t3h = data;
+ }
+ if (offset == 7)
+ {
+ state->m_t3l = data;
+ }
+
+ float num = ((VIDEO_MASTER_CLOCK / 10)/((state->m_t3l + 1)*(state->m_t3h + 1)));
+ float denom1 = ((state->m_t3h *(state->m_t3l + 1)+ 1)/(2*(state->m_t1 + 1)));
+
+ int denom2 = denom1 +0.5;//need to round up, this gives same precision as chip
+ int freq=num*denom2;
+
+ if (freq)
+ {
+ okim6376_set_frequency(msm6376, freq);
+ }
+}
+
+static const ptm6840_interface ptm_ic3ss_vid_intf =
+{
+ VIDEO_MASTER_CLOCK / 10, /* 68k E clock */
+ { 0, 0, 0 },
+ { DEVCB_HANDLER(ic3ss_vid_o1_callback),
+ DEVCB_HANDLER(ic3ss_vid_o2_callback),
+ DEVCB_HANDLER(ic3ss_vid_o3_callback) },
+ DEVCB_NULL
+};
+
/*************************************
*
* Input defintions
@@ -1201,21 +1257,14 @@ static INPUT_PORTS_START( crmaze )
PORT_BIT(0xFF, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_START("ORANGE2")
- PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("08")
- PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("09")
- PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("10")
- PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("11")
- PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("12")
- PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("13")
- PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("14")
- PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("200p")
+ PORT_BIT(0xFF, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_START("BLACK1")
- PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("16")
- PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("17")
- PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("18")
- PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("19")
- PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("20")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("Test Switch")
PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("Refill Key") PORT_CODE(KEYCODE_R) PORT_TOGGLE
PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("Door Switch?") PORT_TOGGLE
@@ -1310,43 +1359,43 @@ INPUT_PORTS_END
static INPUT_PORTS_START( mating )
PORT_START("ORANGE1")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("00")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("01")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("02")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("03")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("04")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("05")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("06")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("07")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_START("ORANGE2")
- PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("08")
- PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("09")
- PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("10")
- PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("11")
- PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("12")
- PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("13")
- PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("14")
- PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("200p?")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_START("BLACK1")
- PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("16")
- PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("17")
- PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("18")
- PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("19")
- PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("20")
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("Test Button") PORT_CODE(KEYCODE_W) PORT_TOGGLE
PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("Refill Key") PORT_CODE(KEYCODE_R) PORT_TOGGLE
PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_INTERLOCK) PORT_NAME("Cashbox Door") PORT_CODE(KEYCODE_Q) PORT_TOGGLE
PORT_START("BLACK2")
- PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("Right Yellow")
- PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_BUTTON1) PORT_NAME("Right Red") // selects the answer
- PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("26")
- PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("Left Yellow")
- PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("Left Red")
- PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("Getout Yellow")
- PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_OTHER) PORT_NAME("Getout Red")/* Labelled Escape on cabinet */
+ PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_BUTTON1) PORT_NAME("Right Yellow")
+ PORT_BIT(0x02, IP_ACTIVE_HIGH, IPT_BUTTON2) PORT_NAME("Right Red") // selects the answer
+ PORT_BIT(0x04, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x08, IP_ACTIVE_HIGH, IPT_BUTTON3) PORT_NAME("Left Yellow")
+ PORT_BIT(0x10, IP_ACTIVE_HIGH, IPT_BUTTON4) PORT_NAME("Left Red")
+ PORT_BIT(0x20, IP_ACTIVE_HIGH, IPT_UNUSED)
+ PORT_BIT(0x40, IP_ACTIVE_HIGH, IPT_UNUSED)
PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_SERVICE) PORT_NAME("100p Service?")
PORT_START("DIL1")
@@ -1899,34 +1948,6 @@ static INPUT_PORTS_START( adders )
PORT_BIT(0x80, IP_ACTIVE_HIGH, IPT_COIN4) PORT_NAME("100p")PORT_IMPULSE(5)
INPUT_PORTS_END
-/* OKI M6376 (for Mating Game) FIXME */
-static READ16_DEVICE_HANDLER( oki_r )
-{
-// logerror("RO%X \n",offset);
-
- {
- return device->machine().rand();
- }
-}
-
-static WRITE16_DEVICE_HANDLER( oki_w )
-{
- // 0x10: .xxx xxxx OKIM6736 I6-I0
- // 0x12: .... ...x OKIM6736 /ST
-
- //FIXME
- if (offset == 0x10)
- {
- okim6376_w(device, 0, data & 0x7f);
- }
- if (offset == 0x12)
- {
- okim6376_st_w(device,data & 0x01);
- }
-
- logerror("O%X D%X\n",offset, data);
-}
-
static void video_reset(device_t *device)
{
device->machine().device("6840ptm_68k")->reset();
@@ -1991,6 +2012,26 @@ static ADDRESS_MAP_START( mpu4_68k_map, AS_PROGRAM, 16 )
AM_RANGE(0xffd000, 0xffd00f) AM_READWRITE(characteriser16_r, characteriser16_w)
ADDRESS_MAP_END
+static ADDRESS_MAP_START( mpu4oki_68k_map, AS_PROGRAM, 16 )
+ AM_RANGE(0x000000, 0x5fffff) AM_ROM AM_WRITENOP
+ AM_RANGE(0x600000, 0x63ffff) AM_RAM /* The Mating Game has an extra 256kB RAM on the program card */
+ AM_RANGE(0x640000, 0x7fffff) AM_NOP /* Possible bug, reads and writes here */
+ AM_RANGE(0x800000, 0x80ffff) AM_RAM AM_BASE_MEMBER(mpu4_state, m_vid_mainram)
+ AM_RANGE(0x900000, 0x900001) AM_DEVWRITE8("saa", saa1099_data_w, 0x00ff)
+ AM_RANGE(0x900002, 0x900003) AM_DEVWRITE8("saa", saa1099_control_w, 0x00ff)
+ AM_RANGE(0xa00000, 0xa00003) AM_READWRITE(ef9369_r, ef9369_w)
+ AM_RANGE(0xb00000, 0xb0000f) AM_READWRITE(mpu4_vid_scn2674_r, mpu4_vid_scn2674_w)
+ AM_RANGE(0xc00000, 0xc1ffff) AM_READWRITE(mpu4_vid_vidram_r, mpu4_vid_vidram_w)
+ AM_RANGE(0xff8000, 0xff8001) AM_DEVREADWRITE8_MODERN("acia6850_1", acia6850_device, status_read, control_write, 0xff)
+ AM_RANGE(0xff8002, 0xff8003) AM_DEVREADWRITE8_MODERN("acia6850_1", acia6850_device, data_read, data_write, 0xff)
+ AM_RANGE(0xff9000, 0xff900f) AM_DEVREADWRITE8_MODERN("6840ptm_68k", ptm6840_device, read, write, 0xff)
+ AM_RANGE(0xffa040, 0xffa04f) AM_DEVREAD8_MODERN("ptm_ic3ss_vid", ptm6840_device, read,0xff) // 6840PTM on sampled sound board
+ AM_RANGE(0xffa040, 0xffa04f) AM_WRITE8(ic3ss_vid_w,0x00ff) // 6840PTM on sampled sound board
+ AM_RANGE(0xffa060, 0xffa067) AM_DEVREADWRITE8_MODERN("pia_ic4ss", pia6821_device, read, write,0x00ff) // PIA6821 on sampled sound board
+ AM_RANGE(0xffd000, 0xffd00f) AM_READWRITE(characteriser16_r, characteriser16_w)
+ AM_RANGE(0xfff000, 0xffffff) AM_NOP /* Possible bug, reads and writes here */
+ADDRESS_MAP_END
+
/* TODO: Fix up MPU4 map*/
static ADDRESS_MAP_START( mpu4_6809_map, AS_PROGRAM, 8 )
AM_RANGE(0x0000, 0x07ff) AM_RAM AM_SHARE("nvram")
@@ -2073,9 +2114,10 @@ static ADDRESS_MAP_START( bwbvid5_68k_map, AS_PROGRAM, 16 )
AM_RANGE(0xc00000, 0xc1ffff) AM_READWRITE(mpu4_vid_vidram_r, mpu4_vid_vidram_w)
AM_RANGE(0xe00000, 0xe00001) AM_DEVREADWRITE8_MODERN("acia6850_1", acia6850_device, status_read, control_write, 0xff)
AM_RANGE(0xe00002, 0xe00003) AM_DEVREADWRITE8_MODERN("acia6850_1", acia6850_device, data_read, data_write, 0xff)
- AM_RANGE(0xe01000, 0xe0100f) AM_DEVREADWRITE8_MODERN("6840ptm_68k", ptm6840_device, read, write, 0xff)
- AM_RANGE(0xe02000, 0xe02007) AM_DEVREADWRITE8_MODERN("pia_ic4ss", pia6821_device, read, write, 0xff)
- AM_RANGE(0xe03000, 0xe0300f) AM_DEVREADWRITE8_MODERN("6840ptm_ic3ss", ptm6840_device, read, write, 0xff)
+ AM_RANGE(0xe01000, 0xe0100f) AM_DEVREADWRITE8_MODERN("6840ptm_68k", ptm6840_device, read, write, 0x00ff)
+ AM_RANGE(0xe02000, 0xe02007) AM_DEVREADWRITE8_MODERN("pia_ic4ss", pia6821_device, read, write, 0xff00)
+ AM_RANGE(0xe03000, 0xe0300f) AM_DEVREAD8_MODERN("ptm_ic3ss_vid", ptm6840_device, read,0xff00) // 6840PTM on sampled sound board
+ AM_RANGE(0xe03000, 0xe0300f) AM_WRITE8(ic3ss_vid_w,0xff00) // 6840PTM on sampled sound board
AM_RANGE(0xe04000, 0xe0400f) AM_READWRITE(bwb_characteriser16_r, bwb_characteriser16_w)//AM_READWRITE(adpcm_r, adpcm_w) CHR ?
ADDRESS_MAP_END
@@ -2252,7 +2294,7 @@ static TIMER_DEVICE_CALLBACK( scanline_timer_callback )
/* Ready - this triggers for the first scanline of the screen */
if (state->m_scn2674_irq_mask&0x02)
{
- LOGSTUFF(("SCN2674 Ready\n"));
+ LOG2674(("SCN2674 Ready\n"));
state->m_scn2674_irq_state = 1;
state->m_scn2674_irq_register |= 0x02;
update_mpu68_interrupts(timer.machine());
@@ -2262,10 +2304,11 @@ static TIMER_DEVICE_CALLBACK( scanline_timer_callback )
// should be triggered at the start of each ROW (line zero for that row)
if ((current_scanline%8 == 7) && (current_scanline<296))
{
+
state->m_scn2674_status_register |= 0x08;
if (state->m_scn2674_irq_mask&0x08)
{
- LOGSTUFF(("SCN2674 Line Zero\n"));
+ LOG2674(("SCN2674 Line Zero\n"));
state->m_scn2674_irq_state = 1;
state->m_scn2674_irq_register |= 0x08;
update_mpu68_interrupts(timer.machine());
@@ -2283,7 +2326,7 @@ static TIMER_DEVICE_CALLBACK( scanline_timer_callback )
state->m_scn2674_status_register |= 0x04;
if (state->m_scn2674_irq_mask&0x04)
{
- LOGSTUFF(("SCN2674 Split Screen 1\n"));
+ LOG2674(("SCN2674 Split Screen 1\n"));
state->m_scn2674_irq_state = 1;
update_mpu68_interrupts(timer.machine());
timer.machine().primary_screen->update_partial(timer.machine().primary_screen->vpos());
@@ -2303,7 +2346,7 @@ static TIMER_DEVICE_CALLBACK( scanline_timer_callback )
state->m_scn2674_status_register |= 0x01;
if (state->m_scn2674_irq_mask&0x01)
{
- LOGSTUFF(("SCN2674 Split Screen 2 irq\n"));
+ LOG2674(("SCN2674 Split Screen 2 irq\n"));
state->m_scn2674_irq_state = 1;
state->m_scn2674_irq_register |= 0x01;
update_mpu68_interrupts(timer.machine());
@@ -2320,7 +2363,7 @@ static TIMER_DEVICE_CALLBACK( scanline_timer_callback )
state->m_scn2674_status_register |= 0x10;
if (state->m_scn2674_irq_mask&0x10)
{
- LOGSTUFF(("vblank irq\n"));
+ //LOG2674(("vblank irq\n"));
state->m_scn2674_irq_state = 1;
state->m_scn2674_irq_register |= 0x10;
update_mpu68_interrupts(timer.machine());
@@ -2360,7 +2403,7 @@ static MACHINE_CONFIG_START( mpu4_vid, mpu4_state )
MCFG_CPU_ADD("video", M68000, VIDEO_MASTER_CLOCK )
MCFG_CPU_PROGRAM_MAP(mpu4_68k_map)
- MCFG_QUANTUM_TIME(attotime::from_hz(960))
+// MCFG_QUANTUM_TIME(attotime::from_hz(960))
MCFG_MACHINE_START(mpu4_vid)
MCFG_MACHINE_RESET(mpu4_vid)
@@ -2387,7 +2430,12 @@ static MACHINE_CONFIG_DERIVED( crmaze, mpu4_vid )
MACHINE_CONFIG_END
static MACHINE_CONFIG_DERIVED( mating, crmaze )
- MCFG_SOUND_ADD("oki", OKIM6376, 64000) //?
+ MCFG_CPU_MODIFY("video")
+ MCFG_CPU_PROGRAM_MAP(mpu4oki_68k_map)
+ MCFG_PTM6840_ADD("ptm_ic3ss_vid", ptm_ic3ss_intf)
+ MCFG_PIA6821_ADD("pia_ic4ss", pia_ic4ss_intf)
+
+ MCFG_SOUND_ADD("msm6376", OKIM6376, 128000) //?
MCFG_SOUND_ROUTE(0, "lspeaker", 0.5)
MCFG_SOUND_ROUTE(1, "rspeaker", 0.5)
MACHINE_CONFIG_END
@@ -2452,10 +2500,10 @@ static MACHINE_CONFIG_DERIVED( bwbvid5, bwbvid )
MCFG_CPU_MODIFY("video")
MCFG_CPU_PROGRAM_MAP(bwbvid5_68k_map)
- MCFG_PTM6840_ADD("6840ptm_ic3ss", ptm_ic3ss_intf)
+ MCFG_PTM6840_ADD("ptm_ic3ss_vid", ptm_ic3ss_intf)
MCFG_PIA6821_ADD("pia_ic4ss", pia_ic4ss_intf)
- MCFG_SOUND_ADD("msm6376", OKIM6376, 64000) //?
+ MCFG_SOUND_ADD("msm6376", OKIM6376, 128000) //?
MCFG_SOUND_ROUTE(0, "lspeaker", 0.5)
MCFG_SOUND_ROUTE(1, "rspeaker", 0.5)
@@ -2873,14 +2921,6 @@ static DRIVER_INIT (crmaze3a)
static DRIVER_INIT (mating)
{
mpu4_state *state = machine.driver_data<mpu4_state>();
- address_space *space = machine.device("video")->memory().space(AS_PROGRAM);
- device_t *device = machine.device("oki");
-
- /* The Mating Game has an extra 256kB RAM on the program card */
- space->install_ram(0x600000, 0x63ffff);
-
- /* There is also an OKIM6376 present on the program card */
- space->install_legacy_readwrite_handler(*device, 0xffa040, 0xffa0ff, FUNC(oki_r), FUNC(oki_w) );
state->m_reels = 0;//currently no hybrid games
state->m_current_chr_table = mating_data;
@@ -3291,7 +3331,7 @@ ROM_START( mating )
ROM_LOAD16_BYTE( "matq.p10", 0x400001, 0x040000, CRC(90364c3c) SHA1(6a4d2a3dd2cf9040887503888e6f38341578ad64) )
/* Mating Game has an extra OKI sound chip */
- ROM_REGION( 0x200000, "oki", 0 )
+ ROM_REGION( 0x200000, "msm6376", 0 )
ROM_LOAD( "matsnd.p1", 0x000000, 0x080000, CRC(f16df9e3) SHA1(fd9b82d73e18e635a9ea4aabd8c0b4aa2c8c6fdb) )
ROM_LOAD( "matsnd.p2", 0x080000, 0x080000, CRC(0c041621) SHA1(9156bf17ef6652968d9fbdc0b2bde64d3a67459c) )
ROM_LOAD( "matsnd.p3", 0x100000, 0x080000, CRC(c7435af9) SHA1(bd6080afaaaecca0d65e6d4125b46849aa4d1f33) )
@@ -3315,7 +3355,7 @@ ROM_START( matingd )
ROM_LOAD16_BYTE( "matq.p10", 0x400001, 0x040000, CRC(90364c3c) SHA1(6a4d2a3dd2cf9040887503888e6f38341578ad64) )
/* Mating Game has an extra OKI sound chip */
- ROM_REGION( 0x200000, "oki", 0 )
+ ROM_REGION( 0x200000, "msm6376", 0 )
ROM_LOAD( "matsnd.p1", 0x000000, 0x080000, CRC(f16df9e3) SHA1(fd9b82d73e18e635a9ea4aabd8c0b4aa2c8c6fdb) )
ROM_LOAD( "matsnd.p2", 0x080000, 0x080000, CRC(0c041621) SHA1(9156bf17ef6652968d9fbdc0b2bde64d3a67459c) )
ROM_LOAD( "matsnd.p3", 0x100000, 0x080000, CRC(c7435af9) SHA1(bd6080afaaaecca0d65e6d4125b46849aa4d1f33) )
diff --git a/src/mame/includes/jpmimpct.h b/src/mame/includes/jpmimpct.h
index b688413f32d..b0fe229345a 100644
--- a/src/mame/includes/jpmimpct.h
+++ b/src/mame/includes/jpmimpct.h
@@ -64,6 +64,12 @@ public:
UINT8 m_Lamps[256];
int m_optic_pattern;
int m_payen;
+ int m_alpha_data_line;
+ int m_alpha_clock;
+ int m_hopinhibit;
+ int m_slidesout;
+ int m_hopper[3];
+ int m_motor[3];
UINT16 *m_vram;
struct bt477_t m_bt477;
};