1 // FB Alpha Kick Boy / Dacholer / Itazura Tenshi driver module
2 // Based on MAME driver by Pierpaolo Prazzoli
3 
4 #include "tiles_generic.h"
5 #include "z80_intf.h"
6 #include "msm5205.h"
7 #include "ay8910.h"
8 
9 static UINT8 *AllMem;
10 static UINT8 *MemEnd;
11 static UINT8 *AllRam;
12 static UINT8 *RamEnd;
13 
14 static UINT8 *DrvZ80ROM0;
15 static UINT8 *DrvZ80ROM1;
16 static UINT8 *DrvGfxROM0;
17 static UINT8 *DrvGfxROM1;
18 static UINT8 *DrvGfxROM2;
19 static UINT8 *DrvColPROM;
20 static UINT8 *DrvZ80RAM0;
21 static UINT8 *DrvZ80RAM1;
22 static UINT8 *DrvBgRAM;
23 static UINT8 *DrvFgRAM;
24 static UINT8 *DrvSprRAM;
25 
26 static UINT32 *DrvPalette;
27 static UINT8 DrvRecalc;
28 
29 static UINT8 bgbank;
30 static UINT8 flipscreen;
31 static UINT8 soundlatch;
32 static UINT8 scrollx;
33 static UINT8 scrolly;
34 static UINT8 music_interrupt_enable;
35 static UINT8 sound_interrupt_enable;
36 static UINT8 msm_toggle;
37 static UINT8 msm_data;
38 static UINT8 sound_ack;
39 
40 static UINT8 DrvJoy1[8];
41 static UINT8 DrvJoy2[8];
42 static UINT8 DrvJoy3[8];
43 static UINT8 DrvDips[2];
44 static UINT8 DrvInputs[3];
45 static UINT8 DrvReset;
46 
47 static INT32 itaten = 0;
48 static INT32 dacholer = 0;
49 
50 static struct BurnInputInfo DacholerInputList[] = {
51 	{"P1 Coin",			BIT_DIGITAL,	DrvJoy3 + 4,	"p1 coin"	},
52 	{"P1 Start",		BIT_DIGITAL,	DrvJoy3 + 0,	"p1 start"	},
53 	{"P1 Up",			BIT_DIGITAL,	DrvJoy1 + 0,	"p1 up"		},
54 	{"P1 Down",			BIT_DIGITAL,	DrvJoy1 + 1,	"p1 down"	},
55 	{"P1 Left",			BIT_DIGITAL,	DrvJoy1 + 2,	"p1 left"	},
56 	{"P1 Right",		BIT_DIGITAL,	DrvJoy1 + 3,	"p1 right"	},
57 	{"P1 Button 1",		BIT_DIGITAL,	DrvJoy1 + 4,	"p1 fire 1"	},
58 	{"P1 Button 2",		BIT_DIGITAL,	DrvJoy1 + 5,	"p1 fire 2"	},
59 
60 	{"P2 Coin",			BIT_DIGITAL,	DrvJoy3 + 5,	"p2 coin"	},
61 	{"P2 Start",		BIT_DIGITAL,	DrvJoy3 + 1,	"p2 start"	},
62 	{"P2 Up",			BIT_DIGITAL,	DrvJoy2 + 0,	"p2 up"		},
63 	{"P2 Down",			BIT_DIGITAL,	DrvJoy2 + 1,	"p2 down"	},
64 	{"P2 Left",			BIT_DIGITAL,	DrvJoy2 + 2,	"p2 left"	},
65 	{"P2 Right",		BIT_DIGITAL,	DrvJoy2 + 3,	"p2 right"	},
66 	{"P2 Button 1",		BIT_DIGITAL,	DrvJoy2 + 4,	"p2 fire 1"	},
67 	{"P2 Button 2",		BIT_DIGITAL,	DrvJoy2 + 5,	"p2 fire 2"	},
68 
69 	{"Reset",			BIT_DIGITAL,	&DrvReset,		"reset"		},
70 	{"Service",			BIT_DIGITAL,	DrvJoy3 + 2,	"service"	},
71 	{"Dip A",			BIT_DIPSWITCH,	DrvDips + 0,	"dip"		},
72 	{"Dip B",			BIT_DIPSWITCH,	DrvDips + 1,	"dip"		},
73 };
74 
75 STDINPUTINFO(Dacholer)
76 
77 static struct BurnInputInfo ItatenInputList[] = {
78 	{"P1 Coin",			BIT_DIGITAL,	DrvJoy3 + 4,	"p1 coin"	},
79 	{"P1 Start",		BIT_DIGITAL,	DrvJoy3 + 0,	"p1 start"	},
80 	{"P1 Up",			BIT_DIGITAL,	DrvJoy1 + 0,	"p1 up"		},
81 	{"P1 Down",			BIT_DIGITAL,	DrvJoy1 + 1,	"p1 down"	},
82 	{"P1 Left",			BIT_DIGITAL,	DrvJoy1 + 2,	"p1 left"	},
83 	{"P1 Right",		BIT_DIGITAL,	DrvJoy1 + 3,	"p1 right"	},
84 	{"P1 Button 1",		BIT_DIGITAL,	DrvJoy1 + 4,	"p1 fire 1"	},
85 
86 	{"P2 Coin",			BIT_DIGITAL,	DrvJoy3 + 5,	"p2 coin"	},
87 	{"P2 Start",		BIT_DIGITAL,	DrvJoy3 + 1,	"p2 start"	},
88 	{"P2 Up",			BIT_DIGITAL,	DrvJoy2 + 0,	"p2 up"		},
89 	{"P2 Down",			BIT_DIGITAL,	DrvJoy2 + 1,	"p2 down"	},
90 	{"P2 Left",			BIT_DIGITAL,	DrvJoy2 + 2,	"p2 left"	},
91 	{"P2 Right",		BIT_DIGITAL,	DrvJoy2 + 3,	"p2 right"	},
92 	{"P2 Button 1",		BIT_DIGITAL,	DrvJoy2 + 4,	"p2 fire 1"	},
93 
94 	{"Reset",			BIT_DIGITAL,	&DrvReset,		"reset"		},
95 	{"Service",			BIT_DIGITAL,	DrvJoy3 + 2,	"service"	},
96 	{"Dip A",			BIT_DIPSWITCH,	DrvDips + 0,	"dip"		},
97 	{"Dip B",			BIT_DIPSWITCH,	DrvDips + 1,	"dip"		},
98 };
99 
100 STDINPUTINFO(Itaten)
101 
102 static struct BurnDIPInfo DacholerDIPList[]=
103 {
104 	{0x12, 0xff, 0xff, 0x0f, NULL				},
105 	{0x13, 0xff, 0xff, 0x3d, NULL				},
106 
107 	{0   , 0xfe, 0   ,    4, "Coin A"			},
108 	{0x12, 0x01, 0x03, 0x01, "2 Coins 1 Credits"		},
109 	{0x12, 0x01, 0x03, 0x03, "1 Coin  1 Credits"		},
110 	{0x12, 0x01, 0x03, 0x00, "2 Coins 3 Credits"		},
111 	{0x12, 0x01, 0x03, 0x02, "1 Coin  2 Credits"		},
112 
113 	{0   , 0xfe, 0   ,    4, "Coin B"			},
114 	{0x12, 0x01, 0x0c, 0x00, "6 Coins 1 Credits"		},
115 	{0x12, 0x01, 0x0c, 0x04, "5 Coins 1 Credits"		},
116 	{0x12, 0x01, 0x0c, 0x08, "4 Coins 1 Credits"		},
117 	{0x12, 0x01, 0x0c, 0x0c, "1 Coin  1 Credits"		},
118 
119 	{0   , 0xfe, 0   ,    4, "Lives"			},
120 	{0x13, 0x01, 0x03, 0x03, "1"				},
121 	{0x13, 0x01, 0x03, 0x02, "2"				},
122 	{0x13, 0x01, 0x03, 0x01, "3"				},
123 	{0x13, 0x01, 0x03, 0x00, "4"				},
124 
125 	{0   , 0xfe, 0   ,    13, "Bonus Life"			},
126 	{0x13, 0x01, 0x3c, 0x3c, "20k 70k then every 50k"	},
127 	{0x13, 0x01, 0x3c, 0x38, "30k 80k then every 50k"	},
128 	{0x13, 0x01, 0x3c, 0x34, "40k 90k then every 50k"	},
129 	{0x13, 0x01, 0x3c, 0x2c, "20k 90k then every 70k"	},
130 	{0x13, 0x01, 0x3c, 0x28, "30k 100k then every 70k"	},
131 	{0x13, 0x01, 0x3c, 0x24, "40k 110k then every 70k"	},
132 	{0x13, 0x01, 0x3c, 0x1c, "20k 120k then every 100k"	},
133 	{0x13, 0x01, 0x3c, 0x18, "30k 130k then every 100k"	},
134 	{0x13, 0x01, 0x3c, 0x14, "40k 140k then every 100k"	},
135 	{0x13, 0x01, 0x3c, 0x0c, "20k only"			},
136 	{0x13, 0x01, 0x3c, 0x08, "30k only"			},
137 	{0x13, 0x01, 0x3c, 0x04, "40k only"			},
138 	{0x13, 0x01, 0x3c, 0x00, "None"				},
139 
140 	{0   , 0xfe, 0   ,    2, "Demo Sounds"			},
141 	{0x13, 0x01, 0x40, 0x40, "Off"				},
142 	{0x13, 0x01, 0x40, 0x00, "On"				},
143 
144 	{0   , 0xfe, 0   ,    2, "Cabinet"			},
145 	{0x13, 0x01, 0x80, 0x00, "Upright"			},
146 	{0x13, 0x01, 0x80, 0x80, "Cocktail"			},
147 };
148 
149 STDDIPINFO(Dacholer)
150 
151 static struct BurnDIPInfo KickboyDIPList[]=
152 {
153 	{0x12, 0xff, 0xff, 0x0f, NULL				},
154 	{0x13, 0xff, 0xff, 0x7d, NULL				},
155 
156 	{0   , 0xfe, 0   ,    4, "Coin A"			},
157 	{0x12, 0x01, 0x03, 0x01, "2 Coins 1 Credits"		},
158 	{0x12, 0x01, 0x03, 0x03, "1 Coin  1 Credits"		},
159 	{0x12, 0x01, 0x03, 0x00, "2 Coins 3 Credits"		},
160 	{0x12, 0x01, 0x03, 0x02, "1 Coin  2 Credits"		},
161 
162 	{0   , 0xfe, 0   ,    4, "Coin B"			},
163 	{0x12, 0x01, 0x0c, 0x04, "2 Coins 1 Credits"		},
164 	{0x12, 0x01, 0x0c, 0x0c, "1 Coin  1 Credits"		},
165 	{0x12, 0x01, 0x0c, 0x08, "1 Coin  2 Credits"		},
166 	{0x12, 0x01, 0x0c, 0x00, "Free Play"			},
167 
168 	{0   , 0xfe, 0   ,    4, "Lives"			},
169 	{0x13, 0x01, 0x03, 0x03, "3"				},
170 	{0x13, 0x01, 0x03, 0x02, "4"				},
171 	{0x13, 0x01, 0x03, 0x01, "5"				},
172 	{0x13, 0x01, 0x03, 0x00, "99 (Cheat)"			},
173 
174 	{0   , 0xfe, 0   ,    13, "Bonus Life"			},
175 	{0x13, 0x01, 0x3c, 0x3c, "20k 50k then every 30k"	},
176 	{0x13, 0x01, 0x3c, 0x38, "30k 60k then every 30k"	},
177 	{0x13, 0x01, 0x3c, 0x34, "40k 70k then every 30k"	},
178 	{0x13, 0x01, 0x3c, 0x2c, "20k 70k then every 50k"	},
179 	{0x13, 0x01, 0x3c, 0x28, "30k 80k then every 50k"	},
180 	{0x13, 0x01, 0x3c, 0x24, "40k 90k then every 50k"	},
181 	{0x13, 0x01, 0x3c, 0x1c, "20k 90k then every 70k"	},
182 	{0x13, 0x01, 0x3c, 0x18, "30k 100k then every 70k"	},
183 	{0x13, 0x01, 0x3c, 0x14, "40k 110k then every 70k"	},
184 	{0x13, 0x01, 0x3c, 0x0c, "20k only"			},
185 	{0x13, 0x01, 0x3c, 0x08, "30k only"			},
186 	{0x13, 0x01, 0x3c, 0x04, "40k only"			},
187 	{0x13, 0x01, 0x3c, 0x00, "None"				},
188 
189 	{0   , 0xfe, 0   ,    2, "Difficulty"			},
190 	{0x13, 0x01, 0x40, 0x40, "Easy"				},
191 	{0x13, 0x01, 0x40, 0x00, "Hard"				},
192 
193 	{0   , 0xfe, 0   ,    2, "Cabinet"			},
194 	{0x13, 0x01, 0x80, 0x00, "Upright"			},
195 	{0x13, 0x01, 0x80, 0x80, "Cocktail"			},
196 };
197 
198 STDDIPINFO(Kickboy)
199 
200 static struct BurnDIPInfo ItatenDIPList[]=
201 {
202 	{0x10, 0xff, 0xff, 0xff, NULL				},
203 	{0x11, 0xff, 0xff, 0x3f, NULL				},
204 
205 	{0   , 0xfe, 0   ,    4, "Coin A"			},
206 	{0x10, 0x01, 0x03, 0x01, "2 Coins 1 Credits"		},
207 	{0x10, 0x01, 0x03, 0x03, "1 Coin  1 Credits"		},
208 	{0x10, 0x01, 0x03, 0x02, "1 Coin  2 Credits"		},
209 	{0x10, 0x01, 0x03, 0x00, "Free Play"			},
210 
211 	{0   , 0xfe, 0   ,    4, "Coin B"			},
212 	{0x10, 0x01, 0x0c, 0x00, "3 Coins 1 Credits"		},
213 	{0x10, 0x01, 0x0c, 0x04, "2 Coins 3 Credits"		},
214 	{0x10, 0x01, 0x0c, 0x0c, "1 Coin  3 Credits"		},
215 	{0x10, 0x01, 0x0c, 0x08, "1 Coin  6 Credits"		},
216 
217 	{0   , 0xfe, 0   ,    0, "Difficulty"			},
218 	{0x11, 0x01, 0x03, 0x03, "Easy"				},
219 	{0x11, 0x01, 0x03, 0x02, "Medium"			},
220 	{0x11, 0x01, 0x03, 0x01, "Hard"				},
221 	{0x11, 0x01, 0x03, 0x00, "Hardest"			},
222 
223 	{0   , 0xfe, 0   ,    4, "Lives"			},
224 	{0x11, 0x01, 0x0c, 0x0c, "3"				},
225 	{0x11, 0x01, 0x0c, 0x08, "4"				},
226 	{0x11, 0x01, 0x0c, 0x04, "5"				},
227 	{0x11, 0x01, 0x0c, 0x00, "6"				},
228 
229 	{0   , 0xfe, 0   ,    4, "Bonus Life"			},
230 	{0x11, 0x01, 0x30, 0x30, "30k then every 50k"		},
231 	{0x11, 0x01, 0x30, 0x20, "60k then every 50k"		},
232 	{0x11, 0x01, 0x30, 0x10, "30k then every 90k"		},
233 	{0x11, 0x01, 0x30, 0x00, "60k then every 90k"		},
234 
235 	{0   , 0xfe, 0   ,    4, "Demo Sounds"			},
236 	{0x11, 0x01, 0x40, 0x40, "Off"				},
237 	{0x11, 0x01, 0x40, 0x00, "On"				},
238 
239 	{0   , 0xfe, 0   ,    2, "Cabinet"			},
240 	{0x11, 0x01, 0x80, 0x00, "Upright"			},
241 	{0x11, 0x01, 0x80, 0x80, "Cocktail"			},
242 };
243 
STDDIPINFO(Itaten)244 STDDIPINFO(Itaten)
245 
246 static void __fastcall dacholer_main_write_port(UINT16 port, UINT8 data)
247 {
248 	switch (port & 0xff)
249 	{
250 		case 0x20:
251 			// coins & leds
252 		return;
253 
254 		case 0x21:
255 			bgbank = data & 3;
256 			flipscreen = data & 0x0c;
257 		return;
258 
259 		case 0x22:
260 			scrollx = data;
261 		return;
262 
263 		case 0x23:
264 			scrolly = data + 16;
265 		return;
266 
267 		case 0x24:
268 			ZetSetIRQLine(0, CPU_IRQSTATUS_NONE);
269 		return;
270 
271 		case 0x27:
272 		{
273 			soundlatch = data;
274 			ZetNmi(1);
275 		}
276 		return;
277 	}
278 }
279 
dacholer_main_read_port(UINT16 port)280 static UINT8 __fastcall dacholer_main_read_port(UINT16 port)
281 {
282 	switch (port & 0xff)
283 	{
284 		case 0x00:
285 		case 0x01:
286 		case 0x02:
287 			return DrvInputs[port & 3];
288 
289 		case 0x03:
290 			return (DrvDips[0] & 0xef) | (sound_ack ? 0x10 : 0); // correct???
291 
292 		case 0x04:
293 			return DrvDips[1];
294 
295 		case 0x05:
296 			return 0; // nop
297 	}
298 
299 	return 0;
300 }
301 
dacholer_sound_write_port(UINT16 port,UINT8 data)302 static void __fastcall dacholer_sound_write_port(UINT16 port, UINT8 data)
303 {
304 	switch (port & 0xff)
305 	{
306 		case 0x00:
307 			soundlatch = 0;
308 		return;
309 
310 		case 0x04:
311 			music_interrupt_enable = data;
312 		return;
313 
314 		case 0x08:
315 			sound_interrupt_enable = data;
316 			if (data) MSM5205ResetWrite(0, 0);
317 		return;
318 
319 		case 0x0c:
320 			sound_ack = data;
321 		return;
322 
323 		case 0x80:
324 			msm_data = data;
325 			msm_toggle = 0;
326 		return;
327 
328 		case 0x86:
329 		case 0x87:
330 			AY8910Write(0, ~port & 1, data);
331 		return;
332 
333 		case 0x8a:
334 		case 0x8b:
335 			AY8910Write(1, ~port & 1, data);
336 		return;
337 
338 		case 0x8e:
339 		case 0x8f:
340 			AY8910Write(2, ~port & 1, data);
341 		return;
342 	}
343 }
344 
dacholer_sound_read_port(UINT16 port)345 static UINT8 __fastcall dacholer_sound_read_port(UINT16 port)
346 {
347 	switch (port & 0xff)
348 	{
349 		case 0x00:
350 			return soundlatch;
351 	}
352 
353 	return 0;
354 }
355 
adpcm_int()356 static void adpcm_int()
357 {
358 	if (sound_interrupt_enable == 1 || (sound_interrupt_enable == 0 && msm_toggle == 1))
359 	{
360 		MSM5205DataWrite(0, msm_data >> 4);
361 
362 		msm_data <<= 4;
363 		msm_toggle ^= 1;
364 
365 		if (msm_toggle == 0)
366 		{
367 			ZetSetVector(0x38);
368 			ZetSetIRQLine(0, CPU_IRQSTATUS_HOLD);
369 		}
370 	} else {
371 		MSM5205ResetWrite(0, 1);
372 	}
373 }
374 
DrvSynchroniseStream(INT32 nSoundRate)375 static INT32 DrvSynchroniseStream(INT32 nSoundRate)
376 {
377 	if (ZetGetActive() == -1) return 0;
378 
379 	return (INT64)(double)ZetTotalCycles() * nSoundRate / 2496000;
380 }
381 
DrvDoReset()382 static INT32 DrvDoReset()
383 {
384 	memset (AllRam, 0, RamEnd - AllRam);
385 
386 	ZetOpen(0);
387 	ZetReset();
388 	ZetClose();
389 
390 	ZetOpen(1);
391 	ZetReset();
392 	AY8910Reset(0);
393 	AY8910Reset(1);
394 	AY8910Reset(2);
395 	MSM5205Reset();
396 	ZetClose();
397 
398 	bgbank = 0;
399 	flipscreen = 0;
400 	scrollx = 0;
401 	scrolly = 0;
402 	soundlatch = 0;
403 	music_interrupt_enable = 0;
404 	sound_interrupt_enable = 0;
405 	msm_toggle = 0;
406 	msm_data = 0;
407 	sound_ack = 0;
408 	MSM5205ResetWrite(0, 1);
409 
410 	return 0;
411 }
412 
MemIndex()413 static INT32 MemIndex()
414 {
415 	UINT8 *Next; Next = AllMem;
416 
417 	DrvZ80ROM0		= Next; Next += 0x00a000;
418 	DrvZ80ROM1		= Next; Next += 0x006000;
419 
420 	DrvGfxROM0		= Next; Next += 0x004000;
421 	DrvGfxROM1		= Next; Next += 0x010000;
422 	DrvGfxROM2		= Next; Next += 0x010000;
423 
424 	DrvColPROM		= Next; Next += 0x000020;
425 
426 	DrvPalette		= (UINT32*)Next; Next += 0x0020 * sizeof(UINT32);
427 
428 	AllRam			= Next;
429 
430 	DrvSprRAM		= Next; Next += 0x000100;
431 	DrvFgRAM		= Next; Next += 0x000400;
432 	DrvZ80RAM0		= Next; Next += 0x001800;
433 	DrvZ80RAM1		= Next; Next += 0x001800;
434 	DrvBgRAM		= Next; Next += 0x000400;
435 
436 	RamEnd			= Next;
437 
438 	MemEnd			= Next;
439 
440 	return 0;
441 }
442 
DrvGfxDecode()443 static INT32 DrvGfxDecode()
444 {
445 	INT32 Plane[4]  = { STEP4(0,1) };
446 	INT32 XOffs[16] = { 4,0,12,8,20,16,28,24,36,32,44,40,52,48,60,56 };
447 	INT32 YOffs0[8] = { STEP8(0,32) };
448 	INT32 YOffs1[16]= { STEP16(0,64) };
449 
450 	UINT8 *tmp = (UINT8*)BurnMalloc(0x8000);
451 	if (tmp == NULL) {
452 		return 1;
453 	}
454 
455 	memcpy (tmp, DrvGfxROM0, 0x2000);
456 
457 	GfxDecode(0x0100, 4,  8,  8, Plane, XOffs, YOffs0, 0x100, tmp, DrvGfxROM0);
458 
459 	memcpy (tmp, DrvGfxROM1, 0x8000);
460 
461 	GfxDecode(0x0400, 4,  8,  8, Plane, XOffs, YOffs0, 0x100, tmp, DrvGfxROM1);
462 
463 	memcpy (tmp, DrvGfxROM2, 0x8000);
464 
465 	GfxDecode(0x0100, 4, 16, 16, Plane, XOffs, YOffs1, 0x400, tmp, DrvGfxROM2);
466 
467 	BurnFree(tmp);
468 
469 	return 0;
470 }
471 
DrvInit(INT32 type)472 static INT32 DrvInit(INT32 type)
473 {
474 	BurnAllocMemIndex();
475 
476 	if (type == 0)
477 	{
478 		if (BurnLoadRom(DrvZ80ROM0 + 0x00000,  0, 1)) return 1;
479 		if (BurnLoadRom(DrvZ80ROM0 + 0x02000,  1, 1)) return 1;
480 		if (BurnLoadRom(DrvZ80ROM0 + 0x04000,  2, 1)) return 1;
481 		if (BurnLoadRom(DrvZ80ROM0 + 0x06000,  3, 1)) return 1;
482 
483 		if (BurnLoadRom(DrvZ80ROM1 + 0x00000,  4, 1)) return 1;
484 		if (BurnLoadRom(DrvZ80ROM1 + 0x02000,  5, 1)) return 1;
485 		if (BurnLoadRom(DrvZ80ROM1 + 0x04000,  6, 1)) return 1;
486 
487 		if (BurnLoadRom(DrvGfxROM0 + 0x00000,  7, 1)) return 1;
488 
489 		if (BurnLoadRom(DrvGfxROM1 + 0x00000,  8, 1)) return 1;
490 		if (BurnLoadRom(DrvGfxROM1 + 0x02000,  9, 1)) return 1;
491 		if (BurnLoadRom(DrvGfxROM1 + 0x04000, 10, 1)) return 1;
492 
493 		if (BurnLoadRom(DrvGfxROM2 + 0x00000, 11, 1)) return 1;
494 		if (BurnLoadRom(DrvGfxROM2 + 0x02000, 12, 1)) return 1;
495 		if (BurnLoadRom(DrvGfxROM2 + 0x04000, 13, 1)) return 1;
496 
497 		if (BurnLoadRom(DrvColPROM + 0x00000, 14, 1)) return 1;
498 	//	if (BurnLoadRom(DrvColPROM + 0x00020, 15, 1)) return 1;
499 	//	if (BurnLoadRom(DrvColPROM + 0x00040, 16, 1)) return 1;
500 
501 		dacholer = 1;
502 	}
503 	else if (type == 1)
504 	{
505 		if (BurnLoadRom(DrvZ80ROM0 + 0x00000,  0, 1)) return 1;
506 		if (BurnLoadRom(DrvZ80ROM0 + 0x02000,  1, 1)) return 1;
507 		if (BurnLoadRom(DrvZ80ROM0 + 0x04000,  2, 1)) return 1;
508 		if (BurnLoadRom(DrvZ80ROM0 + 0x06000,  3, 1)) return 1;
509 
510 		if (BurnLoadRom(DrvZ80ROM1 + 0x00000,  4, 1)) return 1;
511 		if (BurnLoadRom(DrvZ80ROM1 + 0x02000,  5, 1)) return 1;
512 		if (BurnLoadRom(DrvZ80ROM1 + 0x04000,  6, 1)) return 1;
513 
514 		if (BurnLoadRom(DrvGfxROM0 + 0x00000,  7, 1)) return 1;
515 
516 		if (BurnLoadRom(DrvGfxROM1 + 0x00000,  8, 1)) return 1;
517 		if (BurnLoadRom(DrvGfxROM1 + 0x02000,  9, 1)) return 1;
518 
519 		if (BurnLoadRom(DrvGfxROM2 + 0x00000, 10, 1)) return 1;
520 		if (BurnLoadRom(DrvGfxROM2 + 0x02000, 11, 1)) return 1;
521 		if (BurnLoadRom(DrvGfxROM2 + 0x04000, 12, 1)) return 1;
522 
523 		if (BurnLoadRom(DrvColPROM + 0x00000, 13, 1)) return 1;
524 	//	if (BurnLoadRom(DrvColPROM + 0x00020, 14, 1)) return 1;
525 	//	if (BurnLoadRom(DrvColPROM + 0x00040, 15, 1)) return 1;
526 
527 		dacholer = 1; // kickboy (dacholer clone)
528 	}
529 	else if (type == 2)
530 	{
531 		if (BurnLoadRom(DrvZ80ROM0 + 0x00000,  0, 1)) return 1;
532 		if (BurnLoadRom(DrvZ80ROM0 + 0x02000,  1, 1)) return 1;
533 		if (BurnLoadRom(DrvZ80ROM0 + 0x04000,  2, 1)) return 1;
534 		if (BurnLoadRom(DrvZ80ROM0 + 0x06000,  3, 1)) return 1;
535 		if (BurnLoadRom(DrvZ80ROM0 + 0x08000,  4, 1)) return 1;
536 
537 		if (BurnLoadRom(DrvZ80ROM1 + 0x00000,  5, 1)) return 1;
538 		if (BurnLoadRom(DrvZ80ROM1 + 0x02000,  6, 1)) return 1;
539 
540 		if (BurnLoadRom(DrvGfxROM0 + 0x00000,  7, 1)) return 1;
541 
542 		if (BurnLoadRom(DrvGfxROM1 + 0x00000,  8, 1)) return 1;
543 		if (BurnLoadRom(DrvGfxROM1 + 0x02000,  9, 1)) return 1;
544 		if (BurnLoadRom(DrvGfxROM1 + 0x04000, 10, 1)) return 1;
545 		if (BurnLoadRom(DrvGfxROM1 + 0x06000, 11, 1)) return 1;
546 
547 		if (BurnLoadRom(DrvGfxROM2 + 0x00000, 12, 1)) return 1;
548 		if (BurnLoadRom(DrvGfxROM2 + 0x02000, 13, 1)) return 1;
549 		if (BurnLoadRom(DrvGfxROM2 + 0x04000, 14, 1)) return 1;
550 		if (BurnLoadRom(DrvGfxROM2 + 0x06000, 15, 1)) return 1;
551 
552 		if (BurnLoadRom(DrvColPROM + 0x00000, 16, 1)) return 1;
553 	//	if (BurnLoadRom(DrvColPROM + 0x00020, 17, 1)) return 1;
554 	//	if (BurnLoadRom(DrvColPROM + 0x00040, 18, 1)) return 1;
555 
556 		itaten = 1;
557 	}
558 
559 	DrvGfxDecode();
560 
561 	ZetInit(0);
562 	ZetOpen(0);
563 	ZetMapMemory(DrvZ80ROM0,	0x0000, 0x7fff, MAP_ROM);
564 	ZetMapMemory(DrvBgRAM,		0xc000, 0xc3ff, MAP_RAM);
565 	ZetMapMemory(DrvBgRAM,		0xc400, 0xc7ff, MAP_RAM);
566 	ZetMapMemory(DrvFgRAM,		0xd000, 0xd3ff, MAP_RAM);
567 	ZetMapMemory(DrvSprRAM,		0xe000, 0xe0ff, MAP_RAM);
568 
569 	if (itaten)
570 	{
571 		ZetMapMemory(DrvZ80ROM0 + 0x8000, 0x8000, 0x9fff, MAP_ROM);
572 		ZetMapMemory(DrvZ80RAM0,	  0xa000, 0xb7ff, MAP_RAM);
573 	}
574 	else
575 	{
576 		ZetMapMemory(DrvZ80RAM0,	  0x8800, 0x97ff, MAP_RAM);
577 	}
578 
579 	ZetSetOutHandler(dacholer_main_write_port);
580 	ZetSetInHandler(dacholer_main_read_port);
581 	ZetClose();
582 
583 	ZetInit(1);
584 	ZetOpen(1);
585 	ZetMapMemory(DrvZ80ROM1,	0x0000, 0x5fff, MAP_ROM);
586 	ZetMapMemory(DrvZ80RAM1,	0xd000, 0xe7ff, MAP_RAM);
587 	ZetSetOutHandler(dacholer_sound_write_port);
588 	ZetSetInHandler(dacholer_sound_read_port);
589 	ZetClose();
590 
591 	AY8910Init(0, 1248000, 0);
592 	AY8910Init(1, 1248000, 1);
593 	AY8910Init(2, 1248000, 1);
594 	AY8910SetAllRoutes(0, 0.10, BURN_SND_ROUTE_BOTH);
595 	AY8910SetAllRoutes(1, 0.10, BURN_SND_ROUTE_BOTH);
596 	AY8910SetAllRoutes(2, 0.10, BURN_SND_ROUTE_BOTH);
597 	AY8910SetBuffered(ZetTotalCycles, 2496000);
598 
599 	MSM5205Init(0, DrvSynchroniseStream, 384000, adpcm_int, MSM5205_S96_4B, 1);
600 	MSM5205SetRoute(0, 0.30, BURN_SND_ROUTE_BOTH);
601 
602 	GenericTilesInit();
603 
604 	DrvDoReset();
605 
606 	return 0;
607 }
608 
DrvExit()609 static INT32 DrvExit()
610 {
611 	GenericTilesExit();
612 
613 	ZetExit();
614 	AY8910Exit(0);
615 	AY8910Exit(1);
616 	AY8910Exit(2);
617 	MSM5205Exit();
618 
619 	BurnFreeMemIndex();
620 
621 	itaten = 0;
622 	dacholer = 0;
623 
624 	return 0;
625 }
626 
DrvPaletteInit()627 static void DrvPaletteInit()
628 {
629 	for (INT32 i = 0;i < 0x20; i++)
630 	{
631 		INT32 bit0 = (DrvColPROM[i] >> 0) & 0x01;
632 		INT32 bit1 = (DrvColPROM[i] >> 1) & 0x01;
633 		INT32 bit2 = (DrvColPROM[i] >> 2) & 0x01;
634 		INT32 r = bit0 * 33 + bit1 * 71 + bit2 * 151; //bit0 * 151 + bit1 * 71 + bit2 * 33;
635 
636 		bit0 = (DrvColPROM[i] >> 3) & 0x01;
637 		bit1 = (DrvColPROM[i] >> 4) & 0x01;
638 		bit2 = (DrvColPROM[i] >> 5) & 0x01;
639 		INT32 g = bit0 * 33 + bit1 * 71 + bit2 * 151; //bit0 * 151 + bit1 * 71 + bit2 * 33;
640 
641 
642 		bit0 = (DrvColPROM[i] >> 6) & 0x01;
643 		bit1 = (DrvColPROM[i] >> 7) & 0x01;
644 		INT32 b = bit0 * 81 + bit1 * 174; //bit0 * 174 + bit1 * 81;
645 
646 		DrvPalette[i] = BurnHighCol(r,g,b,0);
647 	}
648 }
649 
draw_bg_layer()650 static void draw_bg_layer()
651 {
652 	INT32 color = (itaten) ? 0 : 0x10;
653 
654 	for (INT32 offs = 0; offs < 32 * 32; offs++)
655 	{
656 		INT32 sx = (offs & 0x1f) * 8;
657 		INT32 sy = (offs / 0x20) * 8;
658 
659 		sx -= scrollx;
660 		if (sx < -7) sx += 256;
661 		sy -= scrolly;
662 		if (sy < -7) sy += 256;
663 
664 		INT32 code = DrvBgRAM[offs] + (bgbank * 0x100);
665 
666 		Render8x8Tile_Clip(pTransDraw, code, sx, sy, color, 0, 0, DrvGfxROM1);
667 	}
668 }
669 
draw_fg_layer()670 static void draw_fg_layer()
671 {
672 	for (INT32 offs = (32 * 2); offs < (32 * 32) - (32 * 2); offs++)
673 	{
674 		INT32 sx = (offs & 0x1f) * 8;
675 		INT32 sy = (offs / 0x20) * 8;
676 
677 		INT32 code = DrvFgRAM[offs];
678 
679 		Render8x8Tile_Mask(pTransDraw, code, sx, sy - 16, 0, 0, 0, 0, DrvGfxROM0);
680 	}
681 }
682 
draw_sprites()683 static void draw_sprites()
684 {
685 	for (INT32 offs = 0; offs < 0x100; offs += 4)
686 	{
687 		INT32 code  = DrvSprRAM[offs + 1];
688 		INT32 attr  = DrvSprRAM[offs + 2];
689 
690 		INT32 flipx = attr & 0x10;
691 		INT32 flipy = attr & 0x20;
692 
693 		INT32 sx = (DrvSprRAM[offs + 3] - 128) + 256 * (attr & 0x01);
694 		INT32 sy = 255 - DrvSprRAM[offs];
695 
696 		if (flipscreen)
697 		{
698 			sx = 240 - sx;
699 			sy = 240 - sy;
700 			flipx = !flipx;
701 			flipy = !flipy;
702 		}
703 
704 		Draw16x16MaskTile(pTransDraw, code, sx, sy - 16, flipx, flipy, 0, 4, 0, 0x10, DrvGfxROM2);
705 	}
706 }
707 
DrvDraw()708 static INT32 DrvDraw()
709 {
710 	if (DrvRecalc) {
711 		DrvPaletteInit();
712 		DrvRecalc = 0;
713 	}
714 
715 	if ((nBurnLayer & 1) == 0) BurnTransferClear();
716 	if ((nBurnLayer & 1) == 1) draw_bg_layer();
717 	if ((nBurnLayer & 2) == 2) draw_sprites();
718 	if ((nBurnLayer & 4) == 4) draw_fg_layer();
719 
720 	BurnTransferCopy(DrvPalette);
721 
722 	return 0;
723 }
724 
DrvFrame()725 static INT32 DrvFrame()
726 {
727 	if (DrvReset) {
728 		DrvDoReset();
729 	}
730 
731 	ZetNewFrame();
732 
733 	{
734 		UINT8 *DrvJoy[3] = { DrvJoy1, DrvJoy2, DrvJoy3 };
735 		UINT32 DrvJoyInit[3] = { 0x00, 0x00, 0xff };
736 
737 		CompileInput(DrvJoy, (void*)DrvInputs, 3, 8, DrvJoyInit);
738 
739 		if (dacholer) {
740 			// Convert to 4-way for Dacholer
741 			ProcessJoystick(&DrvInputs[0], 0, 0,1,2,3, INPUT_4WAY | INPUT_MAKEACTIVELOW | INPUT_CLEAROPPOSITES);
742 			ProcessJoystick(&DrvInputs[1], 1, 0,1,2,3, INPUT_4WAY | INPUT_MAKEACTIVELOW | INPUT_CLEAROPPOSITES);
743 		} else {
744 			ProcessJoystick(&DrvInputs[0], 0, 0,1,2,3, INPUT_MAKEACTIVELOW | INPUT_CLEAROPPOSITES);
745 			ProcessJoystick(&DrvInputs[1], 1, 0,1,2,3, INPUT_MAKEACTIVELOW | INPUT_CLEAROPPOSITES);
746 		}
747 	}
748 
749 	INT32 nInterleave = 256;
750 	INT32 nCyclesTotal[2] = { 4000000 / 60, 2496000 / 60 };
751 	INT32 nCyclesDone[2] = { 0, 0 };
752 
753 	MSM5205NewFrame(0, 2496000, nInterleave);
754 
755 	for (INT32 i = 0; i < nInterleave; i++)
756 	{
757 		ZetOpen(0);
758 		CPU_RUN(0, Zet);
759 		if (i == 240) ZetSetIRQLine(0, CPU_IRQSTATUS_ACK);
760 		ZetClose();
761 
762 		ZetOpen(1);
763 		CPU_RUN(1, Zet);
764 		if (i == 240 && music_interrupt_enable == 1) {
765 			ZetSetVector(0x30);
766 			ZetSetIRQLine(0, CPU_IRQSTATUS_HOLD);
767 		}
768 		MSM5205UpdateScanline(i);
769 		ZetClose();
770 	}
771 
772 	// Make sure the buffer is entirely filled.
773 	if (pBurnSoundOut) {
774 		AY8910Render(pBurnSoundOut, nBurnSoundLen);
775 		MSM5205Render(0, pBurnSoundOut, nBurnSoundLen);
776 	}
777 
778 	if (pBurnDraw) {
779 		DrvDraw();
780 	}
781 
782 	return 0;
783 }
784 
DrvScan(INT32 nAction,INT32 * pnMin)785 static INT32 DrvScan(INT32 nAction, INT32 *pnMin)
786 {
787 	struct BurnArea ba;
788 
789 	if (pnMin) {
790 		*pnMin = 0x029702;
791 	}
792 
793 	if (nAction & ACB_VOLATILE) {
794 		memset(&ba, 0, sizeof(ba));
795 
796 		ba.Data	  = AllRam;
797 		ba.nLen	  = RamEnd - AllRam;
798 		ba.szName = "All Ram";
799 		BurnAcb(&ba);
800 
801 		ZetScan(nAction);
802 		AY8910Scan(nAction, pnMin);
803 		MSM5205Scan(nAction, pnMin);
804 
805 		SCAN_VAR(bgbank);
806 		SCAN_VAR(flipscreen);
807 		SCAN_VAR(scrollx);
808 		SCAN_VAR(scrolly);
809 		SCAN_VAR(soundlatch);
810 		SCAN_VAR(music_interrupt_enable);
811 		SCAN_VAR(sound_interrupt_enable);
812 		SCAN_VAR(msm_toggle);
813 		SCAN_VAR(msm_data);
814 		SCAN_VAR(sound_ack);
815 	}
816 
817 	return 0;
818 }
819 
820 
821 // Dacholer
822 /* AM-1-A & AM-1-B two board stack */
823 
824 static struct BurnRomInfo dacholerRomDesc[] = {
825 	{ "dp_1.5k",	0x2000, 0x8b73a441, 1 | BRF_PRG | BRF_ESS }, //  0 Z80 #0 Code
826 	{ "dp_2.5l",	0x2000, 0x9499289f, 1 | BRF_PRG | BRF_ESS }, //  1
827 	{ "dp_3.5m",	0x2000, 0x39d37281, 1 | BRF_PRG | BRF_ESS }, //  2
828 	{ "dp_4.5n",	0x2000, 0xbb781ea4, 1 | BRF_PRG | BRF_ESS }, //  3
829 
830 	{ "ds_1.6g",	0x2000, 0xcc3a4b68, 2 | BRF_PRG | BRF_ESS }, //  4 Z80 #1 Code
831 	{ "ds_2.6h",	0x2000, 0xaa18e126, 2 | BRF_PRG | BRF_ESS }, //  5
832 	{ "ds_3.6j",	0x2000, 0x3b0131c7, 2 | BRF_PRG | BRF_ESS }, //  6
833 
834 	{ "dc_7.12j",	0x2000, 0xfd649d36, 3 | BRF_GRA },           //  7 Characters
835 
836 	{ "dc_3.13a",	0x2000, 0x9cca0fd2, 4 | BRF_GRA },           //  8 Background tiles
837 	{ "dc_2.12a",	0x2000, 0xc1322b27, 4 | BRF_GRA },           //  9
838 	{ "dc_1.11a",	0x2000, 0x9e1e7198, 4 | BRF_GRA },           // 10
839 
840 	{ "dc_5.2d",	0x2000, 0xdd4818f0, 5 | BRF_GRA },           // 11 Sprites
841 	{ "dc_4.1d",	0x2000, 0x7f338ae0, 5 | BRF_GRA },           // 12
842 	{ "dc_6.3d",	0x2000, 0x0a6d4ec4, 5 | BRF_GRA },           // 13
843 
844 	{ "dc.13d",		0x0020, 0xd273abe5, 6 | BRF_GRA },           // 14 Color data
845 
846 	{ "af-2.1h",	0x0020, 0xe1cac297, 0 | BRF_OPT },           // 15 Unknown data
847 	{ "af-1.3n",	0x0020, 0x5638e485, 0 | BRF_OPT },           // 16
848 };
849 
850 STD_ROM_PICK(dacholer)
STD_ROM_FN(dacholer)851 STD_ROM_FN(dacholer)
852 
853 static INT32 DacholerInit()
854 {
855 	return DrvInit(0);
856 }
857 
858 struct BurnDriver BurnDrvDacholer = {
859 	"dacholer", NULL, NULL, NULL, "1983",
860 	"Dacholer\0", NULL, "Nichibutsu", "Miscellaneous",
861 	NULL, NULL, NULL, NULL,
862 	BDF_GAME_WORKING, 2, HARDWARE_MISC_PRE90S, GBF_ACTION, 0,
863 	NULL, dacholerRomInfo, dacholerRomName, NULL, NULL, NULL, NULL, DacholerInputInfo, DacholerDIPInfo,
864 	DacholerInit, DrvExit, DrvFrame, DrvDraw, DrvScan, &DrvRecalc, 0x20,
865 	256, 224, 4, 3
866 };
867 
868 
869 // Kick Boy
870 
871 static struct BurnRomInfo kickboyRomDesc[] = {
872 	{ "k_1.5k",		0x2000, 0x525746f1, 1 | BRF_PRG | BRF_ESS }, //  0 Z80 #0 Code
873 	{ "k_2.5l",		0x2000, 0x9d091725, 1 | BRF_PRG | BRF_ESS }, //  1
874 	{ "k_3.5m",		0x2000, 0xd61b6ff6, 1 | BRF_PRG | BRF_ESS }, //  2
875 	{ "k_4.5n",		0x2000, 0xa8985bfe, 1 | BRF_PRG | BRF_ESS }, //  3
876 
877 	{ "k_1.6g",		0x2000, 0xcc3a4b68, 2 | BRF_PRG | BRF_ESS }, //  4 Z80 #1 Code
878 	{ "k_2.6h",		0x2000, 0xaa18e126, 2 | BRF_PRG | BRF_ESS }, //  5
879 	{ "k_3.6j",		0x2000, 0x3b0131c7, 2 | BRF_PRG | BRF_ESS }, //  6
880 
881 	{ "k_7.12j",	0x2000, 0x22be46e8, 3 | BRF_GRA },           //  7 Characters
882 
883 	{ "k_3.13a",	0x2000, 0x7eac2a64, 4 | BRF_GRA },           //  8 Background tiles
884 	{ "k_2.12a",	0x2000, 0xb8829572, 4 | BRF_GRA },           //  9
885 
886 	{ "k_5.2d",		0x2000, 0x4b769a1c, 5 | BRF_GRA },           // 10 Sprites
887 	{ "k_4.1d",		0x2000, 0x45199750, 5 | BRF_GRA },           // 11
888 	{ "k_6.3d",		0x2000, 0xd1795506, 5 | BRF_GRA },           // 12
889 
890 	{ "k.13d",		0x0020, 0x82f87a36, 6 | BRF_GRA },           // 13 Color data
891 
892 	{ "af-2.1h",	0x0020, 0xe1cac297, 0 | BRF_OPT },           // 14 Unknown data
893 	{ "af-1.3n",	0x0020, 0x5638e485, 0 | BRF_OPT },           // 15
894 };
895 
896 STD_ROM_PICK(kickboy)
STD_ROM_FN(kickboy)897 STD_ROM_FN(kickboy)
898 
899 static INT32 KickboyInit()
900 {
901 	return DrvInit(1);
902 }
903 
904 struct BurnDriver BurnDrvKickboy = {
905 	"kickboy", NULL, NULL, NULL, "1983",
906 	"Kick Boy\0", NULL, "Nichibutsu", "Miscellaneous",
907 	NULL, NULL, NULL, NULL,
908 	BDF_GAME_WORKING, 2, HARDWARE_MISC_PRE90S, GBF_ACTION, 0,
909 	NULL, kickboyRomInfo, kickboyRomName, NULL, NULL, NULL, NULL, DacholerInputInfo, KickboyDIPInfo,
910 	KickboyInit, DrvExit, DrvFrame, DrvDraw, DrvScan, &DrvRecalc, 0x20,
911 	256, 224, 4, 3
912 };
913 
914 
915 // Itazura Tenshi (Japan)
916 
917 static struct BurnRomInfo itatenRomDesc[] = {
918 	{ "1.5k",		0x2000, 0x84c8a010, 1 | BRF_PRG | BRF_ESS }, //  0 Z80 #0 Code
919 	{ "2.5l",		0x2000, 0x19946038, 1 | BRF_PRG | BRF_ESS }, //  1
920 	{ "3.5m",		0x2000, 0x4f9e26fd, 1 | BRF_PRG | BRF_ESS }, //  2
921 	{ "4.1f",		0x2000, 0x35f85aeb, 1 | BRF_PRG | BRF_ESS }, //  3
922 	{ "5.1e",		0x2000, 0x6cf30924, 1 | BRF_PRG | BRF_ESS }, //  4
923 
924 	{ "6.6g",		0x2000, 0xdfcb1a3e, 2 | BRF_PRG | BRF_ESS }, //  5 Z80 #1 Code
925 	{ "7.6h",		0x1000, 0x844e78d6, 2 | BRF_PRG | BRF_ESS }, //  6
926 
927 	{ "16.12j",		0x2000, 0x8af2bfb8, 3 | BRF_GRA },           //  7 Characters
928 
929 	{ "11.13a",		0x2000, 0xed3279d5, 4 | BRF_GRA },           //  8 Background tiles
930 	{ "10.12a",		0x2000, 0xd2b60e5d, 4 | BRF_GRA },           //  9
931 	{ "9.11a",		0x2000, 0x919cac5e, 4 | BRF_GRA },           // 10
932 	{ "8.10a",		0x2000, 0xc32b0859, 4 | BRF_GRA },           // 11
933 
934 	{ "13.2d",		0x2000, 0xd32559f5, 5 | BRF_GRA },           // 12 Sprites
935 	{ "12.1d",		0x2000, 0xf0f64636, 5 | BRF_GRA },           // 13
936 	{ "14.3d",		0x2000, 0x8c532c74, 5 | BRF_GRA },           // 14
937 	{ "15.4d",		0x2000, 0xd119b483, 5 | BRF_GRA },           // 15
938 
939 	{ "af-3.13d",	0x0020, 0x875429ba, 6 | BRF_GRA },           // 16 Color data
940 
941 	{ "af-2.1h",	0x0020, 0xe1cac297, 0 | BRF_OPT },           // 17 Unknown data
942 	{ "af-1.3n",	0x0020, 0x5638e485, 0 | BRF_OPT },           // 18
943 };
944 
945 STD_ROM_PICK(itaten)
STD_ROM_FN(itaten)946 STD_ROM_FN(itaten)
947 
948 static INT32 ItatenInit()
949 {
950 	return DrvInit(2);
951 }
952 
953 struct BurnDriver BurnDrvItaten = {
954 	"itaten", NULL, NULL, NULL, "1984",
955 	"Itazura Tenshi (Japan)\0", NULL, "Nichibutsu / Alice", "Miscellaneous",
956 	NULL, NULL, NULL, NULL,
957 	BDF_GAME_WORKING, 2, HARDWARE_MISC_PRE90S, GBF_ACTION, 0,
958 	NULL, itatenRomInfo, itatenRomName, NULL, NULL, NULL, NULL, ItatenInputInfo, ItatenDIPInfo,
959 	ItatenInit, DrvExit, DrvFrame, DrvDraw, DrvScan, &DrvRecalc, 0x20,
960 	256, 224, 4, 3
961 };
962