blob: 575771c5e41227d6b7e85d38bf38918267e9c772 [file] [log] [blame]
Dave Chapmana8145842006-03-11 15:44:35 +00001/***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
9 *
10 * Pacbox - a Pacman Emulator for Rockbox
11 *
12 * Based on PIE - Pacman Instructional Emulator
13 *
14 * Copyright (c) 1997-2003,2004 Alessandro Scotti
15 * http://www.ascotti.org/
16 *
Daniel Stenberg2acc0ac2008-06-28 18:10:04 +000017 * This program is free software; you can redistribute it and/or
18 * modify it under the terms of the GNU General Public License
19 * as published by the Free Software Foundation; either version 2
20 * of the License, or (at your option) any later version.
Dave Chapmana8145842006-03-11 15:44:35 +000021 *
22 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
23 * KIND, either express or implied.
24 *
25 ****************************************************************************/
26
27#include "plugin.h"
28#include "hardware.h"
29#include "z80.h"
30#include "z80_internal.h"
31
32// Table with parity, sign and zero flags precomputed for each byte value
Dave Chapman31895332006-03-15 22:39:14 +000033unsigned char PSZ_[256] IDATA_ATTR = {
Dave Chapmana8145842006-03-11 15:44:35 +000034 Zero|Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
35 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
36 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
37 Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
38 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
39 Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
40 Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
41 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
42 Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
43 Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity,
44 Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity,
45 Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
46 Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity,
47 Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
48 Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
49 Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity
50};
51
52// Interrupt flags
53enum {
54 IFF1 = 0x40, // Interrupts enabled/disabled
55 IFF2 = 0x20, // Copy of IFF1 (used by non-maskable interrupts)
56 Halted = 0x10 // Internal use: signals that the CPU is halted
57};
58
59// Implements an opcode
60typedef void (OpcodeHandler)(void);
61
62typedef struct {
63 OpcodeHandler* handler;
64 unsigned cycles;
65} OpcodeInfo;
66
67// Implements an opcode for instructions that use the form (IX/IY + b)
68typedef void (OpcodeHandlerXY)( unsigned );
69
70typedef struct {
71 OpcodeHandlerXY* handler;
72 unsigned cycles;
73} OpcodeInfoXY;
74
75/** */
76void do_opcode_xy( OpcodeInfo * );
77
78/** */
79unsigned do_opcode_xycb( unsigned xy );
80
Dave Chapman31895332006-03-15 22:39:14 +000081unsigned iflags_ IBSS_ATTR; // Interrupt mode (bits 0 and 1) and flags
82unsigned cycles_ IBSS_ATTR; // Number of CPU cycles elapsed so far
Dave Chapmana8145842006-03-11 15:44:35 +000083
84
85// Registers
Dave Chapman31895332006-03-15 22:39:14 +000086unsigned char B IBSS_ATTR; //@- B register
87unsigned char C IBSS_ATTR; //@- C register
88unsigned char D IBSS_ATTR; //@- D register
89unsigned char E IBSS_ATTR; //@- E register
90unsigned char H IBSS_ATTR; //@- H register
91unsigned char L IBSS_ATTR; //@- L register
92unsigned char A IBSS_ATTR; //@- A register (accumulator)
93unsigned char F IBSS_ATTR; //@- Flags register
94unsigned char B1 IBSS_ATTR; //@- Alternate B register (B')
95unsigned char C1 IBSS_ATTR; //@- Alternate C register (C')
96unsigned char D1 IBSS_ATTR; //@- Alternate D register (D')
97unsigned char E1 IBSS_ATTR; //@- Alternate E register (E')
98unsigned char H1 IBSS_ATTR; //@- Alternate H register (H')
99unsigned char L1 IBSS_ATTR; //@- Alternate L register (L')
100unsigned char A1 IBSS_ATTR; //@- Alternate A register (A')
101unsigned char F1 IBSS_ATTR; //@- Alternate flags register (F')
102unsigned IX IBSS_ATTR; //@- Index register X
103unsigned IY IBSS_ATTR; //@- Index register Y
104unsigned PC IBSS_ATTR; //@- Program counter
105unsigned SP IBSS_ATTR; //@- Stack pointer
106unsigned char I IBSS_ATTR; //@- Interrupt register
107unsigned char R IBSS_ATTR; //@- Refresh register
Dave Chapmana8145842006-03-11 15:44:35 +0000108
109
110/** Returns the 16 bit register BC. */
111#define BC() (((unsigned)B << 8) | C)
112#define DE() (((unsigned)D << 8) | E)
113#define HL() (((unsigned)H << 8) | L)
114
115/**
116 Returns the number of Z80 CPU cycles elapsed so far.
117
118 The cycle count is reset to zero when reset() is called, or
119 it can be set to any value with setCycles(). It is updated after
120 a CPU instruction is executed, for example by calling step()
121 or interrupt().
122*/
123unsigned getCycles(void) {
124 return cycles_;
125}
126
127/** Sets the CPU cycle counter to the specified value. */
128void setCycles( unsigned value ) {
129 cycles_ = value;
130}
131
132/** Returns the current interrupt mode. */
133unsigned getInterruptMode(void) {
134 return iflags_ & 0x03;
135}
136
137/** Sets the interrupt mode to the specified value. */
138void setInterruptMode( unsigned mode );
139
140/** Returns non-zero if the CPU is halted, otherwise zero. */
141int isHalted(void) {
142 return iflags_ & Halted;
143}
144
145/*
146 Sets the interrupt mode to IM0, IM1 or IM2.
147*/
148void setInterruptMode( unsigned mode )
149{
150 if( mode <= 2 ) {
151 iflags_ = (iflags_ & ~0x03) | mode;
152 }
153}
154
155/*
156 Calls a subroutine at the specified address.
157*/
158void callSub( unsigned addr )
159{
160 SP -= 2;
161 writeWord( SP, PC ); // Save current program counter in the stack
162 PC = addr & 0xFFFF; // Jump to the specified address
163}
164
165/*
166 Decrements a byte value by one.
167 Note that this is different from subtracting one from the byte value,
168 because flags behave differently.
169*/
170static inline unsigned char decByte( unsigned char b )
171{
172 F = Subtraction | (F & Carry); // Preserve the carry flag
173 if( (b & 0x0F) == 0 ) F |= Halfcarry;
174 --b;
175 if( b == 0x7F ) F |= Overflow;
176 if( b & 0x80 ) F |= Sign;
177 if( b == 0 ) F |= Zero;
178
179 return b;
180}
181
182/*
183 Increments a byte value by one.
184 Note that this is different from adding one to the byte value,
185 because flags behave differently.
186*/
187static inline unsigned char incByte( unsigned char b )
188{
189 ++b;
190 F &= Carry; // Preserve the carry flag
191 if( ! (b & 0x0F) ) F |= Halfcarry;
192 if( b == 0x80 ) F |= Overflow;
193 if( b & 0x80 ) F |= Sign;
194 if( b == 0 ) F |= Zero;
195
196 return b;
197}
198
199/*
200 Reads one byte from port C, updating flags according to the rules of "IN r,(C)".
201*/
202static inline unsigned char inpReg(void)
203{
204 unsigned char r = readPort( C );
205
206 F = (F & Carry) | PSZ_[r];
207
208 return r;
209}
210
211/*
212 Performs a relative jump to the specified offset.
213*/
214static inline void relJump( unsigned char o )
215{
216 int offset = (int)((signed char)o);
217
218 PC = (unsigned)((int)PC + offset) & 0xFFFF;
219 cycles_++;
220}
221
222/*
223 Returns from a subroutine, popping the saved Program Counter from the stack.
224*/
225static inline void retFromSub(void)
226{
227 PC = readWord( SP );
228 SP += 2;
229}
230
231/*
232 Rotates left one byte thru the carry flag.
233*/
234static inline unsigned char rotateLeft( unsigned char op )
235{
236 unsigned char f = F;
237
238 F = 0;
239 if( op & 0x80 ) F |= Carry;
240 op <<= 1;
241 if( f & Carry ) op |= 0x01;
242 F |= PSZ_[op];
243
244 return op;
245}
246
247/*
248 Rotates left one byte copying the most significant bit (bit 7) in the carry flag.
249*/
250static inline unsigned char rotateLeftCarry( unsigned char op )
251{
252 F = 0;
253 if( op & 0x80 ) F |= Carry;
254 op = (op << 1) | (op >> 7);
255 F |= PSZ_[op];
256
257 return op;
258}
259
260/*
261 Rotates right one byte thru the carry flag.
262*/
263static inline unsigned char rotateRight( unsigned char op )
264{
265 unsigned char f = F;
266
267 F = 0;
268 if( op & 0x01 ) F |= Carry;
269 op >>= 1;
270 if( f & Carry ) op |= 0x80;
271 F |= PSZ_[op];
272
273 return op;
274}
275
276/*
277 Rotates right one byte copying the least significant bit (bit 0) in the carry flag.
278*/
279static inline unsigned char rotateRightCarry( unsigned char op )
280{
281 F = 0;
282 if( op & 0x01 ) F |= Carry;
283 op = (op >> 1) | (op << 7);
284 F |= PSZ_[op];
285
286 return op;
287}
288
289/*
290 Shifts left one byte.
291*/
292static inline unsigned char shiftLeft( unsigned char op )
293{
294 F = 0;
295 if( op & 0x80 ) F |= Carry;
296 op <<= 1;
297 F |= PSZ_[op];
298
299 return op;
300}
301
302/*
303 Shifts right one byte, preserving its sign (most significant bit).
304*/
305static inline unsigned char shiftRightArith( unsigned char op )
306{
307 F = 0;
308 if( op & 0x01 ) F |= Carry;
309 op = (op >> 1) | (op & 0x80);
310
311 F |= PSZ_[op];
312
313 return op;
314}
315
316/*
317 Shifts right one byte.
318*/
319static inline unsigned char shiftRightLogical( unsigned char op )
320{
321 F = 0;
322 if( op & 0x01 ) F |= Carry;
323 op >>= 1;
324
325 F |= PSZ_[op];
326
327 return op;
328}
329
330/*
331 Tests whether the specified bit of op is set.
332*/
333static inline void testBit( unsigned char bit, unsigned char op )
334{
335 // Flags for a bit test operation are:
336 // S, P: unknown
337 // Z: set if bit is zero, reset otherwise
338 // N: reset
339 // H: set
340 // C: unaffected
341 // However, it seems that parity is always set like Z, so we emulate that as well.
342 F = (F & (Carry | Sign)) | Halfcarry;
343
344 if( (op & (1 << bit)) == 0 ) {
345 // Bit is not set, so set the zero flag
346 F |= Zero | Parity;
347 }
348}
349
350/*
351 Adds the specified byte op to the accumulator, adding
352 carry.
353*/
354static inline void addByte( unsigned char op, unsigned char cf )
355{
356 unsigned x = A + op;
357
358 if( cf ) x++; // Add carry
359
360 F = 0;
361 if( !(x & 0xFF) ) F |= Zero;
362 if( x & 0x80 ) F |= Sign;
363 if( x >= 0x100 ) F |= Carry;
364
365 /*
366 Halfcarry is set on carry from the low order four bits.
367
368 To see how to compute it, let's take a look at the following table, which
369 shows the binary addition of two binary numbers:
370
371 A B A+B
372 -----------
373 0 0 0
374 0 1 1
375 1 0 1
376 1 1 0
377
378 Note that if only the lowest bit is used, then A+B, A-B and A^B yield the same
379 value. If we know A, B and the sum A+B+C, then C is easily derived:
380 C = A+B+C - A - B, that is
381 C = A+B+C ^ A ^ B.
382
383 For the halfcarry, A and B above are the fifth bit of a byte, which corresponds
384 to the value 0x10. So:
385
386 Halfcarry = ((accumulator+operand+halfcarry) ^ accumulator ^ operand) & 0x10
387
388 Note that masking off all bits but one is important because we have worked all
389 the math by using one bit only.
390 */
391 if( (A ^ op ^ x) & 0x10 ) F |= Halfcarry;
392
393 /*
394 The overflow bit is set when the result is too large to fit into the destination
395 register, causing a change in the sign bit.
396
397 For a sum, we can only have overflow when adding two numbers that are both positive
398 or both negative. For example 0x5E + 0x4B (94 + 75) yields 0xA9 (169), which fits
399 into an 8-bit register only if it is interpreted as an unsigned number. If we
400 consider the result as a signed integer, then 0xA9 corresponds to decimal -87 and
401 we have overflow.
402 Note that if we add two signed numbers of opposite sign then we cannot overflow
403 the destination register, because the absolute value of the result will always fit
404 in 7 bits, leaving the most significant bit free for use as a sign bit.
405
406 We can code all the above concisely by noting that:
407
408 ~(A ^ op) & 0x80
409
410 is true if and only if A and op have the same sign. Also:
411
412 (x ^ op) & 0x80
413
414 is true if and only if the sum of A and op has taken a sign opposite to that
415 of its operands.
416
417 Thus the expression:
418
419 ~(A ^ op) & (x ^ op) & 0x80
420
421 reads "A has the same sign as op, and the opposite as x", where x is the sum of
422 A and op (and an optional carry).
423 */
424 if( ~(A ^ op) & (x ^ op) & 0x80 ) F |= Overflow;
425
426 A = x;
427}
428
429/*
430 Subtracts the specified byte op from the accumulator, using carry as
431 borrow from a previous operation.
432*/
433static inline unsigned char subByte( unsigned char op, unsigned char cf )
434{
435 unsigned char x = A - op;
436
437 if( cf ) x--;
438
439 F = Subtraction;
440 if( x == 0 ) F |= Zero;
441 if( x & 0x80 ) F |= Sign;
442 if( (x >= A) && (op | cf)) F |= Carry;
443
444 // See addByte() for an explanation of the halfcarry bit
445 if( (A ^ op ^ x) & 0x10 ) F |= Halfcarry;
446
447 // See addByte() for an explanation of the overflow bit. The only difference here
448 // is that for a subtraction we must check that the two operands have different
449 // sign, because in fact A-B is A+(-B). Note however that since subtraction is not
450 // symmetric, we have to use (x ^ A) to get the correct result, whereas for the
451 // addition (x ^ A) is equivalent to (x ^ op)
452 if( (A ^ op) & (x ^ A) & 0x80 ) F |= Overflow;
453
454 return x;
455}
456
457static inline unsigned addDispl( unsigned addr, unsigned char displ ) {
458 return (unsigned)((int)addr + (int)(signed char)displ);
459}
460
461/** Compares the accumulator and the specified operand (CP op) */
462static inline void cmpByte( unsigned char op ) {
463 subByte( op, 0 );
464}
465
466/** Fetches a byte from the program counter location */
467static inline unsigned char fetchByte(void) {
468 return readByte( PC++ );
469}
470
471/** Fetches a 16 bit word from the program counter location */
472static inline unsigned fetchWord(void) {
473 unsigned x = readWord( PC );
474 PC += 2;
475 return x;
476}
477
478/** Sets the parity, sign and zero flags from the accumulator value */
479static inline void setFlagsPSZ(void) {
480 F = Halfcarry | PSZ_[A];
481}
482
483/** Sets the parity, sign, zero, 3rd and 5th flag bits from the accumulator value */
484static inline void setFlags35PSZ(void) {
485 F = (F & (Carry | Halfcarry | Subtraction)) | PSZ_[A];
486}
487
488/** */
489static inline void setFlags35PSZ000(void) {
490 F = PSZ_[A];
491}
492
493/* Resets the CPU */
494void z80_reset()
495{
496 PC = 0; // Program counter is zero
497 I = 0; // Interrupt register cleared
498 R = 0; // Memory refresh register cleared
499 iflags_ = 0; // IFF1 and IFF2 cleared, IM0 enabled
500 cycles_ = 0; // Could that be 2 (according to some Zilog docs)?
501
502 // There is no official documentation for the following!
503 B = B1 = 0;
504 C = C1 = 0;
505 D = D1 = 0;
506 E = E1 = 0;
507 H = H1 = 0;
508 L = L1 = 0;
509 A = A1 = 0;
510 F = F1 = 0;
511 IX = 0;
512 IY = 0;
513 SP = 0xF000;
514}
515
516unsigned z80_getSizeOfSnapshotBuffer(void)
517{
518 unsigned result =
519 8*2 + // 8-bit registers
520 1 + // I
521 1 + // R
522 2 + // IX
523 2 + // IY
524 2 + // PC
525 2 + // SP
526 4 + // iflags_
527 4; // cycles_
528
529 return result;
530}
531
532static unsigned saveUint16( unsigned char * buffer, unsigned u )
533{
534 *buffer++ = (unsigned char) (u >> 8);
535 *buffer = (unsigned char) (u);
536
537 return 2;
538}
539
540unsigned z80_takeSnapshot( unsigned char * buffer )
541{
542 unsigned char * buf = buffer;
543
544 *buf++ = A; *buf++ = A1;
545 *buf++ = B; *buf++ = B1;
546 *buf++ = C; *buf++ = C1;
547 *buf++ = D; *buf++ = D1;
548 *buf++ = E; *buf++ = E1;
549 *buf++ = H; *buf++ = H1;
550 *buf++ = L; *buf++ = L1;
551 *buf++ = F; *buf++ = F1;
552
553 *buf++ = I;
554 *buf++ = R;
555
556 buf += saveUint16( buf, IX );
557 buf += saveUint16( buf, IY );
558 buf += saveUint16( buf, PC );
559 buf += saveUint16( buf, SP );
560
561 buf += saveUint16( buf, iflags_ >> 16 );
562 buf += saveUint16( buf, iflags_ );
563 buf += saveUint16( buf, cycles_ >> 16 );
564 buf += saveUint16( buf, cycles_ );
565
566 return buffer - buf;
567}
568
569static unsigned loadUint16( unsigned char ** buffer )
570{
571 unsigned char * buf = *buffer;
572 unsigned result = *buf++;
573
574 result = (result << 8) | *buf++;
575
576 *buffer = buf;
577
578 return result;
579}
580
581unsigned z80_restoreSnapshot( unsigned char * buffer )
582{
583 unsigned char * buf = buffer;
584
585 A = *buf++; A1 = *buf++;
586 B = *buf++; B1 = *buf++;
587 C = *buf++; C1 = *buf++;
588 D = *buf++; D1 = *buf++;
589 E = *buf++; E1 = *buf++;
590 H = *buf++; H1 = *buf++;
591 L = *buf++; L1 = *buf++;
592 F = *buf++; F1 = *buf++;
593
594 I = *buf++;
595 R = *buf++;
596
597 IX = loadUint16( &buf );
598 IY = loadUint16( &buf );
599 PC = loadUint16( &buf );
600 SP = loadUint16( &buf );
601
602 iflags_ = loadUint16( &buf );
603 iflags_ = (iflags_ << 16) | loadUint16(&buf);
604 cycles_ = loadUint16( &buf );
605 cycles_ = (cycles_ << 16) | loadUint16(&buf);
606
607 return buf - buffer;
608}
609
610OpcodeInfo OpInfoCB_[256] = {
611 { &opcode_cb_00, 8 }, // RLC B
612 { &opcode_cb_01, 8 }, // RLC C
613 { &opcode_cb_02, 8 }, // RLC D
614 { &opcode_cb_03, 8 }, // RLC E
615 { &opcode_cb_04, 8 }, // RLC H
616 { &opcode_cb_05, 8 }, // RLC L
617 { &opcode_cb_06, 15 }, // RLC (HL)
618 { &opcode_cb_07, 8 }, // RLC A
619 { &opcode_cb_08, 8 }, // RRC B
620 { &opcode_cb_09, 8 }, // RRC C
621 { &opcode_cb_0a, 8 }, // RRC D
622 { &opcode_cb_0b, 8 }, // RRC E
623 { &opcode_cb_0c, 8 }, // RRC H
624 { &opcode_cb_0d, 8 }, // RRC L
625 { &opcode_cb_0e, 15 }, // RRC (HL)
626 { &opcode_cb_0f, 8 }, // RRC A
627 { &opcode_cb_10, 8 }, // RL B
628 { &opcode_cb_11, 8 }, // RL C
629 { &opcode_cb_12, 8 }, // RL D
630 { &opcode_cb_13, 8 }, // RL E
631 { &opcode_cb_14, 8 }, // RL H
632 { &opcode_cb_15, 8 }, // RL L
633 { &opcode_cb_16, 15 }, // RL (HL)
634 { &opcode_cb_17, 8 }, // RL A
635 { &opcode_cb_18, 8 }, // RR B
636 { &opcode_cb_19, 8 }, // RR C
637 { &opcode_cb_1a, 8 }, // RR D
638 { &opcode_cb_1b, 8 }, // RR E
639 { &opcode_cb_1c, 8 }, // RR H
640 { &opcode_cb_1d, 8 }, // RR L
641 { &opcode_cb_1e, 15 }, // RR (HL)
642 { &opcode_cb_1f, 8 }, // RR A
643 { &opcode_cb_20, 8 }, // SLA B
644 { &opcode_cb_21, 8 }, // SLA C
645 { &opcode_cb_22, 8 }, // SLA D
646 { &opcode_cb_23, 8 }, // SLA E
647 { &opcode_cb_24, 8 }, // SLA H
648 { &opcode_cb_25, 8 }, // SLA L
649 { &opcode_cb_26, 15 }, // SLA (HL)
650 { &opcode_cb_27, 8 }, // SLA A
651 { &opcode_cb_28, 8 }, // SRA B
652 { &opcode_cb_29, 8 }, // SRA C
653 { &opcode_cb_2a, 8 }, // SRA D
654 { &opcode_cb_2b, 8 }, // SRA E
655 { &opcode_cb_2c, 8 }, // SRA H
656 { &opcode_cb_2d, 8 }, // SRA L
657 { &opcode_cb_2e, 15 }, // SRA (HL)
658 { &opcode_cb_2f, 8 }, // SRA A
659 { &opcode_cb_30, 8 }, // SLL B
660 { &opcode_cb_31, 8 }, // SLL C
661 { &opcode_cb_32, 8 }, // SLL D
662 { &opcode_cb_33, 8 }, // SLL E
663 { &opcode_cb_34, 8 }, // SLL H
664 { &opcode_cb_35, 8 }, // SLL L
665 { &opcode_cb_36, 15 }, // SLL (HL)
666 { &opcode_cb_37, 8 }, // SLL A
667 { &opcode_cb_38, 8 }, // SRL B
668 { &opcode_cb_39, 8 }, // SRL C
669 { &opcode_cb_3a, 8 }, // SRL D
670 { &opcode_cb_3b, 8 }, // SRL E
671 { &opcode_cb_3c, 8 }, // SRL H
672 { &opcode_cb_3d, 8 }, // SRL L
673 { &opcode_cb_3e, 15 }, // SRL (HL)
674 { &opcode_cb_3f, 8 }, // SRL A
675 { &opcode_cb_40, 8 }, // BIT 0, B
676 { &opcode_cb_41, 8 }, // BIT 0, C
677 { &opcode_cb_42, 8 }, // BIT 0, D
678 { &opcode_cb_43, 8 }, // BIT 0, E
679 { &opcode_cb_44, 8 }, // BIT 0, H
680 { &opcode_cb_45, 8 }, // BIT 0, L
681 { &opcode_cb_46, 12 }, // BIT 0, (HL)
682 { &opcode_cb_47, 8 }, // BIT 0, A
683 { &opcode_cb_48, 8 }, // BIT 1, B
684 { &opcode_cb_49, 8 }, // BIT 1, C
685 { &opcode_cb_4a, 8 }, // BIT 1, D
686 { &opcode_cb_4b, 8 }, // BIT 1, E
687 { &opcode_cb_4c, 8 }, // BIT 1, H
688 { &opcode_cb_4d, 8 }, // BIT 1, L
689 { &opcode_cb_4e, 12 }, // BIT 1, (HL)
690 { &opcode_cb_4f, 8 }, // BIT 1, A
691 { &opcode_cb_50, 8 }, // BIT 2, B
692 { &opcode_cb_51, 8 }, // BIT 2, C
693 { &opcode_cb_52, 8 }, // BIT 2, D
694 { &opcode_cb_53, 8 }, // BIT 2, E
695 { &opcode_cb_54, 8 }, // BIT 2, H
696 { &opcode_cb_55, 8 }, // BIT 2, L
697 { &opcode_cb_56, 12 }, // BIT 2, (HL)
698 { &opcode_cb_57, 8 }, // BIT 2, A
699 { &opcode_cb_58, 8 }, // BIT 3, B
700 { &opcode_cb_59, 8 }, // BIT 3, C
701 { &opcode_cb_5a, 8 }, // BIT 3, D
702 { &opcode_cb_5b, 8 }, // BIT 3, E
703 { &opcode_cb_5c, 8 }, // BIT 3, H
704 { &opcode_cb_5d, 8 }, // BIT 3, L
705 { &opcode_cb_5e, 12 }, // BIT 3, (HL)
706 { &opcode_cb_5f, 8 }, // BIT 3, A
707 { &opcode_cb_60, 8 }, // BIT 4, B
708 { &opcode_cb_61, 8 }, // BIT 4, C
709 { &opcode_cb_62, 8 }, // BIT 4, D
710 { &opcode_cb_63, 8 }, // BIT 4, E
711 { &opcode_cb_64, 8 }, // BIT 4, H
712 { &opcode_cb_65, 8 }, // BIT 4, L
713 { &opcode_cb_66, 12 }, // BIT 4, (HL)
714 { &opcode_cb_67, 8 }, // BIT 4, A
715 { &opcode_cb_68, 8 }, // BIT 5, B
716 { &opcode_cb_69, 8 }, // BIT 5, C
717 { &opcode_cb_6a, 8 }, // BIT 5, D
718 { &opcode_cb_6b, 8 }, // BIT 5, E
719 { &opcode_cb_6c, 8 }, // BIT 5, H
720 { &opcode_cb_6d, 8 }, // BIT 5, L
721 { &opcode_cb_6e, 12 }, // BIT 5, (HL)
722 { &opcode_cb_6f, 8 }, // BIT 5, A
723 { &opcode_cb_70, 8 }, // BIT 6, B
724 { &opcode_cb_71, 8 }, // BIT 6, C
725 { &opcode_cb_72, 8 }, // BIT 6, D
726 { &opcode_cb_73, 8 }, // BIT 6, E
727 { &opcode_cb_74, 8 }, // BIT 6, H
728 { &opcode_cb_75, 8 }, // BIT 6, L
729 { &opcode_cb_76, 12 }, // BIT 6, (HL)
730 { &opcode_cb_77, 8 }, // BIT 6, A
731 { &opcode_cb_78, 8 }, // BIT 7, B
732 { &opcode_cb_79, 8 }, // BIT 7, C
733 { &opcode_cb_7a, 8 }, // BIT 7, D
734 { &opcode_cb_7b, 8 }, // BIT 7, E
735 { &opcode_cb_7c, 8 }, // BIT 7, H
736 { &opcode_cb_7d, 8 }, // BIT 7, L
737 { &opcode_cb_7e, 12 }, // BIT 7, (HL)
738 { &opcode_cb_7f, 8 }, // BIT 7, A
739 { &opcode_cb_80, 8 }, // RES 0, B
740 { &opcode_cb_81, 8 }, // RES 0, C
741 { &opcode_cb_82, 8 }, // RES 0, D
742 { &opcode_cb_83, 8 }, // RES 0, E
743 { &opcode_cb_84, 8 }, // RES 0, H
744 { &opcode_cb_85, 8 }, // RES 0, L
745 { &opcode_cb_86, 15 }, // RES 0, (HL)
746 { &opcode_cb_87, 8 }, // RES 0, A
747 { &opcode_cb_88, 8 }, // RES 1, B
748 { &opcode_cb_89, 8 }, // RES 1, C
749 { &opcode_cb_8a, 8 }, // RES 1, D
750 { &opcode_cb_8b, 8 }, // RES 1, E
751 { &opcode_cb_8c, 8 }, // RES 1, H
752 { &opcode_cb_8d, 8 }, // RES 1, L
753 { &opcode_cb_8e, 15 }, // RES 1, (HL)
754 { &opcode_cb_8f, 8 }, // RES 1, A
755 { &opcode_cb_90, 8 }, // RES 2, B
756 { &opcode_cb_91, 8 }, // RES 2, C
757 { &opcode_cb_92, 8 }, // RES 2, D
758 { &opcode_cb_93, 8 }, // RES 2, E
759 { &opcode_cb_94, 8 }, // RES 2, H
760 { &opcode_cb_95, 8 }, // RES 2, L
761 { &opcode_cb_96, 15 }, // RES 2, (HL)
762 { &opcode_cb_97, 8 }, // RES 2, A
763 { &opcode_cb_98, 8 }, // RES 3, B
764 { &opcode_cb_99, 8 }, // RES 3, C
765 { &opcode_cb_9a, 8 }, // RES 3, D
766 { &opcode_cb_9b, 8 }, // RES 3, E
767 { &opcode_cb_9c, 8 }, // RES 3, H
768 { &opcode_cb_9d, 8 }, // RES 3, L
769 { &opcode_cb_9e, 15 }, // RES 3, (HL)
770 { &opcode_cb_9f, 8 }, // RES 3, A
771 { &opcode_cb_a0, 8 }, // RES 4, B
772 { &opcode_cb_a1, 8 }, // RES 4, C
773 { &opcode_cb_a2, 8 }, // RES 4, D
774 { &opcode_cb_a3, 8 }, // RES 4, E
775 { &opcode_cb_a4, 8 }, // RES 4, H
776 { &opcode_cb_a5, 8 }, // RES 4, L
777 { &opcode_cb_a6, 15 }, // RES 4, (HL)
778 { &opcode_cb_a7, 8 }, // RES 4, A
779 { &opcode_cb_a8, 8 }, // RES 5, B
780 { &opcode_cb_a9, 8 }, // RES 5, C
781 { &opcode_cb_aa, 8 }, // RES 5, D
782 { &opcode_cb_ab, 8 }, // RES 5, E
783 { &opcode_cb_ac, 8 }, // RES 5, H
784 { &opcode_cb_ad, 8 }, // RES 5, L
785 { &opcode_cb_ae, 15 }, // RES 5, (HL)
786 { &opcode_cb_af, 8 }, // RES 5, A
787 { &opcode_cb_b0, 8 }, // RES 6, B
788 { &opcode_cb_b1, 8 }, // RES 6, C
789 { &opcode_cb_b2, 8 }, // RES 6, D
790 { &opcode_cb_b3, 8 }, // RES 6, E
791 { &opcode_cb_b4, 8 }, // RES 6, H
792 { &opcode_cb_b5, 8 }, // RES 6, L
793 { &opcode_cb_b6, 15 }, // RES 6, (HL)
794 { &opcode_cb_b7, 8 }, // RES 6, A
795 { &opcode_cb_b8, 8 }, // RES 7, B
796 { &opcode_cb_b9, 8 }, // RES 7, C
797 { &opcode_cb_ba, 8 }, // RES 7, D
798 { &opcode_cb_bb, 8 }, // RES 7, E
799 { &opcode_cb_bc, 8 }, // RES 7, H
800 { &opcode_cb_bd, 8 }, // RES 7, L
801 { &opcode_cb_be, 15 }, // RES 7, (HL)
802 { &opcode_cb_bf, 8 }, // RES 7, A
803 { &opcode_cb_c0, 8 }, // SET 0, B
804 { &opcode_cb_c1, 8 }, // SET 0, C
805 { &opcode_cb_c2, 8 }, // SET 0, D
806 { &opcode_cb_c3, 8 }, // SET 0, E
807 { &opcode_cb_c4, 8 }, // SET 0, H
808 { &opcode_cb_c5, 8 }, // SET 0, L
809 { &opcode_cb_c6, 15 }, // SET 0, (HL)
810 { &opcode_cb_c7, 8 }, // SET 0, A
811 { &opcode_cb_c8, 8 }, // SET 1, B
812 { &opcode_cb_c9, 8 }, // SET 1, C
813 { &opcode_cb_ca, 8 }, // SET 1, D
814 { &opcode_cb_cb, 8 }, // SET 1, E
815 { &opcode_cb_cc, 8 }, // SET 1, H
816 { &opcode_cb_cd, 8 }, // SET 1, L
817 { &opcode_cb_ce, 15 }, // SET 1, (HL)
818 { &opcode_cb_cf, 8 }, // SET 1, A
819 { &opcode_cb_d0, 8 }, // SET 2, B
820 { &opcode_cb_d1, 8 }, // SET 2, C
821 { &opcode_cb_d2, 8 }, // SET 2, D
822 { &opcode_cb_d3, 8 }, // SET 2, E
823 { &opcode_cb_d4, 8 }, // SET 2, H
824 { &opcode_cb_d5, 8 }, // SET 2, L
825 { &opcode_cb_d6, 15 }, // SET 2, (HL)
826 { &opcode_cb_d7, 8 }, // SET 2, A
827 { &opcode_cb_d8, 8 }, // SET 3, B
828 { &opcode_cb_d9, 8 }, // SET 3, C
829 { &opcode_cb_da, 8 }, // SET 3, D
830 { &opcode_cb_db, 8 }, // SET 3, E
831 { &opcode_cb_dc, 8 }, // SET 3, H
832 { &opcode_cb_dd, 8 }, // SET 3, L
833 { &opcode_cb_de, 15 }, // SET 3, (HL)
834 { &opcode_cb_df, 8 }, // SET 3, A
835 { &opcode_cb_e0, 8 }, // SET 4, B
836 { &opcode_cb_e1, 8 }, // SET 4, C
837 { &opcode_cb_e2, 8 }, // SET 4, D
838 { &opcode_cb_e3, 8 }, // SET 4, E
839 { &opcode_cb_e4, 8 }, // SET 4, H
840 { &opcode_cb_e5, 8 }, // SET 4, L
841 { &opcode_cb_e6, 15 }, // SET 4, (HL)
842 { &opcode_cb_e7, 8 }, // SET 4, A
843 { &opcode_cb_e8, 8 }, // SET 5, B
844 { &opcode_cb_e9, 8 }, // SET 5, C
845 { &opcode_cb_ea, 8 }, // SET 5, D
846 { &opcode_cb_eb, 8 }, // SET 5, E
847 { &opcode_cb_ec, 8 }, // SET 5, H
848 { &opcode_cb_ed, 8 }, // SET 5, L
849 { &opcode_cb_ee, 15 }, // SET 5, (HL)
850 { &opcode_cb_ef, 8 }, // SET 5, A
851 { &opcode_cb_f0, 8 }, // SET 6, B
852 { &opcode_cb_f1, 8 }, // SET 6, C
853 { &opcode_cb_f2, 8 }, // SET 6, D
854 { &opcode_cb_f3, 8 }, // SET 6, E
855 { &opcode_cb_f4, 8 }, // SET 6, H
856 { &opcode_cb_f5, 8 }, // SET 6, L
857 { &opcode_cb_f6, 15 }, // SET 6, (HL)
858 { &opcode_cb_f7, 8 }, // SET 6, A
859 { &opcode_cb_f8, 8 }, // SET 7, B
860 { &opcode_cb_f9, 8 }, // SET 7, C
861 { &opcode_cb_fa, 8 }, // SET 7, D
862 { &opcode_cb_fb, 8 }, // SET 7, E
863 { &opcode_cb_fc, 8 }, // SET 7, H
864 { &opcode_cb_fd, 8 }, // SET 7, L
865 { &opcode_cb_fe, 15 }, // SET 7, (HL)
866 { &opcode_cb_ff, 8 } // SET 7, A
867};
868
869void opcode_cb_00() // RLC B
870{
871 B = rotateLeftCarry( B );
872}
873
874void opcode_cb_01() // RLC C
875{
876 C = rotateLeftCarry( C );
877}
878
879void opcode_cb_02() // RLC D
880{
881 D = rotateLeftCarry( D );
882}
883
884void opcode_cb_03() // RLC E
885{
886 E = rotateLeftCarry( E );
887}
888
889void opcode_cb_04() // RLC H
890{
891 H = rotateLeftCarry( H );
892}
893
894void opcode_cb_05() // RLC L
895{
896 L = rotateLeftCarry( L );
897}
898
899void opcode_cb_06() // RLC (HL)
900{
901 writeByte( HL(), rotateLeftCarry( readByte( HL() ) ) );
902}
903
904void opcode_cb_07() // RLC A
905{
906 A = rotateLeftCarry( A );
907}
908
909void opcode_cb_08() // RRC B
910{
911 B = rotateRightCarry( B );
912}
913
914void opcode_cb_09() // RRC C
915{
916 C = rotateLeftCarry( C );
917}
918
919void opcode_cb_0a() // RRC D
920{
921 D = rotateLeftCarry( D );
922}
923
924void opcode_cb_0b() // RRC E
925{
926 E = rotateLeftCarry( E );
927}
928
929void opcode_cb_0c() // RRC H
930{
931 H = rotateLeftCarry( H );
932}
933
934void opcode_cb_0d() // RRC L
935{
936 L = rotateLeftCarry( L );
937}
938
939void opcode_cb_0e() // RRC (HL)
940{
941 writeByte( HL(), rotateRightCarry( readByte( HL() ) ) );
942}
943
944void opcode_cb_0f() // RRC A
945{
946 A = rotateLeftCarry( A );
947}
948
949void opcode_cb_10() // RL B
950{
951 B = rotateLeft( B );
952}
953
954void opcode_cb_11() // RL C
955{
956 C = rotateLeft( C );
957}
958
959void opcode_cb_12() // RL D
960{
961 D = rotateLeft( D );
962}
963
964void opcode_cb_13() // RL E
965{
966 E = rotateLeft( E );
967}
968
969void opcode_cb_14() // RL H
970{
971 H = rotateLeft( H );
972}
973
974void opcode_cb_15() // RL L
975{
976 L = rotateLeft( L );
977}
978
979void opcode_cb_16() // RL (HL)
980{
981 writeByte( HL(), rotateLeft( readByte( HL() ) ) );
982}
983
984void opcode_cb_17() // RL A
985{
986 A = rotateLeft( A );
987}
988
989void opcode_cb_18() // RR B
990{
991 B = rotateRight( B );
992}
993
994void opcode_cb_19() // RR C
995{
996 C = rotateRight( C );
997}
998
999void opcode_cb_1a() // RR D
1000{
1001 D = rotateRight( D );
1002}
1003
1004void opcode_cb_1b() // RR E
1005{
1006 E = rotateRight( E );
1007}
1008
1009void opcode_cb_1c() // RR H
1010{
1011 H = rotateRight( H );
1012}
1013
1014void opcode_cb_1d() // RR L
1015{
1016 L = rotateRight( L );
1017}
1018
1019void opcode_cb_1e() // RR (HL)
1020{
1021 writeByte( HL(), rotateRight( readByte( HL() ) ) );
1022}
1023
1024void opcode_cb_1f() // RR A
1025{
1026 A = rotateRight( A );
1027}
1028
1029void opcode_cb_20() // SLA B
1030{
1031 B = shiftLeft( B );
1032}
1033
1034void opcode_cb_21() // SLA C
1035{
1036 C = shiftLeft( C );
1037}
1038
1039void opcode_cb_22() // SLA D
1040{
1041 D = shiftLeft( D );
1042}
1043
1044void opcode_cb_23() // SLA E
1045{
1046 E = shiftLeft( E );
1047}
1048
1049void opcode_cb_24() // SLA H
1050{
1051 H = shiftLeft( H );
1052}
1053
1054void opcode_cb_25() // SLA L
1055{
1056 L = shiftLeft( L );
1057}
1058
1059void opcode_cb_26() // SLA (HL)
1060{
1061 writeByte( HL(), shiftLeft( readByte( HL() ) ) );
1062}
1063
1064void opcode_cb_27() // SLA A
1065{
1066 A = shiftLeft( A );
1067}
1068
1069void opcode_cb_28() // SRA B
1070{
1071 B = shiftRightArith( B );
1072}
1073
1074void opcode_cb_29() // SRA C
1075{
1076 C = shiftRightArith( C );
1077}
1078
1079void opcode_cb_2a() // SRA D
1080{
1081 D = shiftRightArith( D );
1082}
1083
1084void opcode_cb_2b() // SRA E
1085{
1086 E = shiftRightArith( E );
1087}
1088
1089void opcode_cb_2c() // SRA H
1090{
1091 H = shiftRightArith( H );
1092}
1093
1094void opcode_cb_2d() // SRA L
1095{
1096 L = shiftRightArith( L );
1097}
1098
1099void opcode_cb_2e() // SRA (HL)
1100{
1101 writeByte( HL(), shiftRightArith( readByte( HL() ) ) );
1102}
1103
1104void opcode_cb_2f() // SRA A
1105{
1106 A = shiftRightArith( A );
1107}
1108
1109void opcode_cb_30() // SLL B
1110{
1111 B = shiftLeft( B ) | 0x01;
1112}
1113
1114void opcode_cb_31() // SLL C
1115{
1116 C = shiftLeft( C ) | 0x01;
1117}
1118
1119void opcode_cb_32() // SLL D
1120{
1121 D = shiftLeft( D ) | 0x01;
1122}
1123
1124void opcode_cb_33() // SLL E
1125{
1126 E = shiftLeft( E ) | 0x01;
1127}
1128
1129void opcode_cb_34() // SLL H
1130{
1131 H = shiftLeft( H ) | 0x01;
1132}
1133
1134void opcode_cb_35() // SLL L
1135{
1136 L = shiftLeft( L ) | 0x01;
1137}
1138
1139void opcode_cb_36() // SLL (HL)
1140{
1141 writeByte( HL(), shiftLeft( readByte( HL() ) ) | 0x01 );
1142}
1143
1144void opcode_cb_37() // SLL A
1145{
1146 A = shiftLeft( A ) | 0x01;
1147}
1148
1149void opcode_cb_38() // SRL B
1150{
1151 B = shiftRightLogical( B );
1152}
1153
1154void opcode_cb_39() // SRL C
1155{
1156 C = shiftRightLogical( C );
1157}
1158
1159void opcode_cb_3a() // SRL D
1160{
1161 D = shiftRightLogical( D );
1162}
1163
1164void opcode_cb_3b() // SRL E
1165{
1166 E = shiftRightLogical( E );
1167}
1168
1169void opcode_cb_3c() // SRL H
1170{
1171 H = shiftRightLogical( H );
1172}
1173
1174void opcode_cb_3d() // SRL L
1175{
1176 L = shiftRightLogical( L );
1177}
1178
1179void opcode_cb_3e() // SRL (HL)
1180{
1181 writeByte( HL(), shiftRightLogical( readByte( HL() ) ) );
1182}
1183
1184void opcode_cb_3f() // SRL A
1185{
1186 A = shiftRightLogical( A );
1187}
1188
1189void opcode_cb_40() // BIT 0, B
1190{
1191 testBit( 0, B );
1192}
1193
1194void opcode_cb_41() // BIT 0, C
1195{
1196 testBit( 0, C );
1197}
1198
1199void opcode_cb_42() // BIT 0, D
1200{
1201 testBit( 0, D );
1202}
1203
1204void opcode_cb_43() // BIT 0, E
1205{
1206 testBit( 0, E );
1207}
1208
1209void opcode_cb_44() // BIT 0, H
1210{
1211 testBit( 0, H );
1212}
1213
1214void opcode_cb_45() // BIT 0, L
1215{
1216 testBit( 0, L );
1217}
1218
1219void opcode_cb_46() // BIT 0, (HL)
1220{
1221 testBit( 0, readByte( HL() ) );
1222}
1223
1224void opcode_cb_47() // BIT 0, A
1225{
1226 testBit( 0, A );
1227}
1228
1229void opcode_cb_48() // BIT 1, B
1230{
1231 testBit( 1, B );
1232}
1233
1234void opcode_cb_49() // BIT 1, C
1235{
1236 testBit( 1, C );
1237}
1238
1239void opcode_cb_4a() // BIT 1, D
1240{
1241 testBit( 1, D );
1242}
1243
1244void opcode_cb_4b() // BIT 1, E
1245{
1246 testBit( 1, E );
1247}
1248
1249void opcode_cb_4c() // BIT 1, H
1250{
1251 testBit( 1, H );
1252}
1253
1254void opcode_cb_4d() // BIT 1, L
1255{
1256 testBit( 1, L );
1257}
1258
1259void opcode_cb_4e() // BIT 1, (HL)
1260{
1261 testBit( 1, readByte( HL() ) );
1262}
1263
1264void opcode_cb_4f() // BIT 1, A
1265{
1266 testBit( 1, A );
1267}
1268
1269void opcode_cb_50() // BIT 2, B
1270{
1271 testBit( 2, B );
1272}
1273
1274void opcode_cb_51() // BIT 2, C
1275{
1276 testBit( 2, C );
1277}
1278
1279void opcode_cb_52() // BIT 2, D
1280{
1281 testBit( 2, D );
1282}
1283
1284void opcode_cb_53() // BIT 2, E
1285{
1286 testBit( 2, E );
1287}
1288
1289void opcode_cb_54() // BIT 2, H
1290{
1291 testBit( 2, H );
1292}
1293
1294void opcode_cb_55() // BIT 2, L
1295{
1296 testBit( 2, L );
1297}
1298
1299void opcode_cb_56() // BIT 2, (HL)
1300{
1301 testBit( 2, readByte( HL() ) );
1302}
1303
1304void opcode_cb_57() // BIT 2, A
1305{
1306 testBit( 2, A );
1307}
1308
1309void opcode_cb_58() // BIT 3, B
1310{
1311 testBit( 3, B );
1312}
1313
1314void opcode_cb_59() // BIT 3, C
1315{
1316 testBit( 3, C );
1317}
1318
1319void opcode_cb_5a() // BIT 3, D
1320{
1321 testBit( 3, D );
1322}
1323
1324void opcode_cb_5b() // BIT 3, E
1325{
1326 testBit( 3, E );
1327}
1328
1329void opcode_cb_5c() // BIT 3, H
1330{
1331 testBit( 3, H );
1332}
1333
1334void opcode_cb_5d() // BIT 3, L
1335{
1336 testBit( 3, L );
1337}
1338
1339void opcode_cb_5e() // BIT 3, (HL)
1340{
1341 testBit( 3, readByte( HL() ) );
1342}
1343
1344void opcode_cb_5f() // BIT 3, A
1345{
1346 testBit( 3, A );
1347}
1348
1349void opcode_cb_60() // BIT 4, B
1350{
1351 testBit( 4, B );
1352}
1353
1354void opcode_cb_61() // BIT 4, C
1355{
1356 testBit( 4, C );
1357}
1358
1359void opcode_cb_62() // BIT 4, D
1360{
1361 testBit( 4, D );
1362}
1363
1364void opcode_cb_63() // BIT 4, E
1365{
1366 testBit( 4, E );
1367}
1368
1369void opcode_cb_64() // BIT 4, H
1370{
1371 testBit( 4, H );
1372}
1373
1374void opcode_cb_65() // BIT 4, L
1375{
1376 testBit( 4, L );
1377}
1378
1379void opcode_cb_66() // BIT 4, (HL)
1380{
1381 testBit( 4, readByte( HL() ) );
1382}
1383
1384void opcode_cb_67() // BIT 4, A
1385{
1386 testBit( 4, A );
1387}
1388
1389void opcode_cb_68() // BIT 5, B
1390{
1391 testBit( 5, B );
1392}
1393
1394void opcode_cb_69() // BIT 5, C
1395{
1396 testBit( 5, C );
1397}
1398
1399void opcode_cb_6a() // BIT 5, D
1400{
1401 testBit( 5, D );
1402}
1403
1404void opcode_cb_6b() // BIT 5, E
1405{
1406 testBit( 5, E );
1407}
1408
1409void opcode_cb_6c() // BIT 5, H
1410{
1411 testBit( 5, H );
1412}
1413
1414void opcode_cb_6d() // BIT 5, L
1415{
1416 testBit( 5, L );
1417}
1418
1419void opcode_cb_6e() // BIT 5, (HL)
1420{
1421 testBit( 5, readByte( HL() ) );
1422}
1423
1424void opcode_cb_6f() // BIT 5, A
1425{
1426 testBit( 5, A );
1427}
1428
1429void opcode_cb_70() // BIT 6, B
1430{
1431 testBit( 6, B );
1432}
1433
1434void opcode_cb_71() // BIT 6, C
1435{
1436 testBit( 6, C );
1437}
1438
1439void opcode_cb_72() // BIT 6, D
1440{
1441 testBit( 6, D );
1442}
1443
1444void opcode_cb_73() // BIT 6, E
1445{
1446 testBit( 6, E );
1447}
1448
1449void opcode_cb_74() // BIT 6, H
1450{
1451 testBit( 6, H );
1452}
1453
1454void opcode_cb_75() // BIT 6, L
1455{
1456 testBit( 6, L );
1457}
1458
1459void opcode_cb_76() // BIT 6, (HL)
1460{
1461 testBit( 6, readByte( HL() ) );
1462}
1463
1464void opcode_cb_77() // BIT 6, A
1465{
1466 testBit( 6, A );
1467}
1468
1469void opcode_cb_78() // BIT 7, B
1470{
1471 testBit( 7, B );
1472}
1473
1474void opcode_cb_79() // BIT 7, C
1475{
1476 testBit( 7, C );
1477}
1478
1479void opcode_cb_7a() // BIT 7, D
1480{
1481 testBit( 7, D );
1482}
1483
1484void opcode_cb_7b() // BIT 7, E
1485{
1486 testBit( 7, E );
1487}
1488
1489void opcode_cb_7c() // BIT 7, H
1490{
1491 testBit( 7, H );
1492}
1493
1494void opcode_cb_7d() // BIT 7, L
1495{
1496 testBit( 7, L );
1497}
1498
1499void opcode_cb_7e() // BIT 7, (HL)
1500{
1501 testBit( 7, readByte( HL() ) );
1502}
1503
1504void opcode_cb_7f() // BIT 7, A
1505{
1506 testBit( 7, A );
1507}
1508
1509void opcode_cb_80() // RES 0, B
1510{
1511 B &= ~(unsigned char) (1 << 0);
1512}
1513
1514void opcode_cb_81() // RES 0, C
1515{
1516 C &= ~(unsigned char) (1 << 0);
1517}
1518
1519void opcode_cb_82() // RES 0, D
1520{
1521 D &= ~(unsigned char) (1 << 0);
1522}
1523
1524void opcode_cb_83() // RES 0, E
1525{
1526 E &= ~(unsigned char) (1 << 0);
1527}
1528
1529void opcode_cb_84() // RES 0, H
1530{
1531 H &= ~(unsigned char) (1 << 0);
1532}
1533
1534void opcode_cb_85() // RES 0, L
1535{
1536 L &= ~(unsigned char) (1 << 0);
1537}
1538
1539void opcode_cb_86() // RES 0, (HL)
1540{
1541 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 0) );
1542}
1543
1544void opcode_cb_87() // RES 0, A
1545{
1546 A &= ~(unsigned char) (1 << 0);
1547}
1548
1549void opcode_cb_88() // RES 1, B
1550{
1551 B &= ~(unsigned char) (1 << 1);
1552}
1553
1554void opcode_cb_89() // RES 1, C
1555{
1556 C &= ~(unsigned char) (1 << 1);
1557}
1558
1559void opcode_cb_8a() // RES 1, D
1560{
1561 D &= ~(unsigned char) (1 << 1);
1562}
1563
1564void opcode_cb_8b() // RES 1, E
1565{
1566 E &= ~(unsigned char) (1 << 1);
1567}
1568
1569void opcode_cb_8c() // RES 1, H
1570{
1571 H &= ~(unsigned char) (1 << 1);
1572}
1573
1574void opcode_cb_8d() // RES 1, L
1575{
1576 L &= ~(unsigned char) (1 << 1);
1577}
1578
1579void opcode_cb_8e() // RES 1, (HL)
1580{
1581 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 1) );
1582}
1583
1584void opcode_cb_8f() // RES 1, A
1585{
1586 A &= ~(unsigned char) (1 << 1);
1587}
1588
1589void opcode_cb_90() // RES 2, B
1590{
1591 B &= ~(unsigned char) (1 << 2);
1592}
1593
1594void opcode_cb_91() // RES 2, C
1595{
1596 C &= ~(unsigned char) (1 << 2);
1597}
1598
1599void opcode_cb_92() // RES 2, D
1600{
1601 D &= ~(unsigned char) (1 << 2);
1602}
1603
1604void opcode_cb_93() // RES 2, E
1605{
1606 E &= ~(unsigned char) (1 << 2);
1607}
1608
1609void opcode_cb_94() // RES 2, H
1610{
1611 H &= ~(unsigned char) (1 << 2);
1612}
1613
1614void opcode_cb_95() // RES 2, L
1615{
1616 L &= ~(unsigned char) (1 << 2);
1617}
1618
1619void opcode_cb_96() // RES 2, (HL)
1620{
1621 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 2) );
1622}
1623
1624void opcode_cb_97() // RES 2, A
1625{
1626 A &= ~(unsigned char) (1 << 2);
1627}
1628
1629void opcode_cb_98() // RES 3, B
1630{
1631 B &= ~(unsigned char) (1 << 3);
1632}
1633
1634void opcode_cb_99() // RES 3, C
1635{
1636 C &= ~(unsigned char) (1 << 3);
1637}
1638
1639void opcode_cb_9a() // RES 3, D
1640{
1641 D &= ~(unsigned char) (1 << 3);
1642}
1643
1644void opcode_cb_9b() // RES 3, E
1645{
1646 E &= ~(unsigned char) (1 << 3);
1647}
1648
1649void opcode_cb_9c() // RES 3, H
1650{
1651 H &= ~(unsigned char) (1 << 3);
1652}
1653
1654void opcode_cb_9d() // RES 3, L
1655{
1656 L &= ~(unsigned char) (1 << 3);
1657}
1658
1659void opcode_cb_9e() // RES 3, (HL)
1660{
1661 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 3) );
1662}
1663
1664void opcode_cb_9f() // RES 3, A
1665{
1666 A &= ~(unsigned char) (1 << 3);
1667}
1668
1669void opcode_cb_a0() // RES 4, B
1670{
1671 B &= ~(unsigned char) (1 << 4);
1672}
1673
1674void opcode_cb_a1() // RES 4, C
1675{
1676 C &= ~(unsigned char) (1 << 4);
1677}
1678
1679void opcode_cb_a2() // RES 4, D
1680{
1681 D &= ~(unsigned char) (1 << 4);
1682}
1683
1684void opcode_cb_a3() // RES 4, E
1685{
1686 E &= ~(unsigned char) (1 << 4);
1687}
1688
1689void opcode_cb_a4() // RES 4, H
1690{
1691 H &= ~(unsigned char) (1 << 4);
1692}
1693
1694void opcode_cb_a5() // RES 4, L
1695{
1696 L &= ~(unsigned char) (1 << 4);
1697}
1698
1699void opcode_cb_a6() // RES 4, (HL)
1700{
1701 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 4) );
1702}
1703
1704void opcode_cb_a7() // RES 4, A
1705{
1706 A &= ~(unsigned char) (1 << 4);
1707}
1708
1709void opcode_cb_a8() // RES 5, B
1710{
1711 B &= ~(unsigned char) (1 << 5);
1712}
1713
1714void opcode_cb_a9() // RES 5, C
1715{
1716 C &= ~(unsigned char) (1 << 5);
1717}
1718
1719void opcode_cb_aa() // RES 5, D
1720{
1721 D &= ~(unsigned char) (1 << 5);
1722}
1723
1724void opcode_cb_ab() // RES 5, E
1725{
1726 E &= ~(unsigned char) (1 << 5);
1727}
1728
1729void opcode_cb_ac() // RES 5, H
1730{
1731 H &= ~(unsigned char) (1 << 5);
1732}
1733
1734void opcode_cb_ad() // RES 5, L
1735{
1736 L &= ~(unsigned char) (1 << 5);
1737}
1738
1739void opcode_cb_ae() // RES 5, (HL)
1740{
1741 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 5) );
1742}
1743
1744void opcode_cb_af() // RES 5, A
1745{
1746 A &= ~(unsigned char) (1 << 5);
1747}
1748
1749void opcode_cb_b0() // RES 6, B
1750{
1751 B &= ~(unsigned char) (1 << 6);
1752}
1753
1754void opcode_cb_b1() // RES 6, C
1755{
1756 C &= ~(unsigned char) (1 << 6);
1757}
1758
1759void opcode_cb_b2() // RES 6, D
1760{
1761 D &= ~(unsigned char) (1 << 6);
1762}
1763
1764void opcode_cb_b3() // RES 6, E
1765{
1766 E &= ~(unsigned char) (1 << 6);
1767}
1768
1769void opcode_cb_b4() // RES 6, H
1770{
1771 H &= ~(unsigned char) (1 << 6);
1772}
1773
1774void opcode_cb_b5() // RES 6, L
1775{
1776 L &= ~(unsigned char) (1 << 6);
1777}
1778
1779void opcode_cb_b6() // RES 6, (HL)
1780{
1781 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 6) );
1782}
1783
1784void opcode_cb_b7() // RES 6, A
1785{
1786 A &= ~(unsigned char) (1 << 6);
1787}
1788
1789void opcode_cb_b8() // RES 7, B
1790{
1791 B &= ~(unsigned char) (1 << 7);
1792}
1793
1794void opcode_cb_b9() // RES 7, C
1795{
1796 C &= ~(unsigned char) (1 << 7);
1797}
1798
1799void opcode_cb_ba() // RES 7, D
1800{
1801 D &= ~(unsigned char) (1 << 7);
1802}
1803
1804void opcode_cb_bb() // RES 7, E
1805{
1806 E &= ~(unsigned char) (1 << 7);
1807}
1808
1809void opcode_cb_bc() // RES 7, H
1810{
1811 H &= ~(unsigned char) (1 << 7);
1812}
1813
1814void opcode_cb_bd() // RES 7, L
1815{
1816 L &= ~(unsigned char) (1 << 7);
1817}
1818
1819void opcode_cb_be() // RES 7, (HL)
1820{
1821 writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 7) );
1822}
1823
1824void opcode_cb_bf() // RES 7, A
1825{
1826 A &= ~(unsigned char) (1 << 7);
1827}
1828
1829void opcode_cb_c0() // SET 0, B
1830{
1831 B |= (unsigned char) (1 << 0);
1832}
1833
1834void opcode_cb_c1() // SET 0, C
1835{
1836 C |= (unsigned char) (1 << 0);
1837}
1838
1839void opcode_cb_c2() // SET 0, D
1840{
1841 D |= (unsigned char) (1 << 0);
1842}
1843
1844void opcode_cb_c3() // SET 0, E
1845{
1846 E |= (unsigned char) (1 << 0);
1847}
1848
1849void opcode_cb_c4() // SET 0, H
1850{
1851 H |= (unsigned char) (1 << 0);
1852}
1853
1854void opcode_cb_c5() // SET 0, L
1855{
1856 L |= (unsigned char) (1 << 0);
1857}
1858
1859void opcode_cb_c6() // SET 0, (HL)
1860{
1861 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 0) );
1862}
1863
1864void opcode_cb_c7() // SET 0, A
1865{
1866 A |= (unsigned char) (1 << 0);
1867}
1868
1869void opcode_cb_c8() // SET 1, B
1870{
1871 B |= (unsigned char) (1 << 1);
1872}
1873
1874void opcode_cb_c9() // SET 1, C
1875{
1876 C |= (unsigned char) (1 << 1);
1877}
1878
1879void opcode_cb_ca() // SET 1, D
1880{
1881 D |= (unsigned char) (1 << 1);
1882}
1883
1884void opcode_cb_cb() // SET 1, E
1885{
1886 E |= (unsigned char) (1 << 1);
1887}
1888
1889void opcode_cb_cc() // SET 1, H
1890{
1891 H |= (unsigned char) (1 << 1);
1892}
1893
1894void opcode_cb_cd() // SET 1, L
1895{
1896 L |= (unsigned char) (1 << 1);
1897}
1898
1899void opcode_cb_ce() // SET 1, (HL)
1900{
1901 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 1) );
1902}
1903
1904void opcode_cb_cf() // SET 1, A
1905{
1906 A |= (unsigned char) (1 << 1);
1907}
1908
1909void opcode_cb_d0() // SET 2, B
1910{
1911 B |= (unsigned char) (1 << 2);
1912}
1913
1914void opcode_cb_d1() // SET 2, C
1915{
1916 C |= (unsigned char) (1 << 2);
1917}
1918
1919void opcode_cb_d2() // SET 2, D
1920{
1921 D |= (unsigned char) (1 << 2);
1922}
1923
1924void opcode_cb_d3() // SET 2, E
1925{
1926 E |= (unsigned char) (1 << 2);
1927}
1928
1929void opcode_cb_d4() // SET 2, H
1930{
1931 H |= (unsigned char) (1 << 2);
1932}
1933
1934void opcode_cb_d5() // SET 2, L
1935{
1936 L |= (unsigned char) (1 << 2);
1937}
1938
1939void opcode_cb_d6() // SET 2, (HL)
1940{
1941 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 2) );
1942}
1943
1944void opcode_cb_d7() // SET 2, A
1945{
1946 A |= (unsigned char) (1 << 2);
1947}
1948
1949void opcode_cb_d8() // SET 3, B
1950{
1951 B |= (unsigned char) (1 << 3);
1952}
1953
1954void opcode_cb_d9() // SET 3, C
1955{
1956 C |= (unsigned char) (1 << 3);
1957}
1958
1959void opcode_cb_da() // SET 3, D
1960{
1961 D |= (unsigned char) (1 << 3);
1962}
1963
1964void opcode_cb_db() // SET 3, E
1965{
1966 E |= (unsigned char) (1 << 3);
1967}
1968
1969void opcode_cb_dc() // SET 3, H
1970{
1971 H |= (unsigned char) (1 << 3);
1972}
1973
1974void opcode_cb_dd() // SET 3, L
1975{
1976 L |= (unsigned char) (1 << 3);
1977}
1978
1979void opcode_cb_de() // SET 3, (HL)
1980{
1981 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 3) );
1982}
1983
1984void opcode_cb_df() // SET 3, A
1985{
1986 A |= (unsigned char) (1 << 3);
1987}
1988
1989void opcode_cb_e0() // SET 4, B
1990{
1991 B |= (unsigned char) (1 << 4);
1992}
1993
1994void opcode_cb_e1() // SET 4, C
1995{
1996 C |= (unsigned char) (1 << 4);
1997}
1998
1999void opcode_cb_e2() // SET 4, D
2000{
2001 D |= (unsigned char) (1 << 4);
2002}
2003
2004void opcode_cb_e3() // SET 4, E
2005{
2006 E |= (unsigned char) (1 << 4);
2007}
2008
2009void opcode_cb_e4() // SET 4, H
2010{
2011 H |= (unsigned char) (1 << 4);
2012}
2013
2014void opcode_cb_e5() // SET 4, L
2015{
2016 L |= (unsigned char) (1 << 4);
2017}
2018
2019void opcode_cb_e6() // SET 4, (HL)
2020{
2021 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 4) );
2022}
2023
2024void opcode_cb_e7() // SET 4, A
2025{
2026 A |= (unsigned char) (1 << 4);
2027}
2028
2029void opcode_cb_e8() // SET 5, B
2030{
2031 B |= (unsigned char) (1 << 5);
2032}
2033
2034void opcode_cb_e9() // SET 5, C
2035{
2036 C |= (unsigned char) (1 << 5);
2037}
2038
2039void opcode_cb_ea() // SET 5, D
2040{
2041 D |= (unsigned char) (1 << 5);
2042}
2043
2044void opcode_cb_eb() // SET 5, E
2045{
2046 E |= (unsigned char) (1 << 5);
2047}
2048
2049void opcode_cb_ec() // SET 5, H
2050{
2051 H |= (unsigned char) (1 << 5);
2052}
2053
2054void opcode_cb_ed() // SET 5, L
2055{
2056 L |= (unsigned char) (1 << 5);
2057}
2058
2059void opcode_cb_ee() // SET 5, (HL)
2060{
2061 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 5) );
2062}
2063
2064void opcode_cb_ef() // SET 5, A
2065{
2066 A |= (unsigned char) (1 << 5);
2067}
2068
2069void opcode_cb_f0() // SET 6, B
2070{
2071 B |= (unsigned char) (1 << 6);
2072}
2073
2074void opcode_cb_f1() // SET 6, C
2075{
2076 C |= (unsigned char) (1 << 6);
2077}
2078
2079void opcode_cb_f2() // SET 6, D
2080{
2081 D |= (unsigned char) (1 << 6);
2082}
2083
2084void opcode_cb_f3() // SET 6, E
2085{
2086 E |= (unsigned char) (1 << 6);
2087}
2088
2089void opcode_cb_f4() // SET 6, H
2090{
2091 H |= (unsigned char) (1 << 6);
2092}
2093
2094void opcode_cb_f5() // SET 6, L
2095{
2096 L |= (unsigned char) (1 << 6);
2097}
2098
2099void opcode_cb_f6() // SET 6, (HL)
2100{
2101 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 6) );
2102}
2103
2104void opcode_cb_f7() // SET 6, A
2105{
2106 A |= (unsigned char) (1 << 6);
2107}
2108
2109void opcode_cb_f8() // SET 7, B
2110{
2111 B |= (unsigned char) (1 << 7);
2112}
2113
2114void opcode_cb_f9() // SET 7, C
2115{
2116 C |= (unsigned char) (1 << 7);
2117}
2118
2119void opcode_cb_fa() // SET 7, D
2120{
2121 D |= (unsigned char) (1 << 7);
2122}
2123
2124void opcode_cb_fb() // SET 7, E
2125{
2126 E |= (unsigned char) (1 << 7);
2127}
2128
2129void opcode_cb_fc() // SET 7, H
2130{
2131 H |= (unsigned char) (1 << 7);
2132}
2133
2134void opcode_cb_fd() // SET 7, L
2135{
2136 L |= (unsigned char) (1 << 7);
2137}
2138
2139void opcode_cb_fe() // SET 7, (HL)
2140{
2141 writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 7) );
2142}
2143
2144void opcode_cb_ff() // SET 7, A
2145{
2146 A |= (unsigned char) (1 << 7);
2147}
2148
2149OpcodeInfo OpInfoDD_[256] = {
2150 { 0, 0 }, // 0x00
2151 { 0, 0 }, // 0x01
2152 { 0, 0 }, // 0x02
2153 { 0, 0 }, // 0x03
2154 { 0, 0 }, // 0x04
2155 { 0, 0 }, // 0x05
2156 { 0, 0 }, // 0x06
2157 { 0, 0 }, // 0x07
2158 { 0, 0 }, // 0x08
2159 { &opcode_dd_09, 15 }, // ADD IX, BC
2160 { 0, 0 }, // 0x0A
2161 { 0, 0 }, // 0x0B
2162 { 0, 0 }, // 0x0C
2163 { 0, 0 }, // 0x0D
2164 { 0, 0 }, // 0x0E
2165 { 0, 0 }, // 0x0F
2166 { 0, 0 }, // 0x10
2167 { 0, 0 }, // 0x11
2168 { 0, 0 }, // 0x12
2169 { 0, 0 }, // 0x13
2170 { 0, 0 }, // 0x14
2171 { 0, 0 }, // 0x15
2172 { 0, 0 }, // 0x16
2173 { 0, 0 }, // 0x17
2174 { 0, 0 }, // 0x18
2175 { &opcode_dd_19, 15 }, // ADD IX, DE
2176 { 0, 0 }, // 0x1A
2177 { 0, 0 }, // 0x1B
2178 { 0, 0 }, // 0x1C
2179 { 0, 0 }, // 0x1D
2180 { 0, 0 }, // 0x1E
2181 { 0, 0 }, // 0x1F
2182 { 0, 0 }, // 0x20
2183 { &opcode_dd_21, 14 }, // LD IX, nn
2184 { &opcode_dd_22, 20 }, // LD (nn), IX
2185 { &opcode_dd_23, 10 }, // INC IX
2186 { &opcode_dd_24, 9 }, // INC IXH
2187 { &opcode_dd_25, 9 }, // DEC IXH
2188 { &opcode_dd_26, 9 }, // LD IXH, n
2189 { 0, 0 }, // 0x27
2190 { 0, 0 }, // 0x28
2191 { &opcode_dd_29, 15 }, // ADD IX, IX
2192 { &opcode_dd_2a, 20 }, // LD IX, (nn)
2193 { &opcode_dd_2b, 10 }, // DEC IX
2194 { &opcode_dd_2c, 9 }, // INC IXL
2195 { &opcode_dd_2d, 9 }, // DEC IXL
2196 { &opcode_dd_2e, 9 }, // LD IXL, n
2197 { 0, 0 }, // 0x2F
2198 { 0, 0 }, // 0x30
2199 { 0, 0 }, // 0x31
2200 { 0, 0 }, // 0x32
2201 { 0, 0 }, // 0x33
2202 { &opcode_dd_34, 23 }, // INC (IX + d)
2203 { &opcode_dd_35, 23 }, // DEC (IX + d)
2204 { &opcode_dd_36, 19 }, // LD (IX + d), n
2205 { 0, 0 }, // 0x37
2206 { 0, 0 }, // 0x38
2207 { &opcode_dd_39, 15 }, // ADD IX, SP
2208 { 0, 0 }, // 0x3A
2209 { 0, 0 }, // 0x3B
2210 { 0, 0 }, // 0x3C
2211 { 0, 0 }, // 0x3D
2212 { 0, 0 }, // 0x3E
2213 { 0, 0 }, // 0x3F
2214 { 0, 0 }, // 0x40
2215 { 0, 0 }, // 0x41
2216 { 0, 0 }, // 0x42
2217 { 0, 0 }, // 0x43
2218 { &opcode_dd_44, 9 }, // LD B, IXH
2219 { &opcode_dd_45, 9 }, // LD B, IXL
2220 { &opcode_dd_46, 19 }, // LD B, (IX + d)
2221 { 0, 0 }, // 0x47
2222 { 0, 0 }, // 0x48
2223 { 0, 0 }, // 0x49
2224 { 0, 0 }, // 0x4A
2225 { 0, 0 }, // 0x4B
2226 { &opcode_dd_4c, 9 }, // LD C, IXH
2227 { &opcode_dd_4d, 9 }, // LD C, IXL
2228 { &opcode_dd_4e, 19 }, // LD C, (IX + d)
2229 { 0, 0 }, // 0x4F
2230 { 0, 0 }, // 0x50
2231 { 0, 0 }, // 0x51
2232 { 0, 0 }, // 0x52
2233 { 0, 0 }, // 0x53
2234 { &opcode_dd_54, 9 }, // LD D, IXH
2235 { &opcode_dd_55, 9 }, // LD D, IXL
2236 { &opcode_dd_56, 19 }, // LD D, (IX + d)
2237 { 0, 0 }, // 0x57
2238 { 0, 0 }, // 0x58
2239 { 0, 0 }, // 0x59
2240 { 0, 0 }, // 0x5A
2241 { 0, 0 }, // 0x5B
2242 { &opcode_dd_5c, 9 }, // LD E, IXH
2243 { &opcode_dd_5d, 9 }, // LD E, IXL
2244 { &opcode_dd_5e, 19 }, // LD E, (IX + d)
2245 { 0, 0 }, // 0x5F
2246 { &opcode_dd_60, 9 }, // LD IXH, B
2247 { &opcode_dd_61, 9 }, // LD IXH, C
2248 { &opcode_dd_62, 9 }, // LD IXH, D
2249 { &opcode_dd_63, 9 }, // LD IXH, E
2250 { &opcode_dd_64, 9 }, // LD IXH, IXH
2251 { &opcode_dd_65, 9 }, // LD IXH, IXL
2252 { &opcode_dd_66, 9 }, // LD H, (IX + d)
2253 { &opcode_dd_67, 9 }, // LD IXH, A
2254 { &opcode_dd_68, 9 }, // LD IXL, B
2255 { &opcode_dd_69, 9 }, // LD IXL, C
2256 { &opcode_dd_6a, 9 }, // LD IXL, D
2257 { &opcode_dd_6b, 9 }, // LD IXL, E
2258 { &opcode_dd_6c, 9 }, // LD IXL, IXH
2259 { &opcode_dd_6d, 9 }, // LD IXL, IXL
2260 { &opcode_dd_6e, 9 }, // LD L, (IX + d)
2261 { &opcode_dd_6f, 9 }, // LD IXL, A
2262 { &opcode_dd_70, 19 }, // LD (IX + d), B
2263 { &opcode_dd_71, 19 }, // LD (IX + d), C
2264 { &opcode_dd_72, 19 }, // LD (IX + d), D
2265 { &opcode_dd_73, 19 }, // LD (IX + d), E
2266 { &opcode_dd_74, 19 }, // LD (IX + d), H
2267 { &opcode_dd_75, 19 }, // LD (IX + d), L
2268 { 0,19 }, // 0x76
2269 { &opcode_dd_77, 19 }, // LD (IX + d), A
2270 { 0, 0 }, // 0x78
2271 { 0, 0 }, // 0x79
2272 { 0, 0 }, // 0x7A
2273 { 0, 0 }, // 0x7B
2274 { &opcode_dd_7c, 9 }, // LD A, IXH
2275 { &opcode_dd_7d, 9 }, // LD A, IXL
2276 { &opcode_dd_7e, 19 }, // LD A, (IX + d)
2277 { 0, 0 }, // 0x7F
2278 { 0, 0 }, // 0x80
2279 { 0, 0 }, // 0x81
2280 { 0, 0 }, // 0x82
2281 { 0, 0 }, // 0x83
2282 { &opcode_dd_84, 9 }, // ADD A, IXH
2283 { &opcode_dd_85, 9 }, // ADD A, IXL
2284 { &opcode_dd_86, 19 }, // ADD A, (IX + d)
2285 { 0, 0 }, // 0x87
2286 { 0, 0 }, // 0x88
2287 { 0, 0 }, // 0x89
2288 { 0, 0 }, // 0x8A
2289 { 0, 0 }, // 0x8B
2290 { &opcode_dd_8c, 9 }, // ADC A, IXH
2291 { &opcode_dd_8d, 9 }, // ADC A, IXL
2292 { &opcode_dd_8e, 19 }, // ADC A, (IX + d)
2293 { 0, 0 }, // 0x8F
2294 { 0, 0 }, // 0x90
2295 { 0, 0 }, // 0x91
2296 { 0, 0 }, // 0x92
2297 { 0, 0 }, // 0x93
2298 { &opcode_dd_94, 9 }, // SUB IXH
2299 { &opcode_dd_95, 9 }, // SUB IXL
2300 { &opcode_dd_96, 19 }, // SUB (IX + d)
2301 { 0, 0 }, // 0x97
2302 { 0, 0 }, // 0x98
2303 { 0, 0 }, // 0x99
2304 { 0, 0 }, // 0x9A
2305 { 0, 0 }, // 0x9B
2306 { &opcode_dd_9c, 9 }, // SBC A, IXH
2307 { &opcode_dd_9d, 9 }, // SBC A, IXL
2308 { &opcode_dd_9e, 19 }, // SBC A, (IX + d)
2309 { 0, 0 }, // 0x9F
2310 { 0, 0 }, // 0xA0
2311 { 0, 0 }, // 0xA1
2312 { 0, 0 }, // 0xA2
2313 { 0, 0 }, // 0xA3
2314 { &opcode_dd_a4, 9 }, // AND IXH
2315 { &opcode_dd_a5, 9 }, // AND IXL
2316 { &opcode_dd_a6, 19 }, // AND (IX + d)
2317 { 0, 0 }, // 0xA7
2318 { 0, 0 }, // 0xA8
2319 { 0, 0 }, // 0xA9
2320 { 0, 0 }, // 0xAA
2321 { 0, 0 }, // 0xAB
2322 { &opcode_dd_ac, 9 }, // XOR IXH
2323 { &opcode_dd_ad, 9 }, // XOR IXL
2324 { &opcode_dd_ae, 19 }, // XOR (IX + d)
2325 { 0, 0 }, // 0xAF
2326 { 0, 0 }, // 0xB0
2327 { 0, 0 }, // 0xB1
2328 { 0, 0 }, // 0xB2
2329 { 0, 0 }, // 0xB3
2330 { &opcode_dd_b4, 9 }, // OR IXH
2331 { &opcode_dd_b5, 9 }, // OR IXL
2332 { &opcode_dd_b6, 19 }, // OR (IX + d)
2333 { 0, 0 }, // 0xB7
2334 { 0, 0 }, // 0xB8
2335 { 0, 0 }, // 0xB9
2336 { 0, 0 }, // 0xBA
2337 { 0, 0 }, // 0xBB
2338 { &opcode_dd_bc, 9 }, // CP IXH
2339 { &opcode_dd_bd, 9 }, // CP IXL
2340 { &opcode_dd_be, 19 }, // CP (IX + d)
2341 { 0, 0 }, // 0xBF
2342 { 0, 0 }, // 0xC0
2343 { 0, 0 }, // 0xC1
2344 { 0, 0 }, // 0xC2
2345 { 0, 0 }, // 0xC3
2346 { 0, 0 }, // 0xC4
2347 { 0, 0 }, // 0xC5
2348 { 0, 0 }, // 0xC6
2349 { 0, 0 }, // 0xC7
2350 { 0, 0 }, // 0xC8
2351 { 0, 0 }, // 0xC9
2352 { 0, 0 }, // 0xCA
2353 { &opcode_dd_cb, 0 }, //
2354 { 0, 0 }, // 0xCC
2355 { 0, 0 }, // 0xCD
2356 { 0, 0 }, // 0xCE
2357 { 0, 0 }, // 0xCF
2358 { 0, 0 }, // 0xD0
2359 { 0, 0 }, // 0xD1
2360 { 0, 0 }, // 0xD2
2361 { 0, 0 }, // 0xD3
2362 { 0, 0 }, // 0xD4
2363 { 0, 0 }, // 0xD5
2364 { 0, 0 }, // 0xD6
2365 { 0, 0 }, // 0xD7
2366 { 0, 0 }, // 0xD8
2367 { 0, 0 }, // 0xD9
2368 { 0, 0 }, // 0xDA
2369 { 0, 0 }, // 0xDB
2370 { 0, 0 }, // 0xDC
2371 { 0, 0 }, // 0xDD
2372 { 0, 0 }, // 0xDE
2373 { 0, 0 }, // 0xDF
2374 { 0, 0 }, // 0xE0
2375 { &opcode_dd_e1, 14 }, // POP IX
2376 { 0, 0 }, // 0xE2
2377 { &opcode_dd_e3, 23 }, // EX (SP), IX
2378 { 0, 0 }, // 0xE4
2379 { &opcode_dd_e5, 15 }, // PUSH IX
2380 { 0, 0 }, // 0xE6
2381 { 0, 0 }, // 0xE7
2382 { 0, 0 }, // 0xE8
2383 { &opcode_dd_e9, 8 }, // JP (IX)
2384 { 0, 0 }, // 0xEA
2385 { 0, 0 }, // 0xEB
2386 { 0, 0 }, // 0xEC
2387 { 0, 0 }, // 0xED
2388 { 0, 0 }, // 0xEE
2389 { 0, 0 }, // 0xEF
2390 { 0, 0 }, // 0xF0
2391 { 0, 0 }, // 0xF1
2392 { 0, 0 }, // 0xF2
2393 { 0, 0 }, // 0xF3
2394 { 0, 0 }, // 0xF4
2395 { 0, 0 }, // 0xF5
2396 { 0, 0 }, // 0xF6
2397 { 0, 0 }, // 0xF7
2398 { 0, 0 }, // 0xF8
2399 { &opcode_dd_f9, 10 }, // LD SP, IX
2400 { 0, 0 }, // 0xFA
2401 { 0, 0 }, // 0xFB
2402 { 0, 0 }, // 0xFC
2403 { 0, 0 }, // 0xFD
2404 { 0, 0 }, // 0xFE
2405 { 0, 0 } // 0xFF
2406};
2407
2408void opcode_dd_09() // ADD IX, BC
2409{
2410 unsigned rr = BC();
2411
2412 F &= (Zero | Sign | Parity);
2413 if( ((IX & 0xFFF)+(rr & 0xFFF)) > 0xFFF ) F |= Halfcarry;
2414 IX += rr;
2415 if( IX & 0x10000 ) F |= Carry;
2416}
2417
2418void opcode_dd_19() // ADD IX, DE
2419{
2420 unsigned rr = DE();
2421
2422 F &= (Zero | Sign | Parity);
2423 if( ((IX & 0xFFF)+(rr & 0xFFF)) > 0xFFF ) F |= Halfcarry;
2424 IX += rr;
2425 if( IX & 0x10000 ) F |= Carry;
2426}
2427
2428void opcode_dd_21() // LD IX, nn
2429{
2430 IX = fetchWord();
2431}
2432
2433void opcode_dd_22() // LD (nn), IX
2434{
2435 writeWord( fetchWord(), IX );
2436}
2437
2438void opcode_dd_23() // INC IX
2439{
2440 IX++;
2441}
2442
2443void opcode_dd_24() // INC IXH
2444{
2445 IX = (IX & 0xFF) | ((unsigned)incByte( IX >> 8 ) << 8);
2446}
2447
2448void opcode_dd_25() // DEC IXH
2449{
2450 IX = (IX & 0xFF) | ((unsigned)decByte( IX >> 8 ) << 8);
2451}
2452
2453void opcode_dd_26() // LD IXH, n
2454{
2455 IX = (IX & 0xFF) | ((unsigned)fetchByte() << 8);
2456}
2457
2458void opcode_dd_29() // ADD IX, IX
2459{
2460 F &= (Zero | Sign | Parity);
2461 if( IX & 0x800 ) F |= Halfcarry;
2462 IX += IX;
2463 if( IX & 0x10000 ) F |= Carry;
2464}
2465
2466void opcode_dd_2a() // LD IX, (nn)
2467{
2468 IX = readWord( fetchWord() );
2469}
2470
2471void opcode_dd_2b() // DEC IX
2472{
2473 IX--;
2474}
2475
2476void opcode_dd_2c() // INC IXL
2477{
2478 IX = (IX & 0xFF00) | incByte( IX & 0xFF );
2479}
2480
2481void opcode_dd_2d() // DEC IXL
2482{
2483 IX = (IX & 0xFF00) | decByte( IX & 0xFF );
2484}
2485
2486void opcode_dd_2e() // LD IXL, n
2487{
2488 IX = (IX & 0xFF00) | fetchByte();
2489}
2490
2491void opcode_dd_34() // INC (IX + d)
2492{
2493 unsigned addr = addDispl( IX, fetchByte() );
2494
2495 writeByte( addr, incByte( readByte( addr ) ) );
2496}
2497
2498void opcode_dd_35() // DEC (IX + d)
2499{
2500 unsigned addr = addDispl( IX, fetchByte() );
2501
2502 writeByte( addr, decByte( readByte( addr ) ) );
2503}
2504
2505void opcode_dd_36() // LD (IX + d), n
2506{
2507 unsigned addr = addDispl( IX, fetchByte() );
2508
2509 writeByte( addr, fetchByte() );
2510}
2511
2512void opcode_dd_39() // ADD IX, SP
2513{
2514 F &= (Zero | Sign | Parity);
2515 if( ((IX & 0xFFF)+(SP & 0xFFF)) > 0xFFF ) F |= Halfcarry;
2516 IX += SP;
2517 if( IX & 0x10000 ) F |= Carry;
2518}
2519
2520void opcode_dd_44() // LD B, IXH
2521{
2522 B = IX >> 8;
2523}
2524
2525void opcode_dd_45() // LD B, IXL
2526{
2527 B = IX & 0xFF;
2528}
2529
2530void opcode_dd_46() // LD B, (IX + d)
2531{
2532 B = readByte( addDispl(IX,fetchByte()) );
2533}
2534
2535void opcode_dd_4c() // LD C, IXH
2536{
2537 C = IX >> 8;
2538}
2539
2540void opcode_dd_4d() // LD C, IXL
2541{
2542 C = IX & 0xFF;
2543}
2544
2545void opcode_dd_4e() // LD C, (IX + d)
2546{
2547 C = readByte( addDispl(IX,fetchByte()) );
2548}
2549
2550void opcode_dd_54() // LD D, IXH
2551{
2552 D = IX >> 8;
2553}
2554
2555void opcode_dd_55() // LD D, IXL
2556{
2557 D = IX & 0xFF;
2558}
2559
2560void opcode_dd_56() // LD D, (IX + d)
2561{
2562 D = readByte( addDispl(IX,fetchByte()) );
2563}
2564
2565void opcode_dd_5c() // LD E, IXH
2566{
2567 E = IX >> 8;
2568}
2569
2570void opcode_dd_5d() // LD E, IXL
2571{
2572 E = IX & 0xFF;
2573}
2574
2575void opcode_dd_5e() // LD E, (IX + d)
2576{
2577 E = readByte( addDispl(IX,fetchByte()) );
2578}
2579
2580void opcode_dd_60() // LD IXH, B
2581{
2582 IX = (IX & 0xFF) | ((unsigned)B << 8);
2583}
2584
2585void opcode_dd_61() // LD IXH, C
2586{
2587 IX = (IX & 0xFF) | ((unsigned)C << 8);
2588}
2589
2590void opcode_dd_62() // LD IXH, D
2591{
2592 IX = (IX & 0xFF) | ((unsigned)D << 8);
2593}
2594
2595void opcode_dd_63() // LD IXH, E
2596{
2597 IX = (IX & 0xFF) | ((unsigned)E << 8);
2598}
2599
2600void opcode_dd_64() // LD IXH, IXH
2601{
2602}
2603
2604void opcode_dd_65() // LD IXH, IXL
2605{
2606 IX = (IX & 0xFF) | ((IX << 8) & 0xFF00);
2607}
2608
2609void opcode_dd_66() // LD H, (IX + d)
2610{
2611 H = readByte( addDispl(IX,fetchByte()) );
2612}
2613
2614void opcode_dd_67() // LD IXH, A
2615{
2616 IX = (IX & 0xFF) | ((unsigned)A << 8);
2617}
2618
2619void opcode_dd_68() // LD IXL, B
2620{
2621 IX = (IX & 0xFF00) | B;
2622}
2623
2624void opcode_dd_69() // LD IXL, C
2625{
2626 IX = (IX & 0xFF00) | C;
2627}
2628
2629void opcode_dd_6a() // LD IXL, D
2630{
2631 IX = (IX & 0xFF00) | D;
2632}
2633
2634void opcode_dd_6b() // LD IXL, E
2635{
2636 IX = (IX & 0xFF00) | E;
2637}
2638
2639void opcode_dd_6c() // LD IXL, IXH
2640{
2641 IX = (IX & 0xFF00) | ((IX >> 8) & 0xFF);
2642}
2643
2644void opcode_dd_6d() // LD IXL, IXL
2645{
2646}
2647
2648void opcode_dd_6e() // LD L, (IX + d)
2649{
2650 L = readByte( addDispl(IX,fetchByte()) );
2651}
2652
2653void opcode_dd_6f() // LD IXL, A
2654{
2655 IX = (IX & 0xFF00) | A;
2656}
2657
2658void opcode_dd_70() // LD (IX + d), B
2659{
2660 writeByte( addDispl(IX,fetchByte()), B );
2661}
2662
2663void opcode_dd_71() // LD (IX + d), C
2664{
2665 writeByte( addDispl(IX,fetchByte()), C );
2666}
2667
2668void opcode_dd_72() // LD (IX + d), D
2669{
2670 writeByte( addDispl(IX,fetchByte()), D );
2671}
2672
2673void opcode_dd_73() // LD (IX + d), E
2674{
2675 writeByte( addDispl(IX,fetchByte()), E );
2676}
2677
2678void opcode_dd_74() // LD (IX + d), H
2679{
2680 writeByte( addDispl(IX,fetchByte()), H );
2681}
2682
2683void opcode_dd_75() // LD (IX + d), L
2684{
2685 writeByte( addDispl