diff options
Diffstat (limited to 'src/mame/drivers/genesis.c')
-rw-r--r-- | src/mame/drivers/genesis.c | 457 |
1 files changed, 0 insertions, 457 deletions
diff --git a/src/mame/drivers/genesis.c b/src/mame/drivers/genesis.c deleted file mode 100644 index 7febfe33adb..00000000000 --- a/src/mame/drivers/genesis.c +++ /dev/null @@ -1,457 +0,0 @@ -/* Some Generic Sega Genesis stuff used by Megatech / Megaplay etc. */ - -/* - -Genesis hardware games are in - -megatech.c -megaplay.c -gene_sm.c -segac2.c - -*/ - -#include "driver.h" -#include "cpu/z80/z80.h" -#include "cpu/m68000/m68000.h" -#include "sound/2612intf.h" -#include "sound/sn76496.h" - -#include "genesis.h" - -#define MASTER_CLOCK 53693100 - - -/******************** Sega Genesis ******************************/ - -/* Genesis based */ -static UINT32 z80_68000_latch = 0; -static UINT32 z80_latch_bitcount = 0; - -/* interrupt states */ -static UINT8 irq2_int; /* INT2 */ -static UINT8 scanline_int; /* INT4 - programmable */ -static UINT8 vblank_int; /* INT6 - on every VBLANK */ - -static emu_timer * scan_timer; - - -static int z80running; -UINT16 *genesis_68k_ram; -UINT8 *genesis_z80_ram; - - - -/****************************************************************************** - Interrupt handling -******************************************************************************* - - The Genesis uses 2 Different Interrupts, IRQ4 and IRQ6. - The C2 system uses IRQ2 as well. - - IRQ6 = Vblank, this happens after the last visible line of the display has - been drawn (after line 224) - - IRQ4 = H-Int, this happens based upon the value in H-Int Counter. If the - Horizontal Interrupt is enabled and the Counter Value = 0 there - will be a Level 4 Interrupt Triggered - - IRQ2 = sound int, generated by the YM3438 - - -------- - - More H-Counter Information: - - Providing Horizontal Interrupts are active the H-Counter will be loaded - with the value stored in register #10 (0x0A) at the following times: - (1) At the top of the display, before drawing the first line - (2) When the counter has expired - (3) During the VBlank Period (lines 224-261) - The Counter is decreased by 1 after every line. - -******************************************************************************/ - -/* call this whenever the interrupt state has changed */ -static void update_interrupts(running_machine *machine) -{ - cputag_set_input_line(machine, "maincpu", 2, irq2_int ? ASSERT_LINE : CLEAR_LINE); - cputag_set_input_line(machine, "maincpu", 4, scanline_int ? ASSERT_LINE : CLEAR_LINE); - cputag_set_input_line(machine, "maincpu", 6, vblank_int ? ASSERT_LINE : CLEAR_LINE); -} - - -/* timer callback to turn off the IRQ4 signal after a short while */ -static TIMER_CALLBACK( vdp_int4_off ) -{ - scanline_int = 0; - update_interrupts(machine); -} - - -/* timer callback to handle reloading the H counter and generate IRQ4 */ -static TIMER_CALLBACK( vdp_reload_counter ) -{ - int scanline = param; - - /* generate an int if they're enabled */ - if (genesis_vdp_regs[0] & 0x10)/* && !(misc_io_data[7] & 0x10))*/ - if (scanline != 0 || genesis_vdp_regs[10] == 0) - { - scanline_int = 1; - update_interrupts(machine); - timer_set(machine, video_screen_get_time_until_pos(machine->primary_screen, scanline + 1, 0), NULL, 0, vdp_int4_off); - } - - /* advance to the next scanline */ - /* behavior 2: 0 count means interrupt after one scanline */ - /* (this behavior matches the Sega C2 emulator) */ - scanline += genesis_vdp_regs[10] + 1; - if (scanline >= 224) - scanline = 0; - - /* set a timer */ - timer_adjust_oneshot(scan_timer, video_screen_get_time_until_pos(machine->primary_screen, scanline, 320), scanline); -} - - -/* timer callback to turn off the IRQ6 signal after a short while */ -static TIMER_CALLBACK( vdp_int6_off ) -{ - vblank_int = 0; - update_interrupts(machine); -} - - -/* interrupt callback to generate the VBLANK interrupt */ -INTERRUPT_GEN( genesis_vblank_interrupt ) -{ - /* generate the interrupt */ - vblank_int = 1; - update_interrupts(device->machine); - - /* set a timer to turn it off */ - timer_set(device->machine, video_screen_get_time_until_pos(device->machine->primary_screen, video_screen_get_vpos(device->machine->primary_screen), 22), NULL, 0, vdp_int6_off); -} - - -/* interrupt callback to generate the YM3438 interrupt */ -void genesis_irq2_interrupt(const device_config *device, int state) -{ - irq2_int = state; - update_interrupts(device->machine); -} - - -MACHINE_START( genesis ) -{ - state_save_register_global(machine, irq2_int); - state_save_register_global(machine, scanline_int); - state_save_register_global(machine, vblank_int); -} - - -MACHINE_RESET( genesis ) -{ - /* C2 doesn't have a Z80, so we can't just assume */ - if (cputag_get_cpu(machine, "genesis_snd_z80") != NULL && cpu_get_type(cputag_get_cpu(machine, "genesis_snd_z80")) == CPU_Z80) - { - /* the following ensures that the Z80 begins without running away from 0 */ - /* 0x76 is just a forced 'halt' as soon as the CPU is initially run */ - genesis_z80_ram[0] = 0x76; - genesis_z80_ram[0x38] = 0x76; - - cputag_set_input_line(machine, "genesis_snd_z80", INPUT_LINE_HALT, ASSERT_LINE); - - z80running = 0; - } - - logerror("Machine init\n"); - - /* set the first scanline 0 timer to go off */ - scan_timer = timer_alloc(machine, vdp_reload_counter, NULL); - timer_adjust_oneshot(scan_timer, video_screen_get_time_until_pos(machine->primary_screen, 0, 320), 0); -} - -READ16_HANDLER ( genesis_68k_to_z80_r ) -{ - offset *= 2; - offset &= 0x7fff; - - /* Shared Ram */ - if ((offset >= 0x0000) && (offset <= 0x3fff)) - { - offset &=0x1fff; -// logerror("soundram_r returning %x\n",(gen_z80_shared[offset] << 8) + gen_z80_shared[offset+1]); - return (genesis_z80_ram[offset] << 8) + genesis_z80_ram[offset+1]; - } - - - /* YM2610 */ - if ((offset >= 0x4000) && (offset <= 0x5fff)) - { - if (ACCESSING_BITS_0_7) - offset += 1; - return ym3438_r(devtag_get_device(space->machine, "ym"), offset); - } - - /* Bank Register */ - if ((offset >= 0x6000) && (offset <= 0x60ff)) - { - - } - - /* Unused / Illegal */ - if ((offset >= 0x6100) && (offset <= 0x7eff)) - { - /* nothing */ - } - - /* VDP */ - if ((offset >= 0x7f00) && (offset <= 0x7fff)) - { - - } - - return 0x0000; -} - -WRITE16_HANDLER ( genesis_68k_to_z80_w ) -{ - offset *= 2; - offset &= 0x7fff; - - /* Shared Ram */ - if ((offset >= 0x0000) && (offset <= 0x3fff)) - { - offset &=0x1fff; - - if (ACCESSING_BITS_0_7) genesis_z80_ram[offset+1] = data & 0xff; - if (ACCESSING_BITS_8_15) genesis_z80_ram[offset] = (data >> 8) & 0xff; - } - - - /* YM2612 */ - if ((offset >= 0x4000) && (offset <= 0x5fff)) - { - const device_config *ym = devtag_get_device(space->machine, "ym"); - switch (offset & 3) - { - case 0: - if (ACCESSING_BITS_8_15) ym3438_control_port_a_w (ym, 0, (data >> 8) & 0xff); - else ym3438_data_port_a_w (ym, 0, (data >> 0) & 0xff); - break; - case 2: - if (ACCESSING_BITS_8_15) ym3438_control_port_b_w (ym, 0, (data >> 8) & 0xff); - else ym3438_data_port_b_w (ym, 0, (data >> 0) & 0xff); - break; - } - } - - /* Bank Register */ - if ((offset >= 0x6000) && (offset <= 0x60ff)) - { - - } - - /* Unused / Illegal */ - if ((offset >= 0x6100) && (offset <= 0x7eff)) - { - /* nothing */ - } - - /* VDP */ - if ((offset >= 0x7f00) && (offset <= 0x7fff)) - { - offset &= 0x1f; - - if ( (offset >= 0x10) && (offset <=0x17) ) - { - const device_config *sn = devtag_get_device(space->machine, "sn"); - if (ACCESSING_BITS_0_7) sn76496_w(sn, 0, data & 0xff); - if (ACCESSING_BITS_8_15) sn76496_w(sn, 0, (data >>8) & 0xff); - } - - } -} - -/* Gen I/O */ - -/* -cgfm info - -$A10001 Version -$A10003 Port A data -$A10005 Port B data -$A10007 Port C data -$A10009 Port A control -$A1000B Port B control -$A1000D Port C control -$A1000F Port A TxData -$A10011 Port A RxData -$A10013 Port A serial control -$A10015 Port B TxData -$A10017 Port B RxData -$A10019 Port B serial control -$A1001B Port C TxData -$A1001D Port C RxData -$A1001F Port C serial control - -*/ - -#if 0 -static ADDRESS_MAP_START( genesis_map, ADDRESS_SPACE_PROGRAM, 16 ) - AM_RANGE(0x000000, 0x3fffff) AM_ROM /* Cartridge Program Rom */ - AM_RANGE(0xa00000, 0xa0ffff) AM_READWRITE(genesis_68k_to_z80_r, genesis_68k_to_z80_w) - AM_RANGE(0xa10000, 0xa1001f) AM_READWRITE(genesis_io_r, genesis_io_w) AM_BASE(&genesis_io_ram) /* Genesis Input */ - AM_RANGE(0xa11000, 0xa11203) AM_WRITE(genesis_ctrl_w) - AM_RANGE(0xc00000, 0xc0001f) AM_READWRITE(genesis_vdp_r, genesis_vdp_w) /* VDP Access */ - AM_RANGE(0xfe0000, 0xfeffff) AM_RAMBANK(3) /* Main Ram */ - AM_RANGE(0xff0000, 0xffffff) AM_RAM AM_BASE(&genesis_68k_ram) /* Main Ram */ -ADDRESS_MAP_END -#endif - -/* Z80 Sound Hardware - based on MESS code, to be improved, it can do some strange things */ - - -static WRITE8_HANDLER ( genesis_bank_select_w ) /* note value will be meaningless unless all bits are correctly set in */ -{ - if (offset !=0 ) return; -// if (!z80running) logerror("undead Z80 latch write!\n"); - if (z80_latch_bitcount == 0) z80_68000_latch = 0; - - z80_68000_latch = z80_68000_latch | ((( ((UINT8)data) & 0x01) << (15+z80_latch_bitcount))); - logerror("value %x written to latch\n", data); - z80_latch_bitcount++; - if (z80_latch_bitcount == 9) - { - z80_latch_bitcount = 0; - logerror("latch set, value %x\n", z80_68000_latch); - } -} - -READ8_HANDLER ( genesis_z80_r ) -{ - offset += 0x4000; - - /* YM2610 */ - if ((offset >= 0x4000) && (offset <= 0x5fff)) - { - return ym3438_r(devtag_get_device(space->machine, "ym"), offset); - } - - /* Bank Register */ - if ((offset >= 0x6000) && (offset <= 0x60ff)) - { - - } - - /* Unused / Illegal */ - if ((offset >= 0x6100) && (offset <= 0x7eff)) - { - /* nothing */ - } - - /* VDP */ - if ((offset >= 0x7f00) && (offset <= 0x7fff)) - { - - } - - return 0x00; -} - -WRITE8_HANDLER ( genesis_z80_w ) -{ - offset += 0x4000; - - /* YM2610 */ - if ((offset >= 0x4000) && (offset <= 0x5fff)) - { - ym3438_w(devtag_get_device(space->machine, "ym"), offset & 3, data); - } - - /* Bank Register */ - if ((offset >= 0x6000) && (offset <= 0x60ff)) - { - genesis_bank_select_w(space, offset & 0xff, data); - } - - /* Unused / Illegal */ - if ((offset >= 0x6100) && (offset <= 0x7eff)) - { - /* nothing */ - } - - /* VDP */ - if ((offset >= 0x7f00) && (offset <= 0x7fff)) - { - - } -} - -READ8_HANDLER ( genesis_z80_bank_r ) -{ - int address = (z80_68000_latch) + (offset & 0x7fff); - const UINT8 *base = memory_region(space->machine, "soundcpu"); - - if (!z80running) logerror("undead Z80->68000 read!\n"); - - if (z80_latch_bitcount != 0) logerror("reading whilst latch being set!\n"); - - logerror("z80 read from address %x\n", address); - - /* Read the data out of the 68k ROM */ - if (base != NULL && address < 0x400000) return base[BYTE_XOR_BE(address)]; - /* else read the data out of the 68k RAM */ -// else if (address > 0xff0000) return genesis_68k_ram[BYTE_XOR_BE(offset)]; - - return -1; -} - - -#if 0 -static ADDRESS_MAP_START( genesis_z80_map, ADDRESS_SPACE_PROGRAM, 8 ) - AM_RANGE(0x0000, 0x1fff) AM_RAMBANK(1) AM_BASE(&genesis_z80_ram) - AM_RANGE(0x2000, 0x3fff) AM_RAMBANK(2) /* mirror */ - AM_RANGE(0x4000, 0x7fff) AM_READWRITE(genesis_z80_r, genesis_z80_w) - AM_RANGE(0x8000, 0xffff) AM_READ(genesis_z80_bank_r) - // AM_RANGE(0x8000, 0xffff) AM_WRITE(genesis_z80_bank_w) -ADDRESS_MAP_END - -static MACHINE_DRIVER_START( genesis_base ) - /*basic machine hardware */ - MDRV_CPU_ADD("maincpu", M68000, MASTER_CLOCK / 7) - MDRV_CPU_PROGRAM_MAP(genesis_map) - MDRV_CPU_VBLANK_INT("screen", genesis_vblank_interrupt) - - MDRV_CPU_ADD("soundcpu", Z80, MASTER_CLOCK / 15) - MDRV_CPU_PROGRAM_MAP(genesis_z80_map) - MDRV_CPU_VBLANK_INT("screen", irq0_line_hold) /* from vdp at scanline 0xe0 */ - - MDRV_QUANTUM_TIME(HZ(6000)) - - MDRV_MACHINE_START(genesis) - MDRV_MACHINE_RESET(genesis) - - /* video hardware */ - MDRV_VIDEO_ATTRIBUTES(VIDEO_HAS_SHADOWS | VIDEO_HAS_HIGHLIGHTS) - - MDRV_SCREEN_ADD("screen", RASTER) - MDRV_SCREEN_REFRESH_RATE(60) - MDRV_SCREEN_FORMAT(BITMAP_FORMAT_INDEXED16) - MDRV_SCREEN_SIZE(342,262) - MDRV_SCREEN_VISIBLE_AREA(0, 319, 0, 223) - - MDRV_PALETTE_LENGTH(2048) - - MDRV_VIDEO_START(genesis) - MDRV_VIDEO_UPDATE(genesis) - - /* sound hardware */ - MDRV_SPEAKER_STANDARD_MONO("mono") - - MDRV_SOUND_ADD("ym", YM3438, MASTER_CLOCK/7) - MDRV_SOUND_ROUTE(0, "mono", 0.50) - MDRV_SOUND_ROUTE(1, "mono", 0.50) -MACHINE_DRIVER_END -#endif |