diff options
Diffstat (limited to 'src/mame/audio/namco54.c')
-rw-r--r-- | src/mame/audio/namco54.c | 132 |
1 files changed, 132 insertions, 0 deletions
diff --git a/src/mame/audio/namco54.c b/src/mame/audio/namco54.c new file mode 100644 index 00000000000..5a4dacf4dc2 --- /dev/null +++ b/src/mame/audio/namco54.c @@ -0,0 +1,132 @@ +/*************************************************************************** + +Namco 54XX + +This custom chip is a Fujitsu MB8844 MCU programmed to act as a noise +generator. It is used for explosions, the shoot sound in Bosconian, and the +tire screech sound in Pole Position. + +CMD = command from main CPU +OUTn = sound outputs (3 channels) + +The chip reads the command when the /IRQ is pulled down. + + +------+ + EXTAL|1 28|Vcc + XTAL|2 27|CMD7 +/RESET|3 26|CMD6 +OUT0.0|4 25|CMD5 +OUT0.1|5 24|CMD4 +OUT0.2|6 23|/IRQ +OUT0.3|7 22|n.c. [1] +OUT1.0|8 21|n.c. [1] +OUT1.1|9 20|OUT2.3 +OUT1.2|10 19|OUT2.2 +OUT1.3|11 18|OUT2.1 + CMD0|12 17|OUT2.0 + CMD1|13 16|CMD3 + GND|14 15|CMD2 + +------+ + + +[1] The RNG that drives the type A output is output on pin 21, and the one that +drives the type B output is output on pin 22, but those pins are not connected +on the board. + + +The command format is very simple: + +0x: nop +1x: play sound type A +2x: play sound type B +3x: set parameters (type A) (followed by 4 bytes) +4x: set parameters (type B) (followed by 4 bytes) +5x: play sound type C +6x: set parameters (type C) (followed by 5 bytes) +7x: set volume for sound type C to x +8x-Fx: nop + +***************************************************************************/ + +#include "driver.h" +#include "namco54.h" +#include "cpu/mb88xx/mb88xx.h" + + +static UINT8 latched_cmd; + +static TIMER_CALLBACK( namco_54xx_latch_callback ) +{ + latched_cmd = param; +} + +static READ8_HANDLER( namco_54xx_K_r ) +{ + return latched_cmd >> 4; +} + +static READ8_HANDLER( namco_54xx_R0_r ) +{ + return latched_cmd & 0x0f; +} + + +static WRITE8_HANDLER( namco_54xx_O_w ) +{ + UINT8 out = (data & 0x0f); + if (data & 0x10) + discrete_sound_w(NAMCO_54XX_1_DATA, out); + else + discrete_sound_w(NAMCO_54XX_0_DATA, out); +} + +static WRITE8_HANDLER( namco_54xx_R1_w ) +{ + UINT8 out = (data & 0x0f); + + discrete_sound_w(NAMCO_54XX_2_DATA, out); +} + + + +ADDRESS_MAP_START( namco_54xx_map_program, ADDRESS_SPACE_PROGRAM, 8 ) + AM_RANGE(0x000, 0x3ff) AM_ROM +ADDRESS_MAP_END + +ADDRESS_MAP_START( namco_54xx_map_data, ADDRESS_SPACE_DATA, 8 ) + AM_RANGE(0x00, 0x3f) AM_RAM +ADDRESS_MAP_END + +ADDRESS_MAP_START( namco_54xx_map_io, ADDRESS_SPACE_IO, 8 ) + AM_RANGE(MB88_PORTK, MB88_PORTK) AM_READ(namco_54xx_K_r) + AM_RANGE(MB88_PORTO, MB88_PORTO) AM_WRITE(namco_54xx_O_w) + AM_RANGE(MB88_PORTR0, MB88_PORTR0) AM_READ(namco_54xx_R0_r) + AM_RANGE(MB88_PORTR1, MB88_PORTR1) AM_WRITE(namco_54xx_R1_w) + AM_RANGE(MB88_PORTR2, MB88_PORTR2) AM_NOP +ADDRESS_MAP_END + + + +static TIMER_CALLBACK( namco_54xx_irq_clear ) +{ + cpunum_set_input_line(param, 0, CLEAR_LINE); +} + +void namco_54xx_write(UINT8 data) +{ + int cpunum = mame_find_cpu_index(Machine, CPUTAG_54XX); + + if (cpunum == -1) + return; + + timer_call_after_resynch(data, namco_54xx_latch_callback); + + cpunum_set_input_line(cpunum, 0, ASSERT_LINE); + + // The execution time of one instruction is ~4us, so we must make sure to + // give the cpu time to poll the /IRQ input before we clear it. + // The input clock to the 06XX interface chip is 64H, that is + // 18432000/6/64 = 48kHz, so it makes sense for the irq line to be + // asserted for one clock cycle ~= 21us. + timer_set(ATTOTIME_IN_USEC(21), cpunum, namco_54xx_irq_clear); +} |