1 /*****************************************************************************
2  *
3  *	 i8085.c
4  *	 Portable I8085A emulator V1.2
5  *
6  *	 Copyright (c) 1999 Juergen Buchmueller, all rights reserved.
7  *	 Partially based on information out of Z80Em by Marcel De Kogel
8  *
9  * changes in V1.3
10  *   - Added undocumented opcodes for the 8085A, based on a german
11  *     book about microcomputers: "Mikrocomputertechnik mit dem
12  *     Prozessor 8085A".
13  *   - This book also suggest that INX/DCX should modify the X flag bit
14  *     for a LSB to MSB carry and
15  *   - that jumps take 10 T-states only when they're executed, 7 when
16  *     they're skipped.
17  *     Thanks for the info and a copy of the tables go to Timo Sachsenberg
18  *     <timo.sachsenberg@student.uni-tuebingen.de>
19  * changes in V1.2
20  *	 - corrected cycle counts for these classes of opcodes
21  *	   Thanks go to Jim Battle <frustum@pacbell.bet>
22  *
23  *					808x	 Z80
24  *	   DEC A		   5	   4	\
25  *	   INC A		   5	   4	 \
26  *	   LD A,B		   5	   4	  >-- Z80 is faster
27  *	   JP (HL)		   5	   4	 /
28  *	   CALL cc,nnnn: 11/17	 10/17	/
29  *
30  *	   INC HL		   5	   6	\
31  *	   DEC HL		   5	   6	 \
32  *	   LD SP,HL 	   5	   6	  \
33  *	   ADD HL,BC	  10	  11	   \
34  *	   INC (HL) 	  10	  11		>-- 8080 is faster
35  *	   DEC (HL) 	  10	  11	   /
36  *	   IN A,(#) 	  10	  11	  /
37  *	   OUT (#),A	  10	  11	 /
38  *	   EX (SP),HL	  18	  19	/
39  *
40  *	 - This source code is released as freeware for non-commercial purposes.
41  *	 - You are free to use and redistribute this code in modified or
42  *	   unmodified form, provided you list me in the credits.
43  *	 - If you modify this source code, you must add a notice to each modified
44  *	   source file that it has been changed.  If you're a nice person, you
45  *	   will clearly mark each change too.  :)
46  *	 - If you wish to use this for commercial purposes, please contact me at
47  *	   pullmoll@t-online.de
48  *	 - The author of this copywritten work reserves the right to change the
49  *	   terms of its usage and license at any time, including retroactively
50  *	 - This entire notice must remain in the source code.
51  *
52  *
53  * Revisions:
54  *
55  * xx-xx-2002 Acho A. Tang
56  *
57  * - 8085 emulation was in fact never used. It's been treated as a plain 8080.
58  * - protected IRQ0 vector from being overwritten
59  * - modified interrupt handler to properly process 8085-specific IRQ's
60  * - corrected interrupt masking, RIM and SIM behaviors according to Intel's documentation
61  *
62  * 20-Jul-2002 Krzysztof Strzecha
63  *
64  * - SBB r instructions should affect parity flag.
65  *   Fixed only for non x86 asm version (#define i8080_EXACT 1).
66  *   There are probably more opcodes which should affect this flag, but don't.
67  * - JPO nnnn and JPE nnnn opcodes in disassembler were misplaced. Fixed.
68  * - Undocumented i8080 opcodes added:
69  *   08h, 10h, 18h, 20h, 28h, 30h, 38h  -  NOP
70  *   0CBh                               -  JMP
71  *   0D9h                               -  RET
72  *   0DDh, 0EDh, 0FDh                   -  CALL
73  *   Thanks for the info go to Anton V. Ignatichev.
74  *
75  * 08-Dec-2002 Krzysztof Strzecha
76  *
77  * - ADC r instructions should affect parity flag.
78  *   Fixed only for non x86 asm version (#define i8080_EXACT 1).
79  *   There are probably more opcodes which should affect this flag, but don't.
80  *
81  * 05-Sep-2003 Krzysztof Strzecha
82  *
83  * - INR r, DCR r, ADD r, SUB r, CMP r instructions should affect parity flag.
84  *   Fixed only for non x86 asm version (#define i8080_EXACT 1).
85  *
86  *****************************************************************************/
87 
88 /*int survival_prot = 0; */
89 
90 #define VERBOSE 0
91 
92 #include "driver.h"
93 #include "state.h"
94 #include "osd_cpu.h"
95 #include "mamedbg.h"
96 #include "i8085.h"
97 #include "i8085cpu.h"
98 #include "i8085daa.h"
99 
100 #if VERBOSE
101 #include <stdio.h>
102 #include "driver.h"
103 #define LOG(x) logerror x
104 #else
105 #define LOG(x)
106 #endif
107 
108 #define I8085_INTR      0xff
109 
110 /* Layout of the registers in the debugger */
111 static UINT8 i8085_reg_layout[] = {
112 	I8085_PC,I8085_SP,I8085_AF,I8085_BC,I8085_DE,I8085_HL, -1,
113 	I8085_HALT,I8085_IM,I8085_IREQ,I8085_ISRV,I8085_VECTOR, -1,
114 	I8085_TRAP_STATE,I8085_INTR_STATE,I8085_RST55_STATE,I8085_RST65_STATE,I8085_RST75_STATE,
115 	0 };
116 
117 /* Layout of the debugger windows x,y,w,h */
118 static UINT8 i8085_win_layout[] = {
119 	25, 0,55, 3,	/* register window (top, right rows) */
120 	 0, 0,24,22,	/* disassembler window (left colums) */
121 	25, 4,55, 9,	/* memory #1 window (right, upper middle) */
122 	25,14,55, 8,	/* memory #2 window (right, lower middle) */
123 	 0,23,80, 1,	/* command line window (bottom rows) */
124 };
125 
126 
127 typedef struct {
128 	int 	cputype;	/* 0 8080, 1 8085A */
129 	PAIR	PC,SP,AF,BC,DE,HL,XX;
130 	UINT8	HALT;
131 	UINT8	IM; 		/* interrupt mask */
132 	UINT8	IREQ;		/* requested interrupts */
133 	UINT8	ISRV;		/* serviced interrupt */
134 	UINT32	INTR;		/* vector for INTR */
135 	UINT32	IRQ2;		/* scheduled interrupt address */
136 	UINT32	IRQ1;		/* executed interrupt address */
137 	INT8	nmi_state;
138 	INT8	irq_state[4];
139 	INT8	filler; /* align on dword boundary */
140 	int 	(*irq_callback)(int);
141 	void	(*sod_callback)(int state);
142 }	i8085_Regs;
143 
144 int i8085_ICount = 0;
145 
146 static i8085_Regs I;
147 static UINT8 ZS[256];
148 static UINT8 ZSP[256];
149 static UINT8 RIM_IEN = 0; //AT: IEN status latch used by the RIM instruction
ROP(void)150 static UINT8 ROP(void)
151 {
152 	return cpu_readop(I.PC.w.l++);
153 }
154 
ARG(void)155 static UINT8 ARG(void)
156 {
157 	return cpu_readop_arg(I.PC.w.l++);
158 }
159 
ARG16(void)160 static UINT16 ARG16(void)
161 {
162 	UINT16 w;
163 	w  = cpu_readop_arg(I.PC.d);
164 	I.PC.w.l++;
165 	w += cpu_readop_arg(I.PC.d) << 8;
166 	I.PC.w.l++;
167 	return w;
168 }
169 
RM(UINT32 a)170 static UINT8 RM(UINT32 a)
171 {
172 	return cpu_readmem16(a);
173 }
174 
WM(UINT32 a,UINT8 v)175 static void WM(UINT32 a, UINT8 v)
176 {
177 	cpu_writemem16(a, v);
178 }
179 
illegal(void)180 static	void illegal(void)
181 {
182 #if VERBOSE
183 	UINT16 pc = I.PC.w.l - 1;
184 	LOG(("i8085 illegal instruction %04X $%02X\n", pc, cpu_readop(pc)));
185 #endif
186 }
187 
execute_one(int opcode)188 static INLINE void execute_one(int opcode)
189 {
190 	switch (opcode)
191 	{
192 		case 0x00: i8085_ICount -= 4;	/* NOP	*/
193 			/* no op */
194 			break;
195 		case 0x01: i8085_ICount -= 10;	/* LXI	B,nnnn */
196 			I.BC.w.l = ARG16();
197 			break;
198 		case 0x02: i8085_ICount -= 7;	/* STAX B */
199 			WM(I.BC.d, I.AF.b.h);
200 			break;
201 		case 0x03: i8085_ICount -= 5;	/* INX	B */
202 			I.BC.w.l++;
203 			if (I.BC.b.l == 0x00) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
204 			break;
205 		case 0x04: i8085_ICount -= 5;	/* INR	B */
206 			M_INR(I.BC.b.h);
207 			break;
208 		case 0x05: i8085_ICount -= 5;	/* DCR	B */
209 			M_DCR(I.BC.b.h);
210 			break;
211 		case 0x06: i8085_ICount -= 7;	/* MVI	B,nn */
212 			M_MVI(I.BC.b.h);
213 			break;
214 		case 0x07: i8085_ICount -= 4;	/* RLC	*/
215 			M_RLC;
216 			break;
217 
218 		case 0x08:
219 			if( I.cputype ) {
220 				i8085_ICount -= 10;		/* DSUB */
221 				M_DSUB();
222 			} else {
223 				i8085_ICount -= 4;		/* NOP undocumented */
224 			}
225 			break;
226 		case 0x09: i8085_ICount -= 10;	/* DAD	B */
227 			M_DAD(BC);
228 			break;
229 		case 0x0a: i8085_ICount -= 7;	/* LDAX B */
230 			I.AF.b.h = RM(I.BC.d);
231 			break;
232 		case 0x0b: i8085_ICount -= 5;	/* DCX	B */
233 			I.BC.w.l--;
234 			if (I.BC.b.l == 0xff) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
235 			break;
236 		case 0x0c: i8085_ICount -= 5;	/* INR	C */
237 			M_INR(I.BC.b.l);
238 			break;
239 		case 0x0d: i8085_ICount -= 5;	/* DCR	C */
240 			M_DCR(I.BC.b.l);
241 			break;
242 		case 0x0e: i8085_ICount -= 7;	/* MVI	C,nn */
243 			M_MVI(I.BC.b.l);
244 			break;
245 		case 0x0f: i8085_ICount -= 4;	/* RRC	*/
246 			M_RRC;
247 			break;
248 
249 		case 0x10:
250 			if( I.cputype ) {
251 				i8085_ICount -= 7;		/* ASRH */
252 				I.AF.b.l = (I.AF.b.l & ~CF) | (I.HL.b.l & CF);
253 				I.HL.w.l = (I.HL.w.l >> 1);
254 			} else {
255 				i8085_ICount -= 4;		/* NOP undocumented */
256 			}
257 			break;
258 		case 0x11: i8085_ICount -= 10;	/* LXI	D,nnnn */
259 			I.DE.w.l = ARG16();
260 			break;
261 		case 0x12: i8085_ICount -= 7;	/* STAX D */
262 			WM(I.DE.d, I.AF.b.h);
263 			break;
264 		case 0x13: i8085_ICount -= 5;	/* INX	D */
265 			I.DE.w.l++;
266 			if (I.DE.b.l == 0x00) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
267 			break;
268 		case 0x14: i8085_ICount -= 5;	/* INR	D */
269 			M_INR(I.DE.b.h);
270 			break;
271 		case 0x15: i8085_ICount -= 5;	/* DCR	D */
272 			M_DCR(I.DE.b.h);
273 			break;
274 		case 0x16: i8085_ICount -= 7;	/* MVI	D,nn */
275 			M_MVI(I.DE.b.h);
276 			break;
277 		case 0x17: i8085_ICount -= 4;	/* RAL	*/
278 			M_RAL;
279 			break;
280 
281 		case 0x18:
282 			if( I.cputype ) {
283 				i8085_ICount -= 10;		/* RLDE */
284 				I.AF.b.l = (I.AF.b.l & ~(CF | VF)) | (I.DE.b.h >> 7);
285 				I.DE.w.l = (I.DE.w.l << 1) | (I.DE.w.l >> 15);
286 				if (0 != (((I.DE.w.l >> 15) ^ I.AF.b.l) & CF))
287 					I.AF.b.l |= VF;
288 			} else {
289 				i8085_ICount -= 4;		/* NOP undocumented */
290 			}
291 			break;
292 		case 0x19: i8085_ICount -= 10;	/* DAD	D */
293 			M_DAD(DE);
294 			break;
295 		case 0x1a: i8085_ICount -= 7;	/* LDAX D */
296 			I.AF.b.h = RM(I.DE.d);
297 			break;
298 		case 0x1b: i8085_ICount -= 5;	/* DCX	D */
299 			I.DE.w.l--;
300 			if (I.DE.b.l == 0xff) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
301 			break;
302 		case 0x1c: i8085_ICount -= 5;	/* INR	E */
303 			M_INR(I.DE.b.l);
304 			break;
305 		case 0x1d: i8085_ICount -= 5;	/* DCR	E */
306 			M_DCR(I.DE.b.l);
307 			break;
308 		case 0x1e: i8085_ICount -= 7;	/* MVI	E,nn */
309 			M_MVI(I.DE.b.l);
310 			break;
311 		case 0x1f: i8085_ICount -= 4;	/* RAR	*/
312 			M_RAR;
313 			break;
314 
315 		case 0x20:
316 			if( I.cputype ) {
317 				i8085_ICount -= 7;		/* RIM	*/
318 				I.AF.b.h = I.IM;
319 				I.AF.b.h |= RIM_IEN; RIM_IEN = 0; //AT: read and clear IEN status latch
320 /*				survival_prot ^= 0x01; */
321 			} else {
322 				i8085_ICount -= 4;		/* NOP undocumented */
323 			}
324 			break;
325 		case 0x21: i8085_ICount -= 10;	/* LXI	H,nnnn */
326 			I.HL.w.l = ARG16();
327 			break;
328 		case 0x22: i8085_ICount -= 16;	/* SHLD nnnn */
329 			I.XX.w.l = ARG16();
330 			WM(I.XX.d, I.HL.b.l);
331 			I.XX.w.l++;
332 			WM(I.XX.d, I.HL.b.h);
333 			break;
334 		case 0x23: i8085_ICount -= 5;	/* INX	H */
335 			I.HL.w.l++;
336 			if (I.HL.b.l == 0x00) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
337 			break;
338 		case 0x24: i8085_ICount -= 5;	/* INR	H */
339 			M_INR(I.HL.b.h);
340 			break;
341 		case 0x25: i8085_ICount -= 5;	/* DCR	H */
342 			M_DCR(I.HL.b.h);
343 			break;
344 		case 0x26: i8085_ICount -= 7;	/* MVI	H,nn */
345 			M_MVI(I.HL.b.h);
346 			break;
347 		case 0x27: i8085_ICount -= 4;	/* DAA	*/
348 			I.XX.d = I.AF.b.h;
349 			if (I.AF.b.l & CF) I.XX.d |= 0x100;
350 			if (I.AF.b.l & HF) I.XX.d |= 0x200;
351 			if (I.AF.b.l & NF) I.XX.d |= 0x400;
352 			I.AF.w.l = DAA[I.XX.d];
353 			break;
354 
355 		case 0x28:
356 			if( I.cputype ) {
357 				i8085_ICount -= 10;		/* LDEH nn */
358 				I.XX.d = ARG();
359 				I.DE.d = (I.HL.d + I.XX.d) & 0xffff;
360 			} else {
361 				i8085_ICount -= 4;		/* NOP undocumented */
362 			}
363 			break;
364 		case 0x29: i8085_ICount -= 10;	/* DAD	H */
365 			M_DAD(HL);
366 			break;
367 		case 0x2a: i8085_ICount -= 16;	/* LHLD nnnn */
368 			I.XX.d = ARG16();
369 			I.HL.b.l = RM(I.XX.d);
370 			I.XX.w.l++;
371 			I.HL.b.h = RM(I.XX.d);
372 			break;
373 		case 0x2b: i8085_ICount -= 5;	/* DCX	H */
374 			I.HL.w.l--;
375 			if (I.HL.b.l == 0xff) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
376 			break;
377 		case 0x2c: i8085_ICount -= 5;	/* INR	L */
378 			M_INR(I.HL.b.l);
379 			break;
380 		case 0x2d: i8085_ICount -= 5;	/* DCR	L */
381 			M_DCR(I.HL.b.l);
382 			break;
383 		case 0x2e: i8085_ICount -= 7;	/* MVI	L,nn */
384 			M_MVI(I.HL.b.l);
385 			break;
386 		case 0x2f: i8085_ICount -= 4;	/* CMA	*/
387 			I.AF.b.h ^= 0xff;
388 			I.AF.b.l |= HF + NF;
389 			break;
390 
391 		case 0x30:
392 			if( I.cputype ) {
393 				i8085_ICount -= 7;		/* SIM	*/
394 				if ((I.IM ^ I.AF.b.h) & 0x80)
395 					if (I.sod_callback) (*I.sod_callback)(I.AF.b.h >> 7);
396 //AT
397 				//I.IM &= (IM_SID + IM_IEN + IM_TRAP);
398 				//I.IM |= (I.AF.b.h & ~(IM_SID + IM_SOD + IM_IEN + IM_TRAP));
399 
400 				// overwrite RST5.5-7.5 interrupt masks only when bit 0x08 of the accumulator is set
401 				if (I.AF.b.h & 0x08)
402 					I.IM = (I.IM & ~(IM_RST55+IM_RST65+IM_RST75)) | (I.AF.b.h & (IM_RST55+IM_RST65+IM_RST75));
403 //ZT
404 				if (I.AF.b.h & 0x80) I.IM |= IM_SOD;
405 			} else {
406 				i8085_ICount -= 4;		/* NOP undocumented */
407 			}
408 			break;
409 		case 0x31: i8085_ICount -= 10;	/* LXI SP,nnnn */
410 			I.SP.w.l = ARG16();
411 			break;
412 		case 0x32: i8085_ICount -= 13;	/* STAX nnnn */
413 			I.XX.d = ARG16();
414 			WM(I.XX.d, I.AF.b.h);
415 			break;
416 		case 0x33: i8085_ICount -= 5;	/* INX	SP */
417 			I.SP.w.l++;
418 			if (I.SP.b.l == 0x00) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
419 			break;
420 		case 0x34: i8085_ICount -= 10;	/* INR	M */
421 			I.XX.b.l = RM(I.HL.d);
422 			M_INR(I.XX.b.l);
423 			WM(I.HL.d, I.XX.b.l);
424 			break;
425 		case 0x35: i8085_ICount -= 10;	/* DCR	M */
426 			I.XX.b.l = RM(I.HL.d);
427 			M_DCR(I.XX.b.l);
428 			WM(I.HL.d, I.XX.b.l);
429 			break;
430 		case 0x36: i8085_ICount -= 10;	/* MVI	M,nn */
431 			I.XX.b.l = ARG();
432 			WM(I.HL.d, I.XX.b.l);
433 			break;
434 		case 0x37: i8085_ICount -= 4;	/* STC	*/
435 			I.AF.b.l = (I.AF.b.l & ~(HF + NF)) | CF;
436 			break;
437 
438 		case 0x38:
439 			if( I.cputype ) {
440 				i8085_ICount -= 10;		/* LDES nn */
441 				I.XX.d = ARG();
442 				I.DE.d = (I.SP.d + I.XX.d) & 0xffff;
443 			} else {
444 				i8085_ICount -= 4;		/* NOP undocumented */
445 			}
446 			break;
447 		case 0x39: i8085_ICount -= 10;	/* DAD SP */
448 			M_DAD(SP);
449 			break;
450 		case 0x3a: i8085_ICount -= 13;	/* LDAX nnnn */
451 			I.XX.d = ARG16();
452 			I.AF.b.h = RM(I.XX.d);
453 			break;
454 		case 0x3b: i8085_ICount -= 5;	/* DCX	SP */
455 			I.SP.w.l--;
456 			if (I.SP.b.l == 0xff) I.AF.b.l |= XF; else I.AF.b.l &= ~XF;
457 			break;
458 		case 0x3c: i8085_ICount -= 5;	/* INR	A */
459 			M_INR(I.AF.b.h);
460 			break;
461 		case 0x3d: i8085_ICount -= 5;	/* DCR	A */
462 			M_DCR(I.AF.b.h);
463 			break;
464 		case 0x3e: i8085_ICount -= 7;	/* MVI	A,nn */
465 			M_MVI(I.AF.b.h);
466 			break;
467 		case 0x3f: i8085_ICount -= 4;	/* CMF	*/
468 			I.AF.b.l = ((I.AF.b.l & ~(HF + NF)) |
469 					   ((I.AF.b.l & CF) << 4)) ^ CF;
470 			break;
471 
472 		case 0x40: i8085_ICount -= 5;	/* MOV	B,B */
473 			/* no op */
474 			break;
475 		case 0x41: i8085_ICount -= 5;	/* MOV	B,C */
476 			I.BC.b.h = I.BC.b.l;
477 			break;
478 		case 0x42: i8085_ICount -= 5;	/* MOV	B,D */
479 			I.BC.b.h = I.DE.b.h;
480 			break;
481 		case 0x43: i8085_ICount -= 5;	/* MOV	B,E */
482 			I.BC.b.h = I.DE.b.l;
483 			break;
484 		case 0x44: i8085_ICount -= 5;	/* MOV	B,H */
485 			I.BC.b.h = I.HL.b.h;
486 			break;
487 		case 0x45: i8085_ICount -= 5;	/* MOV	B,L */
488 			I.BC.b.h = I.HL.b.l;
489 			break;
490 		case 0x46: i8085_ICount -= 7;	/* MOV	B,M */
491 			I.BC.b.h = RM(I.HL.d);
492 			break;
493 		case 0x47: i8085_ICount -= 5;	/* MOV	B,A */
494 			I.BC.b.h = I.AF.b.h;
495 			break;
496 
497 		case 0x48: i8085_ICount -= 5;	/* MOV	C,B */
498 			I.BC.b.l = I.BC.b.h;
499 			break;
500 		case 0x49: i8085_ICount -= 5;	/* MOV	C,C */
501 			/* no op */
502 			break;
503 		case 0x4a: i8085_ICount -= 5;	/* MOV	C,D */
504 			I.BC.b.l = I.DE.b.h;
505 			break;
506 		case 0x4b: i8085_ICount -= 5;	/* MOV	C,E */
507 			I.BC.b.l = I.DE.b.l;
508 			break;
509 		case 0x4c: i8085_ICount -= 5;	/* MOV	C,H */
510 			I.BC.b.l = I.HL.b.h;
511 			break;
512 		case 0x4d: i8085_ICount -= 5;	/* MOV	C,L */
513 			I.BC.b.l = I.HL.b.l;
514 			break;
515 		case 0x4e: i8085_ICount -= 7;	/* MOV	C,M */
516 			I.BC.b.l = RM(I.HL.d);
517 			break;
518 		case 0x4f: i8085_ICount -= 5;	/* MOV	C,A */
519 			I.BC.b.l = I.AF.b.h;
520 			break;
521 
522 		case 0x50: i8085_ICount -= 5;	/* MOV	D,B */
523 			I.DE.b.h = I.BC.b.h;
524 			break;
525 		case 0x51: i8085_ICount -= 5;	/* MOV	D,C */
526 			I.DE.b.h = I.BC.b.l;
527 			break;
528 		case 0x52: i8085_ICount -= 5;	/* MOV	D,D */
529 			/* no op */
530 			break;
531 		case 0x53: i8085_ICount -= 5;	/* MOV	D,E */
532 			I.DE.b.h = I.DE.b.l;
533 			break;
534 		case 0x54: i8085_ICount -= 5;	/* MOV	D,H */
535 			I.DE.b.h = I.HL.b.h;
536 			break;
537 		case 0x55: i8085_ICount -= 5;	/* MOV	D,L */
538 			I.DE.b.h = I.HL.b.l;
539 			break;
540 		case 0x56: i8085_ICount -= 7;	/* MOV	D,M */
541 			I.DE.b.h = RM(I.HL.d);
542 			break;
543 		case 0x57: i8085_ICount -= 5;	/* MOV	D,A */
544 			I.DE.b.h = I.AF.b.h;
545 			break;
546 
547 		case 0x58: i8085_ICount -= 5;	/* MOV	E,B */
548 			I.DE.b.l = I.BC.b.h;
549 			break;
550 		case 0x59: i8085_ICount -= 5;	/* MOV	E,C */
551 			I.DE.b.l = I.BC.b.l;
552 			break;
553 		case 0x5a: i8085_ICount -= 5;	/* MOV	E,D */
554 			I.DE.b.l = I.DE.b.h;
555 			break;
556 		case 0x5b: i8085_ICount -= 5;	/* MOV	E,E */
557 			/* no op */
558 			break;
559 		case 0x5c: i8085_ICount -= 5;	/* MOV	E,H */
560 			I.DE.b.l = I.HL.b.h;
561 			break;
562 		case 0x5d: i8085_ICount -= 5;	/* MOV	E,L */
563 			I.DE.b.l = I.HL.b.l;
564 			break;
565 		case 0x5e: i8085_ICount -= 7;	/* MOV	E,M */
566 			I.DE.b.l = RM(I.HL.d);
567 			break;
568 		case 0x5f: i8085_ICount -= 5;	/* MOV	E,A */
569 			I.DE.b.l = I.AF.b.h;
570 			break;
571 
572 		case 0x60: i8085_ICount -= 5;	/* MOV	H,B */
573 			I.HL.b.h = I.BC.b.h;
574 			break;
575 		case 0x61: i8085_ICount -= 5;	/* MOV	H,C */
576 			I.HL.b.h = I.BC.b.l;
577 			break;
578 		case 0x62: i8085_ICount -= 5;	/* MOV	H,D */
579 			I.HL.b.h = I.DE.b.h;
580 			break;
581 		case 0x63: i8085_ICount -= 5;	/* MOV	H,E */
582 			I.HL.b.h = I.DE.b.l;
583 			break;
584 		case 0x64: i8085_ICount -= 5;	/* MOV	H,H */
585 			/* no op */
586 			break;
587 		case 0x65: i8085_ICount -= 5;	/* MOV	H,L */
588 			I.HL.b.h = I.HL.b.l;
589 			break;
590 		case 0x66: i8085_ICount -= 7;	/* MOV	H,M */
591 			I.HL.b.h = RM(I.HL.d);
592 			break;
593 		case 0x67: i8085_ICount -= 5;	/* MOV	H,A */
594 			I.HL.b.h = I.AF.b.h;
595 			break;
596 
597 		case 0x68: i8085_ICount -= 5;	/* MOV	L,B */
598 			I.HL.b.l = I.BC.b.h;
599 			break;
600 		case 0x69: i8085_ICount -= 5;	/* MOV	L,C */
601 			I.HL.b.l = I.BC.b.l;
602 			break;
603 		case 0x6a: i8085_ICount -= 5;	/* MOV	L,D */
604 			I.HL.b.l = I.DE.b.h;
605 			break;
606 		case 0x6b: i8085_ICount -= 5;	/* MOV	L,E */
607 			I.HL.b.l = I.DE.b.l;
608 			break;
609 		case 0x6c: i8085_ICount -= 5;	/* MOV	L,H */
610 			I.HL.b.l = I.HL.b.h;
611 			break;
612 		case 0x6d: i8085_ICount -= 5;	/* MOV	L,L */
613 			/* no op */
614 			break;
615 		case 0x6e: i8085_ICount -= 7;	/* MOV	L,M */
616 			I.HL.b.l = RM(I.HL.d);
617 			break;
618 		case 0x6f: i8085_ICount -= 5;	/* MOV	L,A */
619 			I.HL.b.l = I.AF.b.h;
620 			break;
621 
622 		case 0x70: i8085_ICount -= 7;	/* MOV	M,B */
623 			WM(I.HL.d, I.BC.b.h);
624 			break;
625 		case 0x71: i8085_ICount -= 7;	/* MOV	M,C */
626 			WM(I.HL.d, I.BC.b.l);
627 			break;
628 		case 0x72: i8085_ICount -= 7;	/* MOV	M,D */
629 			WM(I.HL.d, I.DE.b.h);
630 			break;
631 		case 0x73: i8085_ICount -= 7;	/* MOV	M,E */
632 			WM(I.HL.d, I.DE.b.l);
633 			break;
634 		case 0x74: i8085_ICount -= 7;	/* MOV	M,H */
635 			WM(I.HL.d, I.HL.b.h);
636 			break;
637 		case 0x75: i8085_ICount -= 7;	/* MOV	M,L */
638 			WM(I.HL.d, I.HL.b.l);
639 			break;
640 		case 0x76: i8085_ICount -= 4;	/* HALT */
641 			I.PC.w.l--;
642 			I.HALT = 1;
643 			if (i8085_ICount > 0) i8085_ICount = 0;
644 			break;
645 		case 0x77: i8085_ICount -= 7;	/* MOV	M,A */
646 			WM(I.HL.d, I.AF.b.h);
647 			break;
648 
649 		case 0x78: i8085_ICount -= 5;	/* MOV	A,B */
650 			I.AF.b.h = I.BC.b.h;
651 			break;
652 		case 0x79: i8085_ICount -= 5;	/* MOV	A,C */
653 			I.AF.b.h = I.BC.b.l;
654 			break;
655 		case 0x7a: i8085_ICount -= 5;	/* MOV	A,D */
656 			I.AF.b.h = I.DE.b.h;
657 			break;
658 		case 0x7b: i8085_ICount -= 5;	/* MOV	A,E */
659 			I.AF.b.h = I.DE.b.l;
660 			break;
661 		case 0x7c: i8085_ICount -= 5;	/* MOV	A,H */
662 			I.AF.b.h = I.HL.b.h;
663 			break;
664 		case 0x7d: i8085_ICount -= 5;	/* MOV	A,L */
665 			I.AF.b.h = I.HL.b.l;
666 			break;
667 		case 0x7e: i8085_ICount -= 7;	/* MOV	A,M */
668 			I.AF.b.h = RM(I.HL.d);
669 			break;
670 		case 0x7f: i8085_ICount -= 5;	/* MOV	A,A */
671 			/* no op */
672 			break;
673 
674 		case 0x80: i8085_ICount -= 4;	/* ADD	B */
675 			M_ADD(I.BC.b.h);
676 			break;
677 		case 0x81: i8085_ICount -= 4;	/* ADD	C */
678 			M_ADD(I.BC.b.l);
679 			break;
680 		case 0x82: i8085_ICount -= 4;	/* ADD	D */
681 			M_ADD(I.DE.b.h);
682 			break;
683 		case 0x83: i8085_ICount -= 4;	/* ADD	E */
684 			M_ADD(I.DE.b.l);
685 			break;
686 		case 0x84: i8085_ICount -= 4;	/* ADD	H */
687 			M_ADD(I.HL.b.h);
688 			break;
689 		case 0x85: i8085_ICount -= 4;	/* ADD	L */
690 			M_ADD(I.HL.b.l);
691 			break;
692 		case 0x86: i8085_ICount -= 7;	/* ADD	M */
693 			M_ADD(RM(I.HL.d));
694 			break;
695 		case 0x87: i8085_ICount -= 4;	/* ADD	A */
696 			M_ADD(I.AF.b.h);
697 			break;
698 
699 		case 0x88: i8085_ICount -= 4;	/* ADC	B */
700 			M_ADC(I.BC.b.h);
701 			break;
702 		case 0x89: i8085_ICount -= 4;	/* ADC	C */
703 			M_ADC(I.BC.b.l);
704 			break;
705 		case 0x8a: i8085_ICount -= 4;	/* ADC	D */
706 			M_ADC(I.DE.b.h);
707 			break;
708 		case 0x8b: i8085_ICount -= 4;	/* ADC	E */
709 			M_ADC(I.DE.b.l);
710 			break;
711 		case 0x8c: i8085_ICount -= 4;	/* ADC	H */
712 			M_ADC(I.HL.b.h);
713 			break;
714 		case 0x8d: i8085_ICount -= 4;	/* ADC	L */
715 			M_ADC(I.HL.b.l);
716 			break;
717 		case 0x8e: i8085_ICount -= 7;	/* ADC	M */
718 			M_ADC(RM(I.HL.d));
719 			break;
720 		case 0x8f: i8085_ICount -= 4;	/* ADC	A */
721 			M_ADC(I.AF.b.h);
722 			break;
723 
724 		case 0x90: i8085_ICount -= 4;	/* SUB	B */
725 			M_SUB(I.BC.b.h);
726 			break;
727 		case 0x91: i8085_ICount -= 4;	/* SUB	C */
728 			M_SUB(I.BC.b.l);
729 			break;
730 		case 0x92: i8085_ICount -= 4;	/* SUB	D */
731 			M_SUB(I.DE.b.h);
732 			break;
733 		case 0x93: i8085_ICount -= 4;	/* SUB	E */
734 			M_SUB(I.DE.b.l);
735 			break;
736 		case 0x94: i8085_ICount -= 4;	/* SUB	H */
737 			M_SUB(I.HL.b.h);
738 			break;
739 		case 0x95: i8085_ICount -= 4;	/* SUB	L */
740 			M_SUB(I.HL.b.l);
741 			break;
742 		case 0x96: i8085_ICount -= 7;	/* SUB	M */
743 			M_SUB(RM(I.HL.d));
744 			break;
745 		case 0x97: i8085_ICount -= 4;	/* SUB	A */
746 			M_SUB(I.AF.b.h);
747 			break;
748 
749 		case 0x98: i8085_ICount -= 4;	/* SBB	B */
750 			M_SBB(I.BC.b.h);
751 			break;
752 		case 0x99: i8085_ICount -= 4;	/* SBB	C */
753 			M_SBB(I.BC.b.l);
754 			break;
755 		case 0x9a: i8085_ICount -= 4;	/* SBB	D */
756 			M_SBB(I.DE.b.h);
757 			break;
758 		case 0x9b: i8085_ICount -= 4;	/* SBB	E */
759 			M_SBB(I.DE.b.l);
760 			break;
761 		case 0x9c: i8085_ICount -= 4;	/* SBB	H */
762 			M_SBB(I.HL.b.h);
763 			break;
764 		case 0x9d: i8085_ICount -= 4;	/* SBB	L */
765 			M_SBB(I.HL.b.l);
766 			break;
767 		case 0x9e: i8085_ICount -= 7;	/* SBB	M */
768 			M_SBB(RM(I.HL.d));
769 			break;
770 		case 0x9f: i8085_ICount -= 4;	/* SBB	A */
771 			M_SBB(I.AF.b.h);
772 			break;
773 
774 		case 0xa0: i8085_ICount -= 4;	/* ANA	B */
775 			M_ANA(I.BC.b.h);
776 			break;
777 		case 0xa1: i8085_ICount -= 4;	/* ANA	C */
778 			M_ANA(I.BC.b.l);
779 			break;
780 		case 0xa2: i8085_ICount -= 4;	/* ANA	D */
781 			M_ANA(I.DE.b.h);
782 			break;
783 		case 0xa3: i8085_ICount -= 4;	/* ANA	E */
784 			M_ANA(I.DE.b.l);
785 			break;
786 		case 0xa4: i8085_ICount -= 4;	/* ANA	H */
787 			M_ANA(I.HL.b.h);
788 			break;
789 		case 0xa5: i8085_ICount -= 4;	/* ANA	L */
790 			M_ANA(I.HL.b.l);
791 			break;
792 		case 0xa6: i8085_ICount -= 7;	/* ANA	M */
793 			M_ANA(RM(I.HL.d));
794 			break;
795 		case 0xa7: i8085_ICount -= 4;	/* ANA	A */
796 			M_ANA(I.AF.b.h);
797 			break;
798 
799 		case 0xa8: i8085_ICount -= 4;	/* XRA	B */
800 			M_XRA(I.BC.b.h);
801 			break;
802 		case 0xa9: i8085_ICount -= 4;	/* XRA	C */
803 			M_XRA(I.BC.b.l);
804 			break;
805 		case 0xaa: i8085_ICount -= 4;	/* XRA	D */
806 			M_XRA(I.DE.b.h);
807 			break;
808 		case 0xab: i8085_ICount -= 4;	/* XRA	E */
809 			M_XRA(I.DE.b.l);
810 			break;
811 		case 0xac: i8085_ICount -= 4;	/* XRA	H */
812 			M_XRA(I.HL.b.h);
813 			break;
814 		case 0xad: i8085_ICount -= 4;	/* XRA	L */
815 			M_XRA(I.HL.b.l);
816 			break;
817 		case 0xae: i8085_ICount -= 7;	/* XRA	M */
818 			M_XRA(RM(I.HL.d));
819 			break;
820 		case 0xaf: i8085_ICount -= 4;	/* XRA	A */
821 			M_XRA(I.AF.b.h);
822 			break;
823 
824 		case 0xb0: i8085_ICount -= 4;	/* ORA	B */
825 			M_ORA(I.BC.b.h);
826 			break;
827 		case 0xb1: i8085_ICount -= 4;	/* ORA	C */
828 			M_ORA(I.BC.b.l);
829 			break;
830 		case 0xb2: i8085_ICount -= 4;	/* ORA	D */
831 			M_ORA(I.DE.b.h);
832 			break;
833 		case 0xb3: i8085_ICount -= 4;	/* ORA	E */
834 			M_ORA(I.DE.b.l);
835 			break;
836 		case 0xb4: i8085_ICount -= 4;	/* ORA	H */
837 			M_ORA(I.HL.b.h);
838 			break;
839 		case 0xb5: i8085_ICount -= 4;	/* ORA	L */
840 			M_ORA(I.HL.b.l);
841 			break;
842 		case 0xb6: i8085_ICount -= 7;	/* ORA	M */
843 			M_ORA(RM(I.HL.d));
844 			break;
845 		case 0xb7: i8085_ICount -= 4;	/* ORA	A */
846 			M_ORA(I.AF.b.h);
847 			break;
848 
849 		case 0xb8: i8085_ICount -= 4;	/* CMP	B */
850 			M_CMP(I.BC.b.h);
851 			break;
852 		case 0xb9: i8085_ICount -= 4;	/* CMP	C */
853 			M_CMP(I.BC.b.l);
854 			break;
855 		case 0xba: i8085_ICount -= 4;	/* CMP	D */
856 			M_CMP(I.DE.b.h);
857 			break;
858 		case 0xbb: i8085_ICount -= 4;	/* CMP	E */
859 			M_CMP(I.DE.b.l);
860 			break;
861 		case 0xbc: i8085_ICount -= 4;	/* CMP	H */
862 			M_CMP(I.HL.b.h);
863 			break;
864 		case 0xbd: i8085_ICount -= 4;	/* CMP	L */
865 			M_CMP(I.HL.b.l);
866 			break;
867 		case 0xbe: i8085_ICount -= 7;	/* CMP	M */
868 			M_CMP(RM(I.HL.d));
869 			break;
870 		case 0xbf: i8085_ICount -= 4;	/* CMP	A */
871 			M_CMP(I.AF.b.h);
872 			break;
873 
874 		case 0xc0: i8085_ICount -= 5;	/* RNZ	*/
875 			M_RET( !(I.AF.b.l & ZF) );
876 			break;
877 		case 0xc1: i8085_ICount -= 10;	/* POP	B */
878 			M_POP(BC);
879 			break;
880 		case 0xc2: i8085_ICount -= 7;	/* JNZ	nnnn */
881 			M_JMP( !(I.AF.b.l & ZF) );
882 			break;
883 		case 0xc3: i8085_ICount -= 7;	/* JMP	nnnn */
884 			M_JMP(1);
885 			break;
886 		case 0xc4: i8085_ICount -= 11;	/* CNZ	nnnn */
887 			M_CALL( !(I.AF.b.l & ZF) );
888 			break;
889 		case 0xc5: i8085_ICount -= 11;	/* PUSH B */
890 			M_PUSH(BC);
891 			break;
892 		case 0xc6: i8085_ICount -= 7;	/* ADI	nn */
893 			I.XX.b.l = ARG();
894 			M_ADD(I.XX.b.l);
895 				break;
896 		case 0xc7: i8085_ICount -= 11;	/* RST	0 */
897 			M_RST(0);
898 			break;
899 
900 		case 0xc8: i8085_ICount -= 5;	/* RZ	*/
901 			M_RET( I.AF.b.l & ZF );
902 			break;
903 		case 0xc9: i8085_ICount -= 4;	/* RET	*/
904 			M_RET(1);
905 			break;
906 		case 0xca: i8085_ICount -= 7;	/* JZ	nnnn */
907 			M_JMP( I.AF.b.l & ZF );
908 			break;
909 		case 0xcb:
910 			if( I.cputype ) {
911 				if (I.AF.b.l & VF) {
912 					i8085_ICount -= 12;
913 					M_RST(8);			/* call 0x40 */
914 				} else {
915 					i8085_ICount -= 6;	/* RST  V */
916 				}
917 			} else {
918 				i8085_ICount -= 7;	/* JMP	nnnn undocumented*/
919 				M_JMP(1);
920 			}
921 			break;
922 		case 0xcc: i8085_ICount -= 11;	/* CZ	nnnn */
923 			M_CALL( I.AF.b.l & ZF );
924 			break;
925 		case 0xcd: i8085_ICount -= 11;	/* CALL nnnn */
926 			M_CALL(1);
927 			break;
928 		case 0xce: i8085_ICount -= 7;	/* ACI	nn */
929 			I.XX.b.l = ARG();
930 			M_ADC(I.XX.b.l);
931 			break;
932 		case 0xcf: i8085_ICount -= 11;	/* RST	1 */
933 			M_RST(1);
934 			break;
935 
936 		case 0xd0: i8085_ICount -= 5;	/* RNC	*/
937 			M_RET( !(I.AF.b.l & CF) );
938 			break;
939 		case 0xd1: i8085_ICount -= 10;	/* POP	D */
940 			M_POP(DE);
941 			break;
942 		case 0xd2: i8085_ICount -= 7;	/* JNC	nnnn */
943 			M_JMP( !(I.AF.b.l & CF) );
944 			break;
945 		case 0xd3: i8085_ICount -= 10;	/* OUT	nn */
946 			M_OUT;
947 			break;
948 		case 0xd4: i8085_ICount -= 11;	/* CNC	nnnn */
949 			M_CALL( !(I.AF.b.l & CF) );
950 			break;
951 		case 0xd5: i8085_ICount -= 11;	/* PUSH D */
952 			M_PUSH(DE);
953 			break;
954 		case 0xd6: i8085_ICount -= 7;	/* SUI	nn */
955 			I.XX.b.l = ARG();
956 			M_SUB(I.XX.b.l);
957 			break;
958 		case 0xd7: i8085_ICount -= 11;	/* RST	2 */
959 			M_RST(2);
960 			break;
961 
962 		case 0xd8: i8085_ICount -= 5;	/* RC	*/
963 			M_RET( I.AF.b.l & CF );
964 			break;
965 		case 0xd9:
966 			if( I.cputype ) {
967 				i8085_ICount -= 10;		/* SHLX */
968 				I.XX.w.l = I.DE.w.l;
969 				WM(I.XX.d, I.HL.b.l);
970 				I.XX.w.l++;
971 				WM(I.XX.d, I.HL.b.h);
972 			} else {
973 				i8085_ICount -= 4;	/* RET undocumented */
974 				M_RET(1);
975 			}
976 			break;
977 		case 0xda: i8085_ICount -= 7;	/* JC	nnnn */
978 			M_JMP( I.AF.b.l & CF );
979 			break;
980 		case 0xdb: i8085_ICount -= 10;	/* IN	nn */
981 			M_IN;
982 			break;
983 		case 0xdc: i8085_ICount -= 11;	/* CC	nnnn */
984 			M_CALL( I.AF.b.l & CF );
985 			break;
986 		case 0xdd:
987 			if( I.cputype ) {
988 				i8085_ICount -= 7;		/* JNX  nnnn */
989 				M_JMP( !(I.AF.b.l & XF) );
990 			} else {
991 				i8085_ICount -= 11;	/* CALL nnnn undocumented */
992 				M_CALL(1);
993 			}
994 			break;
995 		case 0xde: i8085_ICount -= 7;	/* SBI	nn */
996 			I.XX.b.l = ARG();
997 			M_SBB(I.XX.b.l);
998 			break;
999 		case 0xdf: i8085_ICount -= 11;	/* RST	3 */
1000 			M_RST(3);
1001 			break;
1002 
1003 		case 0xe0: i8085_ICount -= 5;	/* RPE	  */
1004 			M_RET( !(I.AF.b.l & VF) );
1005 			break;
1006 		case 0xe1: i8085_ICount -= 10;	/* POP	H */
1007 			M_POP(HL);
1008 			break;
1009 		case 0xe2: i8085_ICount -= 7;	/* JPO	nnnn */
1010 			M_JMP( !(I.AF.b.l & VF) );
1011 			break;
1012 		case 0xe3: i8085_ICount -= 18;	/* XTHL */
1013 			M_POP(XX);
1014 			M_PUSH(HL);
1015 			I.HL.d = I.XX.d;
1016 			break;
1017 		case 0xe4: i8085_ICount -= 11;	/* CPE	nnnn */
1018 			M_CALL( !(I.AF.b.l & VF) );
1019 			break;
1020 		case 0xe5: i8085_ICount -= 11;	/* PUSH H */
1021 			M_PUSH(HL);
1022 			break;
1023 		case 0xe6: i8085_ICount -= 7;	/* ANI	nn */
1024 			I.XX.b.l = ARG();
1025 			M_ANA(I.XX.b.l);
1026 			break;
1027 		case 0xe7: i8085_ICount -= 11;	/* RST	4 */
1028 			M_RST(4);
1029 			break;
1030 
1031 		case 0xe8: i8085_ICount -= 5;	/* RPO	*/
1032 			M_RET( I.AF.b.l & VF );
1033 			break;
1034 		case 0xe9: i8085_ICount -= 5;	/* PCHL */
1035 			I.PC.d = I.HL.w.l;
1036 			change_pc16(I.PC.d);
1037 			break;
1038 		case 0xea: i8085_ICount -= 7;	/* JPE	nnnn */
1039 			M_JMP( I.AF.b.l & VF );
1040 			break;
1041 		case 0xeb: i8085_ICount -= 4;	/* XCHG */
1042 			I.XX.d = I.DE.d;
1043 			I.DE.d = I.HL.d;
1044 			I.HL.d = I.XX.d;
1045 			break;
1046 		case 0xec: i8085_ICount -= 11;	/* CPO	nnnn */
1047 			M_CALL( I.AF.b.l & VF );
1048 			break;
1049 		case 0xed:
1050 			if( I.cputype ) {
1051 				i8085_ICount -= 10;		/* LHLX */
1052 				I.XX.w.l = I.DE.w.l;
1053 				I.HL.b.l = RM(I.XX.d);
1054 				I.XX.w.l++;
1055 				I.HL.b.h = RM(I.XX.d);
1056 			} else {
1057 				i8085_ICount -= 11;	/* CALL nnnn undocumented */
1058 				M_CALL(1);
1059 			}
1060 			break;
1061 		case 0xee: i8085_ICount -= 7;	/* XRI	nn */
1062 			I.XX.b.l = ARG();
1063 			M_XRA(I.XX.b.l);
1064 			break;
1065 		case 0xef: i8085_ICount -= 11;	/* RST	5 */
1066 			M_RST(5);
1067 			break;
1068 
1069 		case 0xf0: i8085_ICount -= 5;	/* RP	*/
1070 			M_RET( !(I.AF.b.l&SF) );
1071 			break;
1072 		case 0xf1: i8085_ICount -= 10;	/* POP	A */
1073 			M_POP(AF);
1074 			break;
1075 		case 0xf2: i8085_ICount -= 7;	/* JP	nnnn */
1076 			M_JMP( !(I.AF.b.l & SF) );
1077 			break;
1078 		case 0xf3: i8085_ICount -= 4;	/* DI	*/
1079 			/* remove interrupt enable */
1080 			I.IM &= ~IM_IEN;
1081 			break;
1082 		case 0xf4: i8085_ICount -= 11;	/* CP	nnnn */
1083 			M_CALL( !(I.AF.b.l & SF) );
1084 			break;
1085 		case 0xf5: i8085_ICount -= 11;	/* PUSH A */
1086 			M_PUSH(AF);
1087 			break;
1088 		case 0xf6: i8085_ICount -= 7;	/* ORI	nn */
1089 			I.XX.b.l = ARG();
1090 			M_ORA(I.XX.b.l);
1091 			break;
1092 		case 0xf7: i8085_ICount -= 11;	/* RST	6 */
1093 			M_RST(6);
1094 			break;
1095 
1096 		case 0xf8: i8085_ICount -= 5;	/* RM	*/
1097 			M_RET( I.AF.b.l & SF );
1098 			break;
1099 		case 0xf9: i8085_ICount -= 5;	/* SPHL */
1100 			I.SP.d = I.HL.d;
1101 			break;
1102 		case 0xfa: i8085_ICount -= 7;	/* JM	nnnn */
1103 			M_JMP( I.AF.b.l & SF );
1104 			break;
1105 		case 0xfb: i8085_ICount -= 4;	/* EI */
1106 			/* set interrupt enable */
1107 			I.IM |= IM_IEN;
1108 			/* remove serviced IRQ flag */
1109 			I.IREQ &= ~I.ISRV;
1110 			/* reset serviced IRQ */
1111 			I.ISRV = 0;
1112 			if( I.irq_state[0] != CLEAR_LINE ) {
1113 				LOG(("i8085 EI sets INTR\n"));
1114 				I.IREQ |= IM_INTR;
1115 				I.INTR = I8085_INTR;
1116 			}
1117 			if( I.cputype ) {
1118 				if( I.irq_state[1] != CLEAR_LINE ) {
1119 					LOG(("i8085 EI sets RST5.5\n"));
1120 					I.IREQ |= IM_RST55;
1121 				}
1122 				if( I.irq_state[2] != CLEAR_LINE ) {
1123 					LOG(("i8085 EI sets RST6.5\n"));
1124 					I.IREQ |= IM_RST65;
1125 				}
1126 				if( I.irq_state[3] != CLEAR_LINE ) {
1127 					LOG(("i8085 EI sets RST7.5\n"));
1128 					I.IREQ |= IM_RST75;
1129 				}
1130 				/* find highest priority IREQ flag with
1131 				   IM enabled and schedule for execution */
1132 				if( !(I.IM & IM_RST75) && (I.IREQ & IM_RST75) ) {
1133 					I.ISRV = IM_RST75;
1134 					I.IRQ2 = ADDR_RST75;
1135 				}
1136 				else
1137 				if( !(I.IM & IM_RST65) && (I.IREQ & IM_RST65) ) {
1138 					I.ISRV = IM_RST65;
1139 					I.IRQ2 = ADDR_RST65;
1140 				} else if( !(I.IM & IM_RST55) && (I.IREQ & IM_RST55) ) {
1141 					I.ISRV = IM_RST55;
1142 					I.IRQ2 = ADDR_RST55;
1143 				} else if( !(I.IM & IM_INTR) && (I.IREQ & IM_INTR) ) {
1144 					I.ISRV = IM_INTR;
1145 					I.IRQ2 = I.INTR;
1146 				}
1147 			} else {
1148 				if( !(I.IM & IM_INTR) && (I.IREQ & IM_INTR) ) {
1149 					I.ISRV = IM_INTR;
1150 					I.IRQ2 = I.INTR;
1151 				}
1152 			}
1153 			break;
1154 		case 0xfc: i8085_ICount -= 11;	/* CM	nnnn */
1155 			M_CALL( I.AF.b.l & SF );
1156 			break;
1157 		case 0xfd:
1158 			if( I.cputype ) {
1159 				i8085_ICount -= 7;		/* JX   nnnn */
1160 				M_JMP( I.AF.b.l & XF );
1161 			} else {
1162 				i8085_ICount -= 11;	/* CALL nnnn undocumented */
1163 				M_CALL(1);
1164 			}
1165 			break;
1166 		case 0xfe: i8085_ICount -= 7;	/* CPI	nn */
1167 			I.XX.b.l = ARG();
1168 			M_CMP(I.XX.b.l);
1169 			break;
1170 		case 0xff: i8085_ICount -= 11;	/* RST	7 */
1171 			M_RST(7);
1172 			break;
1173 	}
1174 }
1175 
Interrupt(void)1176 static void Interrupt(void)
1177 {
1178 
1179 	if( I.HALT )		/* if the CPU was halted */
1180 	{
1181 		I.PC.w.l++; 	/* skip HALT instr */
1182 		I.HALT = 0;
1183 	}
1184 //AT
1185 	I.IREQ &= ~I.ISRV; // remove serviced IRQ flag
1186 	RIM_IEN = (I.ISRV==IM_TRAP) ? I.IM & IM_IEN : 0; // latch general interrupt enable bit on TRAP or NMI
1187 //ZT
1188 	I.IM &= ~IM_IEN;		/* remove general interrupt enable bit */
1189 
1190 	if( I.ISRV == IM_INTR )
1191 	{
1192 		LOG(("Interrupt get INTR vector\n"));
1193 		I.IRQ1 = (I.irq_callback)(0);
1194 	}
1195 
1196 	if( I.cputype )
1197 	{
1198 		if( I.ISRV == IM_RST55 )
1199 		{
1200 			LOG(("Interrupt get RST5.5 vector\n"));
1201 			//I.IRQ1 = (I.irq_callback)(1);
1202 			I.irq_state[I8085_RST55_LINE] = CLEAR_LINE; //AT: processing RST5.5, reset interrupt line
1203 		}
1204 
1205 		if( I.ISRV == IM_RST65	)
1206 		{
1207 			LOG(("Interrupt get RST6.5 vector\n"));
1208 			//I.IRQ1 = (I.irq_callback)(2);
1209 			I.irq_state[I8085_RST65_LINE] = CLEAR_LINE; //AT: processing RST6.5, reset interrupt line
1210 		}
1211 
1212 		if( I.ISRV == IM_RST75 )
1213 		{
1214 			LOG(("Interrupt get RST7.5 vector\n"));
1215 			//I.IRQ1 = (I.irq_callback)(3);
1216 			I.irq_state[I8085_RST75_LINE] = CLEAR_LINE; //AT: processing RST7.5, reset interrupt line
1217 		}
1218 	}
1219 
1220 	switch( I.IRQ1 & 0xff0000 )
1221 	{
1222 		case 0xcd0000:	/* CALL nnnn */
1223 			i8085_ICount -= 7;
1224 			M_PUSH(PC);
1225 		case 0xc30000:	/* JMP	nnnn */
1226 			i8085_ICount -= 10;
1227 			I.PC.d = I.IRQ1 & 0xffff;
1228 			change_pc16(I.PC.d);
1229 			break;
1230 		default:
1231 			switch( I.ISRV )
1232 			{
1233 				case IM_TRAP:
1234 				case IM_RST75:
1235 				case IM_RST65:
1236 				case IM_RST55:
1237 					M_PUSH(PC);
1238 					if (I.IRQ1 != (1 << I8085_RST75_LINE))
1239 						I.PC.d = I.IRQ1;
1240 					else
1241 						I.PC.d = 0x3c;
1242 					change_pc16(I.PC.d);
1243 					break;
1244 				default:
1245 					LOG(("i8085 take int $%02x\n", I.IRQ1));
1246 					execute_one(I.IRQ1 & 0xff);
1247 			}
1248 	}
1249 }
1250 
i8085_execute(int cycles)1251 int i8085_execute(int cycles)
1252 {
1253 
1254 	i8085_ICount = cycles;
1255 	do
1256 	{
1257 		CALL_MAME_DEBUG;
1258 		/* interrupts enabled or TRAP pending ? */
1259 		if ( (I.IM & IM_IEN) || (I.IREQ & IM_TRAP) )
1260 		{
1261 			/* copy scheduled to executed interrupt request */
1262 			I.IRQ1 = I.IRQ2;
1263 			/* reset scheduled interrupt request */
1264 			I.IRQ2 = 0;
1265 			/* interrupt now ? */
1266 			if (I.IRQ1) Interrupt();
1267 		}
1268 
1269 		/* here we go... */
1270 		execute_one(ROP());
1271 
1272 	} while (i8085_ICount > 0);
1273 
1274 	return cycles - i8085_ICount;
1275 }
1276 
1277 /****************************************************************************
1278  * Initialise the various lookup tables used by the emulation code
1279  ****************************************************************************/
init_tables(void)1280 static void init_tables (void)
1281 {
1282 	UINT8 zs;
1283 	int i, p;
1284 	for (i = 0; i < 256; i++)
1285 	{
1286 		zs = 0;
1287 		if (i==0) zs |= ZF;
1288 		if (i&128) zs |= SF;
1289 		p = 0;
1290 		if (i&1) ++p;
1291 		if (i&2) ++p;
1292 		if (i&4) ++p;
1293 		if (i&8) ++p;
1294 		if (i&16) ++p;
1295 		if (i&32) ++p;
1296 		if (i&64) ++p;
1297 		if (i&128) ++p;
1298 		ZS[i] = zs;
1299 		ZSP[i] = zs | ((p&1) ? 0 : VF);
1300 	}
1301 }
1302 
1303 /****************************************************************************
1304  * Init the 8085 emulation
1305  ****************************************************************************/
i8085_init(void)1306 void i8085_init(void)
1307 {
1308 	int cpu = cpu_getactivecpu();
1309 	init_tables();
1310 	I.cputype = 1;
1311 
1312 	state_save_register_UINT16("i8085", cpu, "AF", &I.AF.w.l, 1);
1313 	state_save_register_UINT16("i8085", cpu, "BC", &I.BC.w.l, 1);
1314 	state_save_register_UINT16("i8085", cpu, "DE", &I.DE.w.l, 1);
1315 	state_save_register_UINT16("i8085", cpu, "HL", &I.HL.w.l, 1);
1316 	state_save_register_UINT16("i8085", cpu, "SP", &I.SP.w.l, 1);
1317 	state_save_register_UINT16("i8085", cpu, "PC", &I.PC.w.l, 1);
1318 	state_save_register_UINT8("i8085", cpu, "HALT", &I.HALT, 1);
1319 	state_save_register_UINT8("i8085", cpu, "IM", &I.IM, 1);
1320 	state_save_register_UINT8("i8085", cpu, "IREQ", &I.IREQ, 1);
1321 	state_save_register_UINT8("i8085", cpu, "ISRV", &I.ISRV, 1);
1322 	state_save_register_UINT32("i8085", cpu, "INTR", &I.INTR, 1);
1323 	state_save_register_UINT32("i8085", cpu, "IRQ2", &I.IRQ2, 1);
1324 	state_save_register_UINT32("i8085", cpu, "IRQ1", &I.IRQ1, 1);
1325 	state_save_register_INT8("i8085", cpu, "NMI_STATE", &I.nmi_state, 1);
1326 	state_save_register_INT8("i8085", cpu, "IRQ_STATE", I.irq_state, 4);
1327 }
1328 
1329 /****************************************************************************
1330  * Reset the 8085 emulation
1331  ****************************************************************************/
i8085_reset(void * param)1332 void i8085_reset(void *param)
1333 {
1334 	int cputype_bak = I.cputype; //AT: backup cputype(0=8080, 1=8085)
1335 
1336 	init_tables();
1337 	memset(&I, 0, sizeof(i8085_Regs)); //AT: this also resets I.cputype so 8085 features were never ever used!
1338 	change_pc16(I.PC.d);
1339 
1340 	I.cputype = cputype_bak; //AT: restore cputype
1341 }
1342 
1343 /****************************************************************************
1344  * Shut down the CPU emulation
1345  ****************************************************************************/
i8085_exit(void)1346 void i8085_exit(void)
1347 {
1348 	/* nothing to do */
1349 }
1350 
1351 /****************************************************************************
1352  * Get the current 8085 context
1353  ****************************************************************************/
i8085_get_context(void * dst)1354 unsigned i8085_get_context(void *dst)
1355 {
1356 	if( dst )
1357 		*(i8085_Regs*)dst = I;
1358 	return sizeof(i8085_Regs);
1359 }
1360 
1361 /****************************************************************************
1362  * Set the current 8085 context
1363  ****************************************************************************/
i8085_set_context(void * src)1364 void i8085_set_context(void *src)
1365 {
1366 	if( src )
1367 	{
1368 		I = *(i8085_Regs*)src;
1369 		change_pc16(I.PC.d);
1370 	}
1371 }
1372 
1373 /****************************************************************************
1374  * Get a specific register
1375  ****************************************************************************/
i8085_get_reg(int regnum)1376 unsigned i8085_get_reg(int regnum)
1377 {
1378 	switch( regnum )
1379 	{
1380 		case REG_PC: return I.PC.d;
1381 		case I8085_PC: return I.PC.w.l;
1382 		case REG_SP: return I.SP.d;
1383 		case I8085_SP: return I.SP.w.l;
1384 		case I8085_AF: return I.AF.w.l;
1385 		case I8085_BC: return I.BC.w.l;
1386 		case I8085_DE: return I.DE.w.l;
1387 		case I8085_HL: return I.HL.w.l;
1388 		case I8085_IM: return I.IM;
1389 		case I8085_HALT: return I.HALT;
1390 		case I8085_IREQ: return I.IREQ;
1391 		case I8085_ISRV: return I.ISRV;
1392 		case I8085_VECTOR: return I.INTR;
1393 		case I8085_TRAP_STATE: return I.nmi_state;
1394 		case I8085_INTR_STATE: return I.irq_state[I8085_INTR_LINE];
1395 		case I8085_RST55_STATE: return I.irq_state[I8085_RST55_LINE];
1396 		case I8085_RST65_STATE: return I.irq_state[I8085_RST65_LINE];
1397 		case I8085_RST75_STATE: return I.irq_state[I8085_RST75_LINE];
1398 		case REG_PREVIOUSPC: return 0; /* previous pc not supported */
1399 		default:
1400 			if( regnum <= REG_SP_CONTENTS )
1401 			{
1402 				unsigned offset = I.SP.w.l + 2 * (REG_SP_CONTENTS - regnum);
1403 				if( offset < 0xffff )
1404 					return RM( offset ) + ( RM( offset+1 ) << 8 );
1405 			}
1406 	}
1407 	return 0;
1408 }
1409 
1410 /****************************************************************************
1411  * Set a specific register
1412  ****************************************************************************/
i8085_set_reg(int regnum,unsigned val)1413 void i8085_set_reg(int regnum, unsigned val)
1414 {
1415 	switch( regnum )
1416 	{
1417 		case REG_PC: I.PC.w.l = val; change_pc16(I.PC.d); break;
1418 		case I8085_PC: I.PC.w.l = val; break;
1419 		case REG_SP: I.SP.w.l = val; break;
1420 		case I8085_SP: I.SP.w.l = val; break;
1421 		case I8085_AF: I.AF.w.l = val; break;
1422 		case I8085_BC: I.BC.w.l = val; break;
1423 		case I8085_DE: I.DE.w.l = val; break;
1424 		case I8085_HL: I.HL.w.l = val; break;
1425 		case I8085_IM: I.IM = val; break;
1426 		case I8085_HALT: I.HALT = val; break;
1427 		case I8085_IREQ: I.IREQ = val; break;
1428 		case I8085_ISRV: I.ISRV = val; break;
1429 		case I8085_VECTOR: I.INTR = val; break;
1430 		case I8085_TRAP_STATE: I.nmi_state = val; break;
1431 		case I8085_INTR_STATE: I.irq_state[I8085_INTR_LINE] = val; break;
1432 		case I8085_RST55_STATE: I.irq_state[I8085_RST55_LINE] = val; break;
1433 		case I8085_RST65_STATE: I.irq_state[I8085_RST65_LINE] = val; break;
1434 		case I8085_RST75_STATE: I.irq_state[I8085_RST75_LINE] = val; break;
1435 		default:
1436 			if( regnum <= REG_SP_CONTENTS )
1437 			{
1438 				unsigned offset = I.SP.w.l + 2 * (REG_SP_CONTENTS - regnum);
1439 				if( offset < 0xffff )
1440 				{
1441 					WM( offset, val&0xff );
1442 					WM( offset+1, (val>>8)&0xff );
1443 				}
1444 			}
1445 	}
1446 }
1447 
1448 /****************************************************************************/
1449 /* Set the 8085 SID input signal state										*/
1450 /****************************************************************************/
i8085_set_SID(int state)1451 void i8085_set_SID(int state)
1452 {
1453 	LOG(("i8085: SID %d\n", state));
1454 	if (state)
1455 		I.IM |= IM_SID;
1456 	else
1457 		I.IM &= ~IM_SID;
1458 }
1459 
1460 /****************************************************************************/
1461 /* Set a callback to be called at SOD output change 						*/
1462 /****************************************************************************/
i8085_set_sod_callback(void (* callback)(int state))1463 void i8085_set_sod_callback(void (*callback)(int state))
1464 {
1465 	I.sod_callback = callback;
1466 }
1467 
1468 /****************************************************************************/
1469 /* Set TRAP signal state													*/
1470 /****************************************************************************/
i8085_set_TRAP(int state)1471 void i8085_set_TRAP(int state)
1472 {
1473 	LOG(("i8085: TRAP %d\n", state));
1474 	if (state)
1475 	{
1476 		I.IREQ |= IM_TRAP;
1477 		if( I.ISRV & IM_TRAP ) return;	/* already servicing TRAP ? */
1478 		I.ISRV = IM_TRAP;				/* service TRAP */
1479 		I.IRQ2 = ADDR_TRAP;
1480 	}
1481 	else
1482 	{
1483 		I.IREQ &= ~IM_TRAP; 			/* remove request for TRAP */
1484 	}
1485 }
1486 
1487 /****************************************************************************/
1488 /* Set RST7.5 signal state													*/
1489 /****************************************************************************/
i8085_set_RST75(int state)1490 void i8085_set_RST75(int state)
1491 {
1492 	LOG(("i8085: RST7.5 %d\n", state));
1493 	if( state )
1494 	{
1495 
1496 		I.IREQ |= IM_RST75; 			/* request RST7.5 */
1497 		if( I.IM & IM_RST75 ) return;	/* if masked, ignore it for now */
1498 		if( !I.ISRV )					/* if no higher priority IREQ is serviced */
1499 		{
1500 			I.ISRV = IM_RST75;			/* service RST7.5 */
1501 			I.IRQ2 = ADDR_RST75;
1502 		}
1503 	}
1504 	/* RST7.5 is reset only by SIM or end of service routine ! */
1505 }
1506 
1507 /****************************************************************************/
1508 /* Set RST6.5 signal state													*/
1509 /****************************************************************************/
i8085_set_RST65(int state)1510 void i8085_set_RST65(int state)
1511 {
1512 	LOG(("i8085: RST6.5 %d\n", state));
1513 	if( state )
1514 	{
1515 		I.IREQ |= IM_RST65; 			/* request RST6.5 */
1516 		if( I.IM & IM_RST65 ) return;	/* if masked, ignore it for now */
1517 		if( !I.ISRV )					/* if no higher priority IREQ is serviced */
1518 		{
1519 			I.ISRV = IM_RST65;			/* service RST6.5 */
1520 			I.IRQ2 = ADDR_RST65;
1521 		}
1522 	}
1523 	else
1524 	{
1525 		I.IREQ &= ~IM_RST65;			/* remove request for RST6.5 */
1526 	}
1527 }
1528 
1529 /****************************************************************************/
1530 /* Set RST5.5 signal state													*/
1531 /****************************************************************************/
i8085_set_RST55(int state)1532 void i8085_set_RST55(int state)
1533 {
1534 	LOG(("i8085: RST5.5 %d\n", state));
1535 	if( state )
1536 	{
1537 		I.IREQ |= IM_RST55; 			/* request RST5.5 */
1538 		if( I.IM & IM_RST55 ) return;	/* if masked, ignore it for now */
1539 		if( !I.ISRV )					/* if no higher priority IREQ is serviced */
1540 		{
1541 			I.ISRV = IM_RST55;			/* service RST5.5 */
1542 			I.IRQ2 = ADDR_RST55;
1543 		}
1544 	}
1545 	else
1546 	{
1547 		I.IREQ &= ~IM_RST55;			/* remove request for RST5.5 */
1548 	}
1549 }
1550 
1551 /****************************************************************************/
1552 /* Set INTR signal															*/
1553 /****************************************************************************/
i8085_set_INTR(int state)1554 void i8085_set_INTR(int state)
1555 {
1556 	LOG(("i8085: INTR %d\n", state));
1557 	if( state )
1558 	{
1559 		I.IREQ |= IM_INTR;				/* request INTR */
1560 		//I.INTR = state;
1561 		I.INTR = I8085_INTR; //AT: I.INTR is supposed to hold IRQ0 vector(0x38) (0xff in this implementation)
1562 		if( I.IM & IM_INTR ) return;	/* if masked, ignore it for now */
1563 		if( !I.ISRV )					/* if no higher priority IREQ is serviced */
1564 		{
1565 			I.ISRV = IM_INTR;			/* service INTR */
1566 			I.IRQ2 = I.INTR;
1567 		}
1568 	}
1569 	else
1570 	{
1571 		I.IREQ &= ~IM_INTR; 			/* remove request for INTR */
1572 	}
1573 }
1574 
i8085_set_irq_line(int irqline,int state)1575 void i8085_set_irq_line(int irqline, int state)
1576 {
1577 	if (irqline == IRQ_LINE_NMI)
1578 	{
1579 		I.nmi_state = state;
1580 		if( state != CLEAR_LINE )
1581 			i8085_set_TRAP(1);
1582 	}
1583 	else if (irqline < 4)
1584 	{
1585 		I.irq_state[irqline] = state;
1586 		if (state == CLEAR_LINE)
1587 		{
1588 			if( !(I.IM & IM_IEN) )
1589 			{
1590 				switch (irqline)
1591 				{
1592 					case I8085_INTR_LINE: i8085_set_INTR(0); break;
1593 					case I8085_RST55_LINE: i8085_set_RST55(0); break;
1594 					case I8085_RST65_LINE: i8085_set_RST65(0); break;
1595 					case I8085_RST75_LINE: i8085_set_RST75(0); break;
1596 				}
1597 			}
1598 		}
1599 		else
1600 		{
1601 			if( I.IM & IM_IEN )
1602 			{
1603 				switch( irqline )
1604 				{
1605 					case I8085_INTR_LINE: i8085_set_INTR(1); break;
1606 					case I8085_RST55_LINE: i8085_set_RST55(1); break;
1607 					case I8085_RST65_LINE: i8085_set_RST65(1); break;
1608 					case I8085_RST75_LINE: i8085_set_RST75(1); break;
1609 				}
1610 			}
1611 		}
1612 	}
1613 }
1614 
i8085_set_irq_callback(int (* callback)(int))1615 void i8085_set_irq_callback(int (*callback)(int))
1616 {
1617 	I.irq_callback = callback;
1618 }
1619 
1620 /****************************************************************************
1621  * Return a formatted string for a register
1622  ****************************************************************************/
i8085_info(void * context,int regnum)1623 const char *i8085_info(void *context, int regnum)
1624 {
1625 	static char buffer[16][47+1];
1626 	static int which = 0;
1627 	i8085_Regs *r = context;
1628 
1629 	which = (which+1) % 16;
1630 	buffer[which][0] = '\0';
1631 	if( !context )
1632 		r = &I;
1633 
1634 	switch( regnum )
1635 	{
1636 		case CPU_INFO_REG+I8085_AF: sprintf(buffer[which], "AF:%04X", r->AF.w.l); break;
1637 		case CPU_INFO_REG+I8085_BC: sprintf(buffer[which], "BC:%04X", r->BC.w.l); break;
1638 		case CPU_INFO_REG+I8085_DE: sprintf(buffer[which], "DE:%04X", r->DE.w.l); break;
1639 		case CPU_INFO_REG+I8085_HL: sprintf(buffer[which], "HL:%04X", r->HL.w.l); break;
1640 		case CPU_INFO_REG+I8085_SP: sprintf(buffer[which], "SP:%04X", r->SP.w.l); break;
1641 		case CPU_INFO_REG+I8085_PC: sprintf(buffer[which], "PC:%04X", r->PC.w.l); break;
1642 		case CPU_INFO_REG+I8085_IM: sprintf(buffer[which], "IM:%02X", r->IM); break;
1643 		case CPU_INFO_REG+I8085_HALT: sprintf(buffer[which], "HALT:%d", r->HALT); break;
1644 		case CPU_INFO_REG+I8085_IREQ: sprintf(buffer[which], "IREQ:%02X", I.IREQ); break;
1645 		case CPU_INFO_REG+I8085_ISRV: sprintf(buffer[which], "ISRV:%02X", I.ISRV); break;
1646 		case CPU_INFO_REG+I8085_VECTOR: sprintf(buffer[which], "VEC:%02X", I.INTR); break;
1647 		case CPU_INFO_REG+I8085_TRAP_STATE: sprintf(buffer[which], "TRAP:%X", I.nmi_state); break;
1648 		case CPU_INFO_REG+I8085_INTR_STATE: sprintf(buffer[which], "INTR:%X", I.irq_state[I8085_INTR_LINE]); break;
1649 		case CPU_INFO_REG+I8085_RST55_STATE: sprintf(buffer[which], "RST55:%X", I.irq_state[I8085_RST55_LINE]); break;
1650 		case CPU_INFO_REG+I8085_RST65_STATE: sprintf(buffer[which], "RST65:%X", I.irq_state[I8085_RST65_LINE]); break;
1651 		case CPU_INFO_REG+I8085_RST75_STATE: sprintf(buffer[which], "RST75:%X", I.irq_state[I8085_RST75_LINE]); break;
1652 		case CPU_INFO_FLAGS:
1653 			sprintf(buffer[which], "%c%c%c%c%c%c%c%c",
1654 				r->AF.b.l & 0x80 ? 'S':'.',
1655 				r->AF.b.l & 0x40 ? 'Z':'.',
1656 				r->AF.b.l & 0x20 ? '?':'.',
1657 				r->AF.b.l & 0x10 ? 'H':'.',
1658 				r->AF.b.l & 0x08 ? '?':'.',
1659 				r->AF.b.l & 0x04 ? 'P':'.',
1660 				r->AF.b.l & 0x02 ? 'N':'.',
1661 				r->AF.b.l & 0x01 ? 'C':'.');
1662 			break;
1663 		case CPU_INFO_NAME: return "8085A";
1664 		case CPU_INFO_FAMILY: return "Intel 8080";
1665 		case CPU_INFO_VERSION: return "1.1";
1666 		case CPU_INFO_FILE: return __FILE__;
1667 		case CPU_INFO_CREDITS: return "Copyright (c) 1999 Juergen Buchmueller, all rights reserved.";
1668 		case CPU_INFO_REG_LAYOUT: return (const char *)i8085_reg_layout;
1669 		case CPU_INFO_WIN_LAYOUT: return (const char *)i8085_win_layout;
1670 	}
1671 	return buffer[which];
1672 }
1673 
i8085_dasm(char * buffer,unsigned pc)1674 unsigned i8085_dasm(char *buffer, unsigned pc)
1675 {
1676 #ifdef MAME_DEBUG
1677 	return Dasm8085(buffer,pc);
1678 #else
1679 	sprintf( buffer, "$%02X", cpu_readop(pc) );
1680 	return 1;
1681 #endif
1682 }
1683 
1684 
1685 /**************************************************************************
1686  * 8080 section
1687  **************************************************************************/
1688 #if (HAS_8080)
1689 /* Layout of the registers in the debugger */
1690 static UINT8 i8080_reg_layout[] = {
1691 	I8080_AF, I8080_BC, I8080_DE, I8080_HL, I8080_SP, I8080_PC, -1,
1692 	I8080_HALT, I8080_IREQ, I8080_ISRV, I8080_VECTOR, I8080_TRAP_STATE, I8080_INTR_STATE,
1693 	0 };
1694 
1695 /* Layout of the debugger windows x,y,w,h */
1696 static UINT8 i8080_win_layout[] = {
1697 	25, 0,55, 2,	/* register window (top, right rows) */
1698 	 0, 0,24,22,	/* disassembler window (left colums) */
1699 	25, 3,55,10,	/* memory #1 window (right, upper middle) */
1700 	25,14,55, 8,	/* memory #2 window (right, lower middle) */
1701 	 0,23,80, 1,	/* command line window (bottom rows) */
1702 };
1703 
i8080_init(void)1704 void i8080_init(void)
1705 {
1706 	int cpu = cpu_getactivecpu();
1707 	init_tables();
1708 	I.cputype = 0;
1709 
1710 	state_save_register_UINT16("i8080", cpu, "AF", &I.AF.w.l, 1);
1711 	state_save_register_UINT16("i8080", cpu, "BC", &I.BC.w.l, 1);
1712 	state_save_register_UINT16("i8080", cpu, "DE", &I.DE.w.l, 1);
1713 	state_save_register_UINT16("i8080", cpu, "HL", &I.HL.w.l, 1);
1714 	state_save_register_UINT16("i8080", cpu, "SP", &I.SP.w.l, 1);
1715 	state_save_register_UINT16("i8080", cpu, "PC", &I.PC.w.l, 1);
1716 	state_save_register_UINT8("i8080", cpu, "HALT", &I.HALT, 1);
1717 	state_save_register_UINT8("i8080", cpu, "IREQ", &I.IREQ, 1);
1718 	state_save_register_UINT8("i8080", cpu, "ISRV", &I.ISRV, 1);
1719 	state_save_register_UINT32("i8080", cpu, "INTR", &I.INTR, 1);
1720 	state_save_register_UINT32("i8080", cpu, "IRQ2", &I.IRQ2, 1);
1721 	state_save_register_UINT32("i8080", cpu, "IRQ1", &I.IRQ1, 1);
1722 	state_save_register_INT8("i8080", cpu, "nmi_state", &I.nmi_state, 1);
1723 	state_save_register_INT8("i8080", cpu, "irq_state", I.irq_state, 1);
1724 }
1725 
i8080_reset(void * param)1726 void i8080_reset(void *param) { i8085_reset(param); }
i8080_exit(void)1727 void i8080_exit(void) { i8085_exit(); }
i8080_execute(int cycles)1728 int i8080_execute(int cycles) { return i8085_execute(cycles); }
i8080_get_context(void * dst)1729 unsigned i8080_get_context(void *dst) { return i8085_get_context(dst); }
i8080_set_context(void * src)1730 void i8080_set_context(void *src) { i8085_set_context(src); }
i8080_get_reg(int regnum)1731 unsigned i8080_get_reg(int regnum) { return i8085_get_reg(regnum); }
i8080_set_reg(int regnum,unsigned val)1732 void i8080_set_reg(int regnum, unsigned val)  { i8085_set_reg(regnum,val); }
i8080_set_irq_line(int irqline,int state)1733 void i8080_set_irq_line(int irqline, int state)
1734 {
1735 	if (irqline == IRQ_LINE_NMI)
1736 	{
1737 		i8085_set_irq_line(irqline, state);
1738 	}
1739 	else
1740 	{
1741 		I.irq_state[irqline] = state;
1742 		if (state == CLEAR_LINE)
1743 		{
1744 			if (!(I.IM & IM_IEN))
1745 				i8085_set_INTR(0);
1746 		}
1747 		else
1748 		{
1749 			if (I.IM & IM_IEN)
1750 				i8085_set_INTR(1);
1751 		}
1752 	}
1753 }
i8080_set_irq_callback(int (* callback)(int irqline))1754 void i8080_set_irq_callback(int (*callback)(int irqline)) { i8085_set_irq_callback(callback); }
i8080_info(void * context,int regnum)1755 const char *i8080_info(void *context, int regnum)
1756 {
1757 	switch( regnum )
1758 	{
1759 		case CPU_INFO_NAME: return "8080";
1760 		case CPU_INFO_VERSION: return "1.2";
1761 		case CPU_INFO_REG_LAYOUT: return (const char *)i8080_reg_layout;
1762 		case CPU_INFO_WIN_LAYOUT: return (const char *)i8080_win_layout;
1763 	}
1764 	return i8085_info(context,regnum);
1765 }
1766 
i8080_dasm(char * buffer,unsigned pc)1767 unsigned i8080_dasm(char *buffer, unsigned pc)
1768 {
1769 #ifdef MAME_DEBUG
1770 	return Dasm8085(buffer,pc);
1771 #else
1772 	sprintf( buffer, "$%02X", cpu_readop(pc) );
1773 	return 1;
1774 #endif
1775 }
1776 #endif
1777 
1778