summaryrefslogtreecommitdiffstatshomepage
path: root/src/mame/machine/tatsumi.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/mame/machine/tatsumi.c')
-rw-r--r--src/mame/machine/tatsumi.c373
1 files changed, 373 insertions, 0 deletions
diff --git a/src/mame/machine/tatsumi.c b/src/mame/machine/tatsumi.c
new file mode 100644
index 00000000000..f261a96abf7
--- /dev/null
+++ b/src/mame/machine/tatsumi.c
@@ -0,0 +1,373 @@
+#include "driver.h"
+#include "tatsumi.h"
+#include "sound/2151intf.h"
+#include "sound/okim6295.h"
+
+/*static*/ UINT16 tatsumi_control_word=0;
+static UINT16 tatsumi_last_control=0;
+static UINT16 tatsumi_last_irq=0;
+static UINT8 apache3_adc;
+
+UINT16 *tatsumi_68k_ram;
+UINT8 *apache3_z80_ram;
+
+/******************************************************************************/
+
+void tatsumi_reset(void)
+{
+ tatsumi_last_irq=0;
+ tatsumi_last_control=0;
+ tatsumi_control_word=0;
+ apache3_adc=0;
+
+ state_save_register_global(tatsumi_last_irq);
+ state_save_register_global(tatsumi_last_control);
+ state_save_register_global(tatsumi_control_word);
+ state_save_register_global(apache3_adc);
+}
+
+/******************************************************************************/
+
+READ16_HANDLER( apache3_bank_r )
+{
+ return tatsumi_control_word;
+}
+
+WRITE16_HANDLER( apache3_bank_w )
+{
+ /*
+ 0x8000 - Set when accessing palette ram (not implemented, perhaps blank screen?)
+ 0x0080 - Set when accessing IO cpu RAM/ROM (implemented as halt cpu)
+ 0x0060 - IOP bank to access from main cpu (0x0 = RAM, 0x20 = lower ROM, 0x60 = upper ROM)
+ 0x0010 - Set when accessing OBJ cpu RAM/ROM (implemented as halt cpu)
+ 0x000f - OBJ bank to access from main cpu (0x8 = RAM, 0x0 to 0x7 = ROM)
+ */
+
+ COMBINE_DATA(&tatsumi_control_word);
+
+ if (tatsumi_control_word&0x7f00)
+ {
+ logerror("Unknown control Word: %04x\n",tatsumi_control_word);
+ cpunum_set_input_line(3, INPUT_LINE_HALT, CLEAR_LINE); // ?
+ }
+ if ((tatsumi_control_word&0x8)==0 && !(tatsumi_last_control&0x8))
+ cpunum_set_input_line(1, INPUT_LINE_IRQ4, ASSERT_LINE);
+
+ if (tatsumi_control_word&0x10)
+ cpunum_set_input_line(1, INPUT_LINE_HALT, ASSERT_LINE);
+ else
+ cpunum_set_input_line(1, INPUT_LINE_HALT, CLEAR_LINE);
+
+ if (tatsumi_control_word&0x80)
+ cpunum_set_input_line(2, INPUT_LINE_HALT, ASSERT_LINE);
+ else
+ cpunum_set_input_line(2, INPUT_LINE_HALT, CLEAR_LINE);
+
+ tatsumi_last_control=tatsumi_control_word;
+}
+
+WRITE16_HANDLER( apache3_irq_ack_w )
+{
+ cpunum_set_input_line(1, INPUT_LINE_IRQ4, CLEAR_LINE);
+
+ if ((data&2) && (tatsumi_last_irq&2)==0)
+ {
+ cpunum_set_input_line(3, INPUT_LINE_HALT, ASSERT_LINE);
+ }
+
+ if ((tatsumi_last_irq&2) && (data&2)==0)
+ {
+ cpunum_set_input_line(3, INPUT_LINE_HALT, CLEAR_LINE);
+ cpunum_set_input_line_and_vector(3, 0, HOLD_LINE, 0xc7 | 0x10);
+ }
+
+ tatsumi_last_irq=data;
+}
+
+READ16_HANDLER( apache3_v30_v20_r )
+{
+ UINT8 value;
+
+ /* Each V20 byte maps to a V30 word */
+ if ((tatsumi_control_word&0xe0)==0xe0)
+ offset+=0xf8000; /* Upper half */
+ else if ((tatsumi_control_word&0xe0)==0xc0)
+ offset+=0xf0000;
+ else if ((tatsumi_control_word&0xe0)==0x80)
+ offset+=0x00000; // main ram
+ else
+ logerror("%08x: unmapped read z80 rom %08x\n",activecpu_get_pc(),offset);
+
+ cpuintrf_push_context(2);
+ value = program_read_byte(offset);
+ cpuintrf_pop_context();
+ return value | 0xff00;
+}
+
+WRITE16_HANDLER( apache3_v30_v20_w )
+{
+ if ((tatsumi_control_word&0xe0)!=0x80)
+ logerror("%08x: write unmapped v30 rom %08x\n",activecpu_get_pc(),offset);
+
+ /* Only 8 bits of the V30 data bus are connected - ignore writes to the other half */
+ if (ACCESSING_LSB)
+ {
+ cpuintrf_push_context(2);
+ program_write_byte(offset, data&0xff);
+ cpuintrf_pop_context();
+ }
+}
+
+READ16_HANDLER(apache3_z80_r)
+{
+ return apache3_z80_ram[offset];
+}
+
+WRITE16_HANDLER(apache3_z80_w)
+{
+ apache3_z80_ram[offset]=data&0xff;
+}
+
+READ8_HANDLER( apache3_adc_r )
+{
+ if (apache3_adc==0)
+ return readinputport(1);
+ return readinputport(2);
+}
+
+WRITE8_HANDLER( apache3_adc_w )
+{
+ apache3_adc=offset;
+}
+
+UINT16 apache3_a0000[16]; // TODO
+static int a3counter=0; // TODO
+
+WRITE16_HANDLER( apache3_a0000_w )
+{
+ if (a3counter>15) // TODO
+ return;
+ apache3_a0000[a3counter++]=data;
+}
+
+/******************************************************************************/
+
+READ16_HANDLER( roundup_v30_z80_r )
+{
+ UINT8 value;
+
+ /* Each Z80 byte maps to a V30 word */
+ if (tatsumi_control_word&0x20)
+ offset+=0x8000; /* Upper half */
+
+ cpuintrf_push_context(2);
+ value = program_read_byte(offset);
+ cpuintrf_pop_context();
+ return value | 0xff00;
+}
+
+WRITE16_HANDLER( roundup_v30_z80_w )
+{
+ /* Only 8 bits of the V30 data bus are connected - ignore writes to the other half */
+ if (ACCESSING_LSB)
+ {
+ if (tatsumi_control_word&0x20)
+ offset+=0x8000; /* Upper half of Z80 address space */
+
+ cpuintrf_push_context(2);
+ program_write_byte(offset, data&0xff);
+ cpuintrf_pop_context();
+ }
+}
+
+
+WRITE16_HANDLER( roundup5_control_w )
+{
+ COMBINE_DATA(&tatsumi_control_word);
+
+ if (tatsumi_control_word&0x10)
+ cpunum_set_input_line(1, INPUT_LINE_HALT, ASSERT_LINE);
+ else
+ cpunum_set_input_line(1, INPUT_LINE_HALT, CLEAR_LINE);
+
+ if (tatsumi_control_word&0x4)
+ cpunum_set_input_line(2, INPUT_LINE_HALT, ASSERT_LINE);
+ else
+ cpunum_set_input_line(2, INPUT_LINE_HALT, CLEAR_LINE);
+
+// if (offset==1 && (tatsumi_control_w&0xfeff)!=(last_bank&0xfeff))
+// logerror("%08x: Changed bank to %04x (%d)\n",activecpu_get_pc(),tatsumi_control_w,offset);
+
+//todo - watchdog
+
+ /* Bank:
+
+ 0x0017 : OBJ banks
+ 0x0018 : 68000 RAM mask 0x0380 used to save bits when writing
+ 0x0c10 : 68000 ROM
+
+ 0x0040 : Z80 rom (lower half) mapped to 0x10000
+ 0x0060 : Z80 rom (upper half) mapped to 0x10000
+
+ 0x0100 : watchdog.
+
+ 0x0c00 : vram bank (bits 0x7000 also set when writing vram)
+
+ 0x8000 : set whenever writing to palette ram?
+
+ Changed bank to 0060 (0)
+ */
+
+ if ((tatsumi_control_word&0x8)==0 && !(tatsumi_last_control&0x8))
+ cpunum_set_input_line(1, INPUT_LINE_IRQ4, ASSERT_LINE);
+// if (tatsumi_control_w&0x200)
+// cpu_set_reset_line(1, CLEAR_LINE);
+// else
+// cpu_set_reset_line(1, ASSERT_LINE);
+
+// if ((tatsumi_control_w&0x200) && (last_bank&0x200)==0)
+// logerror("68k irq\n");
+// if ((tatsumi_control_w&0x200)==0 && (last_bank&0x200)==0x200)
+// logerror("68k reset\n");
+
+ if (tatsumi_control_word==0x3a00) {
+// cpu_set_reset_line(1, CLEAR_LINE);
+ // logerror("68k on\n");
+
+ }
+
+ tatsumi_last_control=tatsumi_control_word;
+}
+
+WRITE16_HANDLER( roundup5_d0000_w )
+{
+ COMBINE_DATA(&roundup5_d0000_ram[offset]);
+// logerror("d_68k_d0000_w %06x %04x\n",activecpu_get_pc(),data);
+}
+
+WRITE16_HANDLER( roundup5_e0000_w )
+{
+ /* Bit 0x10 is road bank select,
+ Bit 0x100 is used, but unknown
+ */
+
+ COMBINE_DATA(&roundup5_e0000_ram[offset]);
+ cpunum_set_input_line(1, INPUT_LINE_IRQ4, CLEAR_LINE); // guess, probably wrong
+
+// logerror("d_68k_e0000_w %06x %04x\n",activecpu_get_pc(),data);
+}
+
+/******************************************************************************/
+
+READ16_HANDLER(cyclwarr_control_r)
+{
+// logerror("%08x: control_r\n",activecpu_get_pc());
+ return tatsumi_control_word;
+}
+
+WRITE16_HANDLER(cyclwarr_control_w)
+{
+ COMBINE_DATA(&tatsumi_control_word);
+
+// if ((tatsumi_control_word&0xfe)!=(tatsumi_last_control&0xfe))
+// logerror("%08x: control_w %04x\n",activecpu_get_pc(),data);
+
+/*
+
+0x1 - watchdog
+0x4 - cpu bus lock
+
+
+
+*/
+
+ if ((tatsumi_control_word&4)==4 && (tatsumi_last_control&4)==0) {
+// logerror("68k 2 halt\n");
+ cpunum_set_input_line(1, INPUT_LINE_HALT, ASSERT_LINE);
+ }
+
+ if ((tatsumi_control_word&4)==0 && (tatsumi_last_control&4)==4) {
+// logerror("68k 2 irq go\n");
+ cpunum_set_input_line(1, INPUT_LINE_HALT, CLEAR_LINE);
+ }
+
+
+ // hack
+ if (activecpu_get_pc()==0x2c3c34) {
+// cpu_set_reset_line(1, CLEAR_LINE);
+ // logerror("hack 68k2 on\n");
+ }
+
+ tatsumi_last_control=tatsumi_control_word;
+}
+
+/******************************************************************************/
+
+READ16_HANDLER( tatsumi_v30_68000_r )
+{
+ const UINT16* rom=(UINT16*)memory_region(REGION_CPU2);
+
+logerror("%05X:68000_r(%04X),cw=%04X\n", activecpu_get_pc(), offset*2, tatsumi_control_word);
+ /* Read from 68k RAM */
+ if ((tatsumi_control_word&0x1f)==0x18)
+ {
+ // hack to make roundup 5 boot
+ if (activecpu_get_pc()==0xec575)
+ {
+ UINT8 *dst = memory_region(REGION_CPU1);
+ dst[BYTE_XOR_LE(0xec57a)]=0x46;
+ dst[BYTE_XOR_LE(0xec57b)]=0x46;
+
+ dst[BYTE_XOR_LE(0xfc520)]=0x46; //code that stops cpu after coin counter goes mad..
+ dst[BYTE_XOR_LE(0xfc521)]=0x46;
+ dst[BYTE_XOR_LE(0xfc522)]=0x46;
+ dst[BYTE_XOR_LE(0xfc523)]=0x46;
+ dst[BYTE_XOR_LE(0xfc524)]=0x46;
+ dst[BYTE_XOR_LE(0xfc525)]=0x46;
+ }
+
+ return tatsumi_68k_ram[offset & 0x1fff];
+ }
+
+ /* Read from 68k ROM */
+ offset+=(tatsumi_control_word&0x7)*0x8000;
+
+ return rom[offset];
+}
+
+WRITE16_HANDLER( tatsumi_v30_68000_w )
+{
+ if ((tatsumi_control_word&0x1f)!=0x18)
+ logerror("68k write in bank %05x\n",tatsumi_control_word);
+
+ COMBINE_DATA(&tatsumi_68k_ram[offset]);
+}
+
+/***********************************************************************************/
+
+// Todo: Current YM2151 doesn't seem to raise the busy flag quickly enough for the
+// self-test in Tatsumi games. Needs fixed, but hack it here for now.
+READ8_HANDLER(tatsumi_hack_ym2151_r)
+{
+ int r=YM2151_status_port_0_r(0);
+
+ if (activecpu_get_pc()==0x2aca || activecpu_get_pc()==0x29fe
+ || activecpu_get_pc()==0xf9721)
+ return 0x80;
+ return r;
+}
+
+// Todo: Tatsumi self-test fails if OKI doesn't respond (when sound off).
+// Mame really should emulate the OKI status reads even with Mame sound off.
+READ8_HANDLER(tatsumi_hack_oki_r)
+{
+ int r=OKIM6295_status_0_r(0);
+
+ if (activecpu_get_pc()==0x2b70 || activecpu_get_pc()==0x2bb5
+ || activecpu_get_pc()==0x2acc
+ || activecpu_get_pc()==0xf9881)
+ return 0xf;
+ if (activecpu_get_pc()==0x2ba3 || activecpu_get_pc()==0x2a9b || activecpu_get_pc()==0x2adc)
+ return 0;
+ return r;
+}