1 // license:BSD-3-Clause
2 // copyright-holders:David Haywood
3 #ifndef MAME_INCLUDES_MEGADRIV_H
4 #define MAME_INCLUDES_MEGADRIV_H
5 
6 #pragma once
7 
8 #include "coreutil.h"
9 #include "cpu/m68000/m68000.h"
10 #include "cpu/z80/z80.h"
11 #include "sound/2612intf.h"
12 #include "sound/sn76496.h"
13 #include "video/315_5313.h"
14 
15 /* Megadrive Console Specific */
16 #include "bus/megadrive/md_slot.h"
17 #include "bus/megadrive/md_carts.h"
18 #include "machine/mega32x.h"
19 #include "machine/megacd.h"
20 
21 #define MASTER_CLOCK_NTSC 53693175
22 #define MASTER_CLOCK_PAL  53203424
23 
24 #define MD_CPU_REGION_SIZE 0x800000
25 
26 
27 /*----------- defined in machine/megadriv.cpp -----------*/
28 
29 INPUT_PORTS_EXTERN( md_common );
30 INPUT_PORTS_EXTERN( megadriv );
31 INPUT_PORTS_EXTERN( megadri6 );
32 INPUT_PORTS_EXTERN( ssf2mdb );
33 INPUT_PORTS_EXTERN( mk3mdb );
34 
35 struct genesis_z80_vars
36 {
37 	int z80_is_reset;
38 	int z80_has_bus;
39 	uint32_t z80_bank_addr;
40 	std::unique_ptr<uint8_t[]> z80_prgram;
41 };
42 
43 
44 class md_base_state : public driver_device
45 {
46 public:
md_base_state(const machine_config & mconfig,device_type type,const char * tag)47 	md_base_state(const machine_config &mconfig, device_type type, const char *tag) :
48 		driver_device(mconfig, type, tag),
49 		m_maincpu(*this,"maincpu"),
50 		m_z80snd(*this,"genesis_snd_z80"),
51 		m_ymsnd(*this,"ymsnd"),
52 		m_scan_timer(*this, "md_scan_timer"),
53 		m_vdp(*this,"gen_vdp"),
54 		m_megadrive_ram(*this,"megadrive_ram"),
55 		m_io_reset(*this, "RESET"),
56 		m_megadrive_io_read_data_port_ptr(*this),
57 		m_megadrive_io_write_data_port_ptr(*this)
58 	{ }
59 
60 	required_device<m68000_base_device> m_maincpu;
61 	optional_device<cpu_device> m_z80snd;
62 	optional_device<ym2612_device> m_ymsnd;
63 	optional_device<timer_device> m_scan_timer;
64 	required_device<sega315_5313_device> m_vdp;
65 	optional_shared_ptr<uint16_t> m_megadrive_ram;
66 
67 	optional_ioport m_io_reset;
68 	ioport_port *m_io_pad_3b[4];
69 	ioport_port *m_io_pad_6b[4];
70 
71 	genesis_z80_vars m_genz80;
72 	int m_version_hi_nibble;
73 
74 	void init_megadriv_c2();
75 	void init_megadrie();
76 	void init_megadriv();
77 	void init_megadrij();
78 
79 	uint8_t megadriv_68k_YM2612_read(offs_t offset, uint8_t mem_mask = ~0);
80 	void megadriv_68k_YM2612_write(offs_t offset, uint8_t data, uint8_t mem_mask = ~0);
81 	IRQ_CALLBACK_MEMBER(genesis_int_callback);
82 	void megadriv_init_common();
83 
84 	void megadriv_z80_bank_w(uint16_t data);
85 	void megadriv_68k_z80_bank_write(uint16_t data);
86 	void megadriv_z80_z80_bank_w(uint8_t data);
87 	uint16_t megadriv_68k_io_read(offs_t offset);
88 	void megadriv_68k_io_write(offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
89 	uint16_t megadriv_68k_read_z80_ram(offs_t offset, uint16_t mem_mask = ~0);
90 	void megadriv_68k_write_z80_ram(offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
91 	uint16_t megadriv_68k_check_z80_bus(offs_t offset, uint16_t mem_mask = ~0);
92 	void megadriv_68k_req_z80_bus(offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
93 	void megadriv_68k_req_z80_reset(offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
94 	uint8_t z80_read_68k_banked_data(offs_t offset);
95 	void z80_write_68k_banked_data(offs_t offset, uint8_t data);
96 	void megadriv_z80_vdp_write(offs_t offset, uint8_t data);
97 	uint8_t megadriv_z80_vdp_read(offs_t offset);
98 	uint8_t megadriv_z80_unmapped_read();
99 	TIMER_CALLBACK_MEMBER(megadriv_z80_run_state);
100 
101 	/* Megadrive / Genesis has 3 I/O ports */
102 	emu_timer *m_io_timeout[3];
103 	int m_io_stage[3];
104 	uint8_t m_megadrive_io_data_regs[3];
105 	uint8_t m_megadrive_io_ctrl_regs[3];
106 	uint8_t m_megadrive_io_tx_regs[3];
107 	read8sm_delegate m_megadrive_io_read_data_port_ptr;
108 	write16sm_delegate m_megadrive_io_write_data_port_ptr;
109 
110 	WRITE_LINE_MEMBER(vdp_sndirqline_callback_genesis_z80);
111 	WRITE_LINE_MEMBER(vdp_lv6irqline_callback_genesis_68k);
112 	WRITE_LINE_MEMBER(vdp_lv4irqline_callback_genesis_68k);
113 
114 	TIMER_CALLBACK_MEMBER( io_timeout_timer_callback );
115 	void megadrive_reset_io();
116 	uint8_t megadrive_io_read_data_port_6button(offs_t offset);
117 	uint8_t megadrive_io_read_data_port_3button(offs_t offset);
118 	uint8_t megadrive_io_read_ctrl_port(int portnum);
119 	uint8_t megadrive_io_read_tx_port(int portnum);
120 	uint8_t megadrive_io_read_rx_port(int portnum);
121 	uint8_t megadrive_io_read_sctrl_port(int portnum);
122 
123 	void megadrive_io_write_data_port_3button(offs_t offset, uint16_t data);
124 	void megadrive_io_write_data_port_6button(offs_t offset, uint16_t data);
125 	void megadrive_io_write_ctrl_port(int portnum, uint16_t data);
126 	void megadrive_io_write_tx_port(int portnum, uint16_t data);
127 	void megadrive_io_write_rx_port(int portnum, uint16_t data);
128 	void megadrive_io_write_sctrl_port(int portnum, uint16_t data);
129 
130 	void megadriv_stop_scanline_timer();
131 
132 	DECLARE_MACHINE_START( megadriv );
133 	DECLARE_MACHINE_RESET( megadriv );
134 	DECLARE_VIDEO_START( megadriv );
135 	uint32_t screen_update_megadriv(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect);
136 	DECLARE_WRITE_LINE_MEMBER(screen_vblank_megadriv);
137 
138 	void megadriv_tas_callback(offs_t offset, uint8_t data);
139 
140 	void megadriv_timers(machine_config &config);
141 	void md_ntsc(machine_config &config);
142 	void md2_ntsc(machine_config &config);
143 	void md_pal(machine_config &config);
144 	void md2_pal(machine_config &config);
145 	void md_bootleg(machine_config &config);
146 	void dcat16_megadriv_base(machine_config &config);
147 	void dcat16_megadriv_map(address_map &map);
148 	void megadriv_map(address_map &map);
149 	void megadriv_z80_io_map(address_map &map);
150 	void megadriv_z80_map(address_map &map);
151 };
152 
153 class md_cons_state : public md_base_state
154 {
155 public:
md_cons_state(const machine_config & mconfig,device_type type,const char * tag)156 	md_cons_state(const machine_config &mconfig, device_type type, const char *tag) :
157 		md_base_state(mconfig, type, tag),
158 		m_32x(*this,"sega32x"),
159 		m_segacd(*this,"segacd"),
160 		m_cart(*this, "mdslot"),
161 		m_tmss(*this, "tmss")
162 	{ }
163 
164 	ioport_port *m_io_ctrlr;
165 	ioport_port *m_io_pad3b[4];
166 	ioport_port *m_io_pad6b[2][4];
167 
168 	optional_device<sega_32x_device> m_32x;
169 	optional_device<sega_segacd_device> m_segacd;
170 	optional_device<md_cart_slot_device> m_cart;
171 	optional_region_ptr<uint16_t> m_tmss;
172 
173 	void init_mess_md_common();
174 	void init_genesis();
175 	void init_md_eur();
176 	void init_md_jpn();
177 
178 	uint8_t mess_md_io_read_data_port(offs_t offset);
179 	void mess_md_io_write_data_port(offs_t offset, uint16_t data);
180 
181 	DECLARE_MACHINE_START( md_common );     // setup ioport_port
182 	DECLARE_MACHINE_START( ms_megadriv );   // setup ioport_port + install cartslot handlers
183 	DECLARE_MACHINE_START( ms_megacd );     // setup ioport_port + dma delay for cd
184 	DECLARE_MACHINE_RESET( ms_megadriv );
185 
186 	DECLARE_WRITE_LINE_MEMBER(screen_vblank_console);
187 
188 	DECLARE_DEVICE_IMAGE_LOAD_MEMBER( _32x_cart );
189 
190 	void _32x_scanline_callback(int x, uint32_t priority, uint32_t &lineptr);
191 	void _32x_interrupt_callback(int scanline, int irq6);
192 	void _32x_scanline_helper_callback(int scanline);
193 
194 	void install_cartslot();
195 	void install_tmss();
196 	uint16_t tmss_r(offs_t offset);
197 	void tmss_swap_w(uint16_t data);
198 	void genesis_32x_scd(machine_config &config);
199 	void mdj_32x_scd(machine_config &config);
200 	void ms_megadpal(machine_config &config);
201 	void dcat16_megadriv_base(machine_config &config);
202 	void dcat16_megadriv(machine_config &config);
203 	void md_32x_scd(machine_config &config);
204 	void mdj_32x(machine_config &config);
205 	void ms_megadriv(machine_config &config);
206 	void ms_megadriv2(machine_config &config);
207 	void mdj_scd(machine_config &config);
208 	void md2j_scd(machine_config &config);
209 	void md_32x(machine_config &config);
210 	void genesis_32x(machine_config &config);
211 	void md_scd(machine_config &config);
212 	void md2_scd(machine_config &config);
213 	void genesis_scd(machine_config &config);
214 	void genesis2_scd(machine_config &config);
215 	void genesis_tmss(machine_config &config);
216 };
217 
218 #endif // MAME_INCLUDES_MEGADRIV_H
219