summaryrefslogtreecommitdiff
path: root/apps/plugins
diff options
context:
space:
mode:
authorDave Chapman <dave@dchapman.com>2006-03-11 15:44:35 +0000
committerDave Chapman <dave@dchapman.com>2006-03-11 15:44:35 +0000
commita814584c87fef79038f6b0f311cfc70fb51d1b95 (patch)
tree4df31679017735c7fa64b32ae78ec3ad078271ae /apps/plugins
parent1246668a7807f1f5b9253ad7f9a682fb6b2ff7dd (diff)
downloadrockbox-a814584c87fef79038f6b0f311cfc70fb51d1b95.zip
rockbox-a814584c87fef79038f6b0f311cfc70fb51d1b95.tar.gz
rockbox-a814584c87fef79038f6b0f311cfc70fb51d1b95.tar.bz2
rockbox-a814584c87fef79038f6b0f311cfc70fb51d1b95.tar.xz
pacbox - a Pacman arcade machine emulator. Currently working for all colour targets and the iriver H1x0. Requires the Pacman arcade machine ROMs in /.rockbox/pacman/
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@9001 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps/plugins')
-rw-r--r--apps/plugins/Makefile6
-rw-r--r--apps/plugins/pacbox/Makefile113
-rw-r--r--apps/plugins/pacbox/arcade.c577
-rw-r--r--apps/plugins/pacbox/arcade.h199
-rw-r--r--apps/plugins/pacbox/hardware.c197
-rw-r--r--apps/plugins/pacbox/hardware.h141
-rw-r--r--apps/plugins/pacbox/pacbox.c534
-rw-r--r--apps/plugins/pacbox/readme.txt13
-rw-r--r--apps/plugins/pacbox/z80.c8058
-rw-r--r--apps/plugins/pacbox/z80.h160
-rw-r--r--apps/plugins/pacbox/z80_internal.h1062
11 files changed, 11060 insertions, 0 deletions
diff --git a/apps/plugins/Makefile b/apps/plugins/Makefile
index 8c72294..b591432 100644
--- a/apps/plugins/Makefile
+++ b/apps/plugins/Makefile
@@ -77,6 +77,12 @@ ifneq (-DIRIVER_IFP7XX,$(TARGET))
endif
endif
+# For all the colour targets and iriver H1x0
+ifneq (,$(strip $(foreach tgt,IPOD_VIDEO IPOD_NANO IPOD_COLOR IRIVER \
+ IAUDIO_X5 GIGABEAT,$(findstring $(tgt),$(TARGET)))))
+ SUBDIRS += pacbox
+endif
+
.PHONY: $(SUBDIRS)
all: $(BUILDDIR)/libplugin.a $(ROCKS) $(SUBDIRS) $(DEPFILE)
diff --git a/apps/plugins/pacbox/Makefile b/apps/plugins/pacbox/Makefile
new file mode 100644
index 0000000..817c6d4
--- /dev/null
+++ b/apps/plugins/pacbox/Makefile
@@ -0,0 +1,113 @@
+# __________ __ ___.
+# Open \______ \ ____ ____ | | _\_ |__ _______ ___
+# Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+# Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+# Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+# \/ \/ \/ \/ \/
+# $Id$
+#
+
+INCLUDES = -I$(APPSDIR) -I.. -I. -I$(FIRMDIR)/include -I$(FIRMDIR)/export \
+ -I$(FIRMDIR)/common -I$(FIRMDIR)/drivers -I$(OUTDIR) -I$(BUILDDIR)
+CFLAGS = $(INCLUDES) $(GCCOPTS) -O2 $(TARGET) $(EXTRA_DEFINES) \
+ -DTARGET_ID=$(TARGET_ID) -DMEM=${MEMORYSIZE} -DPLUGIN
+
+
+ifdef APPEXTRA
+ INCLUDES += $(patsubst %,-I$(APPSDIR)/%,$(subst :, ,$(APPEXTRA)))
+endif
+
+LINKFILE := $(OBJDIR)/link.lds
+DEPFILE = $(OBJDIR)/dep-pacbox
+SRC = arcade.c pacbox.c hardware.c z80.c
+
+SOURCES = $(SRC)
+OBJS := $(SRC:%.c=$(OBJDIR)/%.o)
+DIRS = .
+
+LDS := ../plugin.lds
+OUTPUT = $(OUTDIR)/pacbox.rock
+
+all: $(OUTPUT)
+
+ifndef SIMVER
+$(OBJDIR)/pacbox.elf: $(OBJS) $(LINKFILE)
+ @echo "LD "`basename $@`
+ @$(CC) $(GCCOPTS) -O -nostdlib -o $@ $(OBJS) -L$(BUILDDIR) -lplugin -lgcc \
+ -T$(LINKFILE) -Wl,-Map,$(OBJDIR)/pacbox.map
+
+$(OUTPUT): $(OBJDIR)/pacbox.elf
+ @echo "OBJCOPY "`basename $@`
+ @$(OC) -O binary $< $@
+else
+
+ifeq ($(SIMVER), x11)
+###################################################
+# This is the X11 simulator version
+
+$(OUTPUT): $(OBJS)
+ @echo "LD $<"
+ @$(CC) $(CFLAGS) -shared $(OBJS) -L$(BUILDDIR) -lplugin -o $@
+ifeq ($(findstring CYGWIN,$(UNAME)),CYGWIN)
+# 'x' must be kept or you'll have "Win32 error 5"
+# $ fgrep 5 /usr/include/w32api/winerror.h | head -1
+# #define ERROR_ACCESS_DENIED 5L
+else
+ @chmod -x $@
+endif
+
+else # end of x11-simulator
+ifeq ($(SIMVER), sdl)
+###################################################
+# This is the SDL simulator version
+
+$(OUTPUT): $(OBJS)
+ @echo "LD $<"
+ @$(CC) $(CFLAGS) -shared $(OBJS) -L$(BUILDDIR) -lplugin -o $@
+ifeq ($(findstring CYGWIN,$(UNAME)),CYGWIN)
+# 'x' must be kept or you'll have "Win32 error 5"
+# $ fgrep 5 /usr/include/w32api/winerror.h | head -1
+# #define ERROR_ACCESS_DENIED 5L
+else
+ @chmod -x $@
+endif
+
+else # end of sdl-simulator
+###################################################
+# This is the win32 simulator version
+DLLTOOLFLAGS = --export-all
+DLLWRAPFLAGS = -s --entry _DllMain@12 --target=i386-mingw32 -mno-cygwin
+
+$(OUTPUT): $(OBJS)
+ @echo "DLL "`basename $@`
+ @$(DLLTOOL) $(DLLTOOLFLAGS) -z $(OBJDIR)/$*.def $(OBJS)
+ @$(DLLWRAP) $(DLLWRAPFLAGS) --def $(OBJDIR)/$*.def $(OBJS) \
+ $(BUILDDIR)/libplugin.a -o $@
+ifeq ($(findstring CYGWIN,$(UNAME)),CYGWIN)
+# 'x' must be kept or you'll have "Win32 error 5"
+# $ fgrep 5 /usr/include/w32api/winerror.h | head -1
+# #define ERROR_ACCESS_DENIED 5L
+else
+ @chmod -x $@
+endif
+endif # end of win32-simulator
+endif
+endif # end of simulator section
+
+
+include $(TOOLSDIR)/make.inc
+
+# MEMORYSIZE should be passed on to this makefile with the chosen memory size
+# given in number of MB
+$(LINKFILE): $(LDS)
+ @echo "build "`basename $@`
+ @cat $< | $(CC) -DMEMORYSIZE=$(MEMORYSIZE) $(INCLUDES) $(TARGET) \
+ $(DEFINES) -E -P - >$@
+
+clean:
+ @echo "cleaning pacbox"
+ @rm -rf $(OBJDIR)/pacbox
+ @rm -f $(OBJDIR)/pacbox.* $(DEPFILE)
+
+-include $(DEPFILE)
+
diff --git a/apps/plugins/pacbox/arcade.c b/apps/plugins/pacbox/arcade.c
new file mode 100644
index 0000000..e7bf124
--- /dev/null
+++ b/apps/plugins/pacbox/arcade.c
@@ -0,0 +1,577 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#include "arcade.h"
+#include "hardware.h"
+#include <string.h>
+#include "plugin.h"
+
+extern struct plugin_api* rb;
+
+#ifndef HAVE_LCD_COLOR
+/* Convert RGB888 to 2-bit greyscale - logic taken from bmp2rb.c */
+static fb_data rgb_to_gray(unsigned int r, unsigned int g, unsigned int b)
+{
+ int brightness = ((3*r + 6*g + b) / 10);
+ return ((brightness & 0xc0) >> 6);
+}
+#endif
+
+unsigned char color_data_[256] = {
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x0b, 0x01,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x0b, 0x03,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x0b, 0x05,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x0b, 0x07,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x01, 0x09,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x0f, 0x00, 0x0e, 0x00, 0x01, 0x0c, 0x0f,
+ 0x00, 0x0e, 0x00, 0x0b, 0x00, 0x0c, 0x0b, 0x0e,
+ 0x00, 0x0c, 0x0f, 0x01, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x01, 0x02, 0x0f, 0x00, 0x07, 0x0c, 0x02,
+ 0x00, 0x09, 0x06, 0x0f, 0x00, 0x0d, 0x0c, 0x0f,
+ 0x00, 0x05, 0x03, 0x09, 0x00, 0x0f, 0x0b, 0x00,
+ 0x00, 0x0e, 0x00, 0x0b, 0x00, 0x0e, 0x00, 0x0b,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x0e, 0x01,
+ 0x00, 0x0f, 0x0b, 0x0e, 0x00, 0x0e, 0x00, 0x0f,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+unsigned char palette_data_[0x20] = {
+ 0x00, 0x07, 0x66, 0xef, 0x00, 0xf8, 0xea, 0x6f,
+ 0x00, 0x3f, 0x00, 0xc9, 0x38, 0xaa, 0xaf, 0xf6,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+enum {
+ Normal = 0x00,
+ FlipY = 0x01,
+ FlipX = 0x02,
+ FlipXY = 0x03
+};
+
+fb_data palette[256]; /* Color palette */
+int vchar_to_x_[1024];
+int vchar_to_y_[1024];
+
+void init_PacmanMachine(int dip)
+{
+ int i;
+
+ /* Initialize the CPU and the RAM */
+ z80_reset();
+ rb->memset( &ram_[0x4000], 0xFF, 0x1000 );
+
+ /* Initialize parameters */
+ port1_ = 0xFF;
+ port2_ = 0xFF;
+ coin_counter_ = 0;
+
+ /* Reset the machine */
+ reset_PacmanMachine();
+
+ /* Set the DIP switches to a default configuration */
+ setDipSwitches( dip );
+
+ /* Initialize the video character translation tables: video memory has a
+ very peculiar arrangement in Pacman so we precompute a few tables to
+ move around faster */
+
+ for( i=0x000; i<0x400; i++ ) {
+ int x, y;
+
+ if( i < 0x040 ) {
+ x = 29 - (i & 0x1F);
+ y = 34 + (i >> 5);
+ }
+ else if( i >= 0x3C0 ) {
+ x = 29 - (i & 0x1F);
+ y = ((i-0x3C0) >> 5);
+ }
+ else {
+ x = 27 - ((i-0x40) >> 5);
+ y = 2 + ((i-0x40) & 0x1F);
+ }
+ vchar_to_x_[i] = x;
+ vchar_to_y_[i] = y;
+ if( (y >= 0) && (y < 36) && (x >= 0) && (x < 28) )
+ vchar_to_i_[i] = y*28 + x;
+ else
+ vchar_to_i_[i] = 0x3FF;
+ }
+}
+
+void reset_PacmanMachine(void)
+{
+ int i;
+
+ z80_reset();
+ output_devices_ = 0;
+ interrupt_vector_ = 0;
+
+ rb->memset( ram_+0x4000, 0, 0x1000 );
+ rb->memset( color_mem_, 0, sizeof(color_mem_) );
+ rb->memset( video_mem_, 0, sizeof(video_mem_) );
+ rb->memset( dirty_, 0, sizeof(dirty_) );
+
+ for( i=0; i<8; i++ ) {
+ sprites_[i].color = 0;
+ sprites_[i].x = ScreenWidth;
+ }
+}
+
+/*
+ Run the machine for one frame.
+*/
+int run(void)
+{
+ /* Run until the CPU has executed the number of cycles per frame
+ (the function returns the number of "extra" cycles spent by the
+ last instruction but that is not really important here) */
+
+ unsigned extraCycles = z80_run( CpuCyclesPerFrame );
+
+ /* Reset the CPU cycle counter to make sure it doesn't overflow,
+ also take into account the extra cycles from the previous run */
+
+ setCycles( extraCycles );
+
+ /* If interrupts are enabled, force a CPU interrupt with the vector
+ set by the program */
+
+ if( output_devices_ & InterruptEnabled ) {
+ z80_interrupt( interrupt_vector_ );
+ }
+
+ return 0;
+}
+
+/** Returns the status of the coin lockout door. */
+unsigned char getCoinLockout(void) {
+ return output_devices_ & CoinLockout ? 1 : 0;
+}
+
+static void decodeCharByte( unsigned char b, unsigned char * charbuf, int charx, int chary, int charwidth )
+{
+ int i;
+
+ for( i=3; i>=0; i-- ) {
+ charbuf[charx+(chary+i)*charwidth] = (b & 1) | ((b >> 3) & 2);
+ b >>= 1;
+ }
+}
+
+static void decodeCharLine( unsigned char * src, unsigned char * charbuf, int charx, int chary, int charwidth )
+{
+ int x;
+
+ for( x=7; x>=0; x-- ) {
+ decodeCharByte( *src++, charbuf, x+charx, chary, charwidth );
+ }
+}
+
+static void decodeCharSet( unsigned char * mem, unsigned char * charset )
+{
+ int i;
+
+ for( i=0; i<256; i++ ) {
+ unsigned char * src = mem + 16*i;
+ unsigned char * dst = charset + 64*i;
+
+ decodeCharLine( src, dst, 0, 4, 8 );
+ decodeCharLine( src+8, dst, 0, 0, 8 );
+ }
+}
+
+static void decodeSprites( unsigned char * mem, unsigned char * sprite_data )
+{
+ int i;
+
+ for( i=0; i<64; i++ ) {
+ unsigned char * src = mem + i*64;
+ unsigned char * dst = sprite_data + 256*i;
+
+ decodeCharLine( src , dst, 8, 12, 16 );
+ decodeCharLine( src+ 8, dst, 8, 0, 16 );
+ decodeCharLine( src+16, dst, 8, 4, 16 );
+ decodeCharLine( src+24, dst, 8, 8, 16 );
+ decodeCharLine( src+32, dst, 0, 12, 16 );
+ decodeCharLine( src+40, dst, 0, 0, 16 );
+ decodeCharLine( src+48, dst, 0, 4, 16 );
+ decodeCharLine( src+56, dst, 0, 8, 16 );
+ }
+}
+
+/*
+ Decode one byte from the encoded color palette.
+
+ An encoded palette byte contains RGB information bit-packed as follows:
+
+ bit: 7 6 5 4 3 2 1 0
+ color: b b g g g r r r
+*/
+static unsigned decodePaletteByte( unsigned char value )
+{
+ unsigned bit0, bit1, bit2;
+ unsigned red, green, blue;
+
+ bit0 = (value >> 0) & 0x01;
+ bit1 = (value >> 1) & 0x01;
+ bit2 = (value >> 2) & 0x01;
+ red = 0x21 * bit0 + 0x47 * bit1 + 0x97 * bit2;
+
+ bit0 = (value >> 3) & 0x01;
+ bit1 = (value >> 4) & 0x01;
+ bit2 = (value >> 5) & 0x01;
+ green = 0x21 * bit0 + 0x47 * bit1 + 0x97 * bit2;
+
+ bit0 = 0;
+ bit1 = (value >> 6) & 0x01;
+ bit2 = (value >> 7) & 0x01;
+ blue = 0x21 * bit0 + 0x47 * bit1 + 0x97 * bit2;
+
+ return (blue << 16 ) | (green << 8) | red;
+}
+
+void decodeROMs(void)
+{
+ unsigned decoded_palette[0x20];
+ unsigned c;
+
+ int i;
+
+ decodeCharSet( charset_rom_, charmap_ );
+ decodeSprites( spriteset_rom_, spritemap_ );
+
+ for( i=0x00; i<0x20; i++ ) {
+ decoded_palette[i] = decodePaletteByte( palette_data_[i] );
+ }
+ for( i=0; i<256; i++ ) {
+ c = decoded_palette[ color_data_[i] & 0x0F ];
+#ifdef HAVE_LCD_COLOR
+ palette[i] = LCD_RGBPACK((unsigned char) (c),
+ (unsigned char) (c >> 8),
+ (unsigned char) (c >> 16));
+#else
+ palette[i] = rgb_to_gray(c, c >> 8, c >> 16);
+#endif
+ }
+}
+
+void getDeviceInfo( enum InputDevice device, unsigned char * mask, unsigned char ** port )
+{
+ static unsigned char MaskInfo[] = {
+ 0x01 , // Joy1_Up
+ 0x02 , // Joy1_Left
+ 0x04 , // Joy1_Right
+ 0x08 , // Joy1_Down
+ 0x10 , // Switch_RackAdvance
+ 0x20 , // CoinSlot_1
+ 0x40 , // CoinSlot_2
+ 0x80 , // Switch_AddCredit
+ 0x01 , // Joy2_Up
+ 0x02 , // Joy2_Left
+ 0x04 , // Joy2_Right
+ 0x08 , // Joy2_Down
+ 0x10 , // Switch_Test
+ 0x20 , // Key_OnePlayer
+ 0x40 , // Key_TwoPlayers
+ 0x80 // Switch_CocktailMode
+ };
+
+ *mask = MaskInfo[device];
+
+ switch( device ) {
+ case Joy1_Up:
+ case Joy1_Left:
+ case Joy1_Right:
+ case Joy1_Down:
+ case Switch_RackAdvance:
+ case CoinSlot_1:
+ case CoinSlot_2:
+ case Switch_AddCredit:
+ *port = &port1_;
+ break;
+ case Joy2_Up:
+ case Joy2_Left:
+ case Joy2_Right:
+ case Joy2_Down:
+ case Switch_Test:
+ case Key_OnePlayer:
+ case Key_TwoPlayers:
+ case Switch_CocktailMode:
+ *port = &port2_;
+ break;
+ default:
+ *port = 0;
+ break;
+ }
+}
+
+enum InputDeviceMode getDeviceMode( enum InputDevice device )
+{
+ unsigned char mask;
+ unsigned char * port;
+
+ getDeviceInfo( device, &mask, &port );
+
+ return (*port & mask) == 0 ? DeviceOn : DeviceOff;
+}
+
+/*
+ Fire an input event, telling the emulator for example
+ that the joystick has been released from the down position.
+*/
+void setDeviceMode( enum InputDevice device, enum InputDeviceMode mode )
+{
+ if( (getCoinLockout() == 0) && ((device == CoinSlot_1)||(device == CoinSlot_2)||(device == Switch_AddCredit)) ) {
+ // Coin slots are locked, ignore command and exit
+ return;
+ }
+
+ unsigned char mask;
+ unsigned char * port;
+
+ getDeviceInfo( device, &mask, &port );
+
+ if( mode == DeviceOn )
+ *port &= ~mask;
+ else if( mode == DeviceOff )
+ *port |= mask;
+ else if( mode == DeviceToggle )
+ *port ^= mask;
+}
+
+void setDipSwitches( unsigned value ) {
+ dip_switches_ = (unsigned char) value;
+
+ setDeviceMode( Switch_RackAdvance, value & DipRackAdvance_Auto ? DeviceOn : DeviceOff );
+ setDeviceMode( Switch_Test, value & DipMode_Test ? DeviceOn : DeviceOff );
+ setDeviceMode( Switch_CocktailMode, value & DipCabinet_Cocktail ? DeviceOn : DeviceOff );
+}
+
+unsigned getDipSwitches(void) {
+ unsigned result = dip_switches_;
+
+ if( getDeviceMode(Switch_RackAdvance) == DeviceOn ) result |= DipRackAdvance_Auto;
+ if( getDeviceMode(Switch_Test) == DeviceOn ) result |= DipMode_Test;
+ if( getDeviceMode(Switch_CocktailMode) == DeviceOn ) result |= DipCabinet_Cocktail;
+
+ return result;
+}
+
+static inline void drawChar( unsigned char * buffer, int index, int ox, int oy, int color )
+{
+ buffer += ox + oy*224; // Make the buffer point to the character position
+ index *= 64; // Make the index point to the character offset into the character table
+ color = (color & 0x3F)*4;
+ int x,y;
+
+ if( output_devices_ & FlipScreen ) {
+ // Flip character
+ buffer += 7*ScreenWidth;
+ for( y=0; y<8; y++ ) {
+ for( x=7; x>=0; x-- ) {
+ buffer[x] = charmap_[ index++ ] + color;
+ }
+ buffer -= ScreenWidth; // Go to the next line
+ }
+ }
+ else {
+ for( y=0; y<8; y++ ) {
+ for( x=0; x<=7; x++ ) {
+ buffer[x] = charmap_[ index++ ] + color;
+ }
+ buffer += ScreenWidth; // Go to the next line
+ }
+ }
+}
+
+inline void drawSprite( unsigned char * buffer, int index )
+{
+ struct PacmanSprite ps = sprites_[index];
+ int x,y;
+
+ // Exit now if sprite not visible at all
+ if( (ps.color == 0) || (ps.x >= ScreenWidth) || (ps.y < 16) || (ps.y >= (ScreenHeight-32)) ) {
+ return;
+ }
+
+ // Clip the sprite coordinates to cut the parts that fall off the screen
+ int start_x = (ps.x < 0) ? 0 : ps.x;
+ int end_x = (ps.x < (ScreenWidth-16)) ? ps.x+16 : ScreenWidth;
+
+ // Prepare variables for drawing
+ int color = (ps.color & 0x3F)*4;
+ unsigned char * spritemap_base = spritemap_ + ((ps.n & 0x3F)*256);
+
+ buffer += ScreenWidth*ps.y;
+
+ // Draw the 16x16 sprite
+ if( ps.mode == 0 ) { // Normal
+ // Draw the 16x16 sprite
+ for( y=0; y<16; y++ ) {
+ char* s = &spritemap_base[start_x-ps.x+y*16];
+ for( x=start_x; x<end_x; x++ ) {
+ int c = *(s++);
+ if( c ) {
+ buffer[x] = c + color;
+ }
+ }
+ buffer += ScreenWidth;
+ }
+ } else if( ps.mode == 1 ) { // Flip Y
+ for( y=0; y<16; y++ ) {
+ char* s = &spritemap_base[start_x-ps.x+(15-y)*16];
+ for( x=start_x; x<end_x; x++ ) {
+ int c = *(s++);
+ if( c ) {
+ buffer[x] = c + color;
+ }
+ }
+ buffer += ScreenWidth;
+ }
+ } else if( ps.mode == 2 ) { // Flip X
+ for( y=0; y<16; y++ ) {
+ char* s = &spritemap_base[15-start_x+ps.x+y*16];
+ for( x=start_x; x<end_x; x++ ) {
+ int c = *(s--);
+ if( c ) {
+ buffer[x] = c + color;
+ }
+ }
+ buffer += ScreenWidth;
+ }
+ } else { // Flip X and Y
+ for( y=0; y<16; y++ ) {
+ char* s = &spritemap_base[15-start_x+ps.x+(15-y)*16];
+ for( x=start_x; x<end_x; x++ ) {
+ int c = *(s--);
+ if( c ) {
+ buffer[x] = c + color;
+ }
+ }
+ buffer += ScreenWidth;
+ }
+ }
+}
+
+/*
+ Draw the video into the specified buffer.
+*/
+bool renderBackground( unsigned char * buffer )
+{
+ unsigned char * video = video_mem_;
+ unsigned char * color = color_mem_;
+ unsigned char * dirty = dirty_;
+ int x,y;
+ bool changed=false;
+
+ // Draw the background first...
+ if( output_devices_ & FlipScreen ) {
+ for( y=ScreenHeight-CharHeight; y>=0; y-=CharHeight ) {
+ for( x=ScreenWidth-CharWidth; x>=0; x-=CharWidth ) {
+ if (*dirty) {
+ drawChar( buffer, *video++, x, y, *color++ );
+ *(dirty++)=0;
+ changed=true;
+ } else {
+ dirty++;
+ video++;
+ color++;
+ }
+ }
+ }
+ }
+ else {
+ for( y=0; y<ScreenHeight; y+=CharHeight ) {
+ for( x=0; x<ScreenWidth; x+=CharWidth ) {
+ if (*dirty) {
+ drawChar( buffer, *video++, x, y, *color++ );
+ *(dirty++)=0;
+ changed=true;
+ } else {
+ dirty++;
+ video++;
+ color++;
+ }
+ }
+ }
+ }
+
+ return changed;
+}
+
+void renderSprites( unsigned char * buffer )
+{
+ int i;
+
+ // ...then add the sprites
+ for( i=7; i>=0; i-- ) {
+ drawSprite( buffer, i );
+ }
+}
+
+/* Enables/disables the speed hack. */
+int setSpeedHack( int enabled )
+{
+ int result = 0;
+
+ if( enabled ) {
+ if( (ram_[0x180B] == 0xBE) && (ram_[0x1FFD] == 0x00) ) {
+ // Patch the ROM to activate the speed hack
+ ram_[0x180B] = 0x01; // Activate speed hack
+ ram_[0x1FFD] = 0xBD; // Fix ROM checksum
+
+ result = 1;
+ }
+ }
+ else {
+ if( (ram_[0x180B] == 0x01) && (ram_[0x1FFD] == 0xBD) ) {
+ // Restore the patched ROM locations
+ ram_[0x180B] = 0xBE;
+ ram_[0x1FFD] = 0x00;
+
+ result = 1;
+ }
+ }
+
+ return result;
+}
diff --git a/apps/plugins/pacbox/arcade.h b/apps/plugins/pacbox/arcade.h
new file mode 100644
index 0000000..5de2517
--- /dev/null
+++ b/apps/plugins/pacbox/arcade.h
@@ -0,0 +1,199 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#ifndef ARCADE_H_
+#define ARCADE_H_
+
+#include "plugin.h"
+#include "z80.h"
+#include "hardware.h"
+
+extern fb_data palette[256]; /* Color palette in native Rockbox format */
+
+/**
+ Pacman sprite properties.
+
+ This information is only needed by applications that want to do their own
+ sprite rendering, as the renderVideo() function already draws the sprites.
+
+ @see PacmanMachine::renderVideo
+*/
+
+/** Machine hardware data */
+enum {
+ ScreenWidth = 224,
+ ScreenHeight = 288,
+ ScreenWidthChars = 28,
+ ScreenHeightChars = 36,
+ CharWidth = 8,
+ CharHeight = 8,
+ VideoFrequency = 60,
+ CpuClock = 3072000,
+ SoundClock = 96000, // CPU clock divided by 32
+ CpuCyclesPerFrame = CpuClock / VideoFrequency
+};
+
+/** Input devices and switches */
+enum InputDevice {
+ Joy1_Up = 0,
+ Joy1_Left,
+ Joy1_Right,
+ Joy1_Down,
+ Switch_RackAdvance,
+ CoinSlot_1,
+ CoinSlot_2,
+ Switch_AddCredit,
+ Joy2_Up,
+ Joy2_Left,
+ Joy2_Right,
+ Joy2_Down,
+ Switch_Test,
+ Key_OnePlayer,
+ Key_TwoPlayers,
+ Switch_CocktailMode
+};
+
+/** Input device mode */
+enum InputDeviceMode {
+ DeviceOn,
+ DevicePushed = DeviceOn,
+ DeviceOff,
+ DeviceReleased = DeviceOff,
+ DeviceToggle
+};
+
+/** DIP switches */
+enum {
+ DipPlay_Free = 0x00, // Coins per play
+ DipPlay_OneCoinOneGame = 0x01,
+ DipPlay_OneCoinTwoGames = 0x02,
+ DipPlay_TwoCoinsOneGame = 0x03,
+ DipPlay_Mask = 0x03,
+ DipLives_1 = 0x00, // Lives per game
+ DipLives_2 = 0x04,
+ DipLives_3 = 0x08,
+ DipLives_5 = 0x0C,
+ DipLives_Mask = 0x0C,
+ DipBonus_10000 = 0x00, // Bonus life
+ DipBonus_15000 = 0x10,
+ DipBonus_20000 = 0x20,
+ DipBonus_None = 0x30,
+ DipBonus_Mask = 0x30,
+ DipDifficulty_Normal = 0x40, // Difficulty
+ DipDifficulty_Hard = 0x00,
+ DipDifficulty_Mask = 0x40,
+ DipGhostNames_Normal = 0x80, // Ghost names
+ DipGhostNames_Alternate = 0x00,
+ DipGhostNames_Mask = 0x80,
+ DipMode_Play = 0x0000, // Play/test mode
+ DipMode_Test = 0x0100,
+ DipMode_Mask = 0x0100,
+ DipCabinet_Upright = 0x0000, // Cabinet upright/cocktail
+ DipCabinet_Cocktail = 0x0200,
+ DipCabinet_Mask = 0x0200,
+ DipRackAdvance_Off = 0x0000, // Automatic level advance
+ DipRackAdvance_Auto = 0x0400,
+ DipRackAdvance_Mask = 0x0400
+};
+
+void init_PacmanMachine(int dip);
+int run(void);
+void reset_PacmanMachine(void);
+void decodeROMs(void);
+
+/**
+ Tells the emulator that the status of an input device has changed.
+*/
+void setDeviceMode( enum InputDevice device, enum InputDeviceMode mode );
+
+/**
+ Returns the value of the DIP switches.
+*/
+unsigned getDipSwitches(void);
+
+/**
+ Sets the value of the DIP switches that control several game settings
+ (see the Dip... constants above).
+
+ Most of the DIP switches are read at program startup and take effect
+ only after a machine reset.
+*/
+void setDipSwitches( unsigned value );
+
+/**
+ Draws the current video into the specified buffer.
+
+ The buffer must be at least 224*288 bytes long. Pixels are stored in
+ left-to-right/top-to-bottom order starting from the upper left corner.
+ There is one byte per pixel, containing an index into the color palette
+ returned by getPalette().
+
+ It's up to the application to display the buffer to the user. The
+ code might look like this:
+ <BLOCKQUOTE>
+ <PRE>
+ @@ unsigned char video_buffer[ PacmanMachine::ScreenWidth * PacmanMachine::ScreenHeight ];
+ @@ unsigned char * vbuf = video_buffer;
+ @@ const unsigned * palette = arcade.getPalette();
+ @@
+ @@ arcade.renderVideo( vbuf );
+ @@
+ @@ for( int y=0; y<PacmanMachine::ScreenHeight; y++ ) {
+ @@ for( int x=0; x<PacmanMachine::ScreenWidth; x++ ) {
+ @@ unsigned color = palette[ *vbuf++ ];
+ @@ unsigned char red = color & 0xFF;
+ @@ unsigned char green = (color >> 8) & 0xFF;
+ @@ unsigned char blue = (color >> 16) & 0xFF;
+ @@
+ @@ setPixel( x, y, red, green, blue );
+ @@ }
+ @@ }
+ </PRE>
+ </BLOCKQUOTE>
+
+*/
+bool renderBackground( unsigned char * buffer );
+void renderSprites( unsigned char * buffer );
+
+/**
+ Enables/disables a common speed hack that allows Pacman to
+ move four times faster than the ghosts.
+
+ @param enabled true to enabled the hack, false to disable
+
+ @return 0 if successful, otherwise the patch could not be applied
+ (probably because the loaded ROM set does not support it)
+*/
+int setSpeedHack( int enabled );
+
+/* Implementation of the Z80 Environment interface */
+unsigned char readByteHigh( unsigned addr );
+
+void writeByte( unsigned, unsigned char );
+
+unsigned char readPort( unsigned port );
+
+void writePort( unsigned, unsigned char );
+
+#endif // ARCADE_H_
diff --git a/apps/plugins/pacbox/hardware.c b/apps/plugins/pacbox/hardware.c
new file mode 100644
index 0000000..3cc4858
--- /dev/null
+++ b/apps/plugins/pacbox/hardware.c
@@ -0,0 +1,197 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#include "plugin.h"
+#include "hardware.h"
+
+extern struct plugin_api* rb;
+
+/* The main data for Pacman */
+
+unsigned char ram_[20*1024] IBSS_ATTR; // ROM (16K) and RAM (4K)
+unsigned char charset_rom_[4*1024] IBSS_ATTR; // Character set ROM (4K)
+unsigned char spriteset_rom_[4*1024] IBSS_ATTR; // Sprite set ROM (4K)
+unsigned char dirty_[1024] IBSS_ATTR;
+unsigned char video_mem_[1024] IBSS_ATTR; // Video memory (1K)
+unsigned char color_mem_[1024] IBSS_ATTR; // Color memory (1K)
+unsigned char charmap_[256*8*8]; /* Character data for 256 8x8 characters */
+unsigned char spritemap_[64*16*16]; /* Sprite data for 64 16x16 sprites */
+unsigned char output_devices_ IBSS_ATTR; /* Output flip-flops set by the game program */
+unsigned char interrupt_vector_ IBSS_ATTR;
+unsigned coin_counter_ IBSS_ATTR;
+unsigned char port1_ IBSS_ATTR;
+unsigned char port2_ IBSS_ATTR;
+unsigned char dip_switches_ IBSS_ATTR;
+
+/* Internal tables and structures for faster access to data */
+struct PacmanSprite sprites_[8]; /* Sprites */
+short vchar_to_i_[1024];
+
+
+/*
+ For Z80 Environment: write a byte to memory.
+*/
+void writeByte( unsigned addr, unsigned char b )
+{
+ addr &= 0x7FFF;
+
+ if( addr < 0x4000 ) {
+ // This is a ROM address, do not write into it!
+ }
+ else if( addr < 0x4400 ) {
+ // Video memory
+ if (ram_[addr] != b) {
+ int x = vchar_to_i_[addr-0x4000];
+ ram_[addr] = b;
+ dirty_[x] = 1;
+ video_mem_[x] = b;
+ }
+ }
+ else if( addr < 0x4800 ) {
+ // Color memory
+ if (ram_[addr] != b) {
+ int x = vchar_to_i_[addr-0x4400];
+ ram_[addr] = b;
+ dirty_[x] = 1;
+ color_mem_[x] = b;
+ }
+ }
+ else if( addr < 0x4FF0 ) {
+ // Standard memory
+ ram_[addr] = b;
+ }
+ else if( addr < 0x5000 ) {
+ // Sprites
+ ram_[addr] = b;
+
+ unsigned idx = (addr - 0x4FF0) / 2;
+
+ if( addr & 1 ) {
+ sprites_[ idx ].color = b;
+ }
+ else {
+ sprites_[ idx ].n = b >> 2;
+ sprites_[ idx ].mode = b & 0x03;
+ }
+ }
+ else {
+ // Memory mapped ports
+ switch( addr ) {
+ case 0x5000:
+ // Interrupt enable
+ setOutputFlipFlop( InterruptEnabled, b & 0x01 );
+ break;
+ case 0x5001:
+ // Sound enable
+ setOutputFlipFlop( SoundEnabled, b & 0x01 );
+ break;
+ case 0x5002:
+ // Aux board enable?
+ break;
+ case 0x5003:
+ // Flip screen
+ setOutputFlipFlop( FlipScreen, b & 0x01 );
+ break;
+ case 0x5004:
+ // Player 1 start light
+ setOutputFlipFlop( PlayerOneLight, b & 0x01 );
+ break;
+ case 0x5005:
+ // Player 2 start light
+ setOutputFlipFlop( PlayerTwoLight, b & 0x01 );
+ break;
+ case 0x5006:
+ // Coin lockout: bit 0 is used to enable/disable the coin insert slots
+ // (0=disable).
+ // The coin slot is enabled at startup and (temporarily) disabled when
+ // the maximum number of credits (99) is inserted.
+ setOutputFlipFlop( CoinLockout, b & 0x01 );
+ break;
+ case 0x5007:
+ // Coin meter (coin counter incremented on 0/1 edge)
+ if( (output_devices_ & CoinMeter) == 0 && (b & 0x01) != 0 )
+ coin_counter_++;
+ setOutputFlipFlop( CoinMeter, b & 0x01 );
+ break;
+ case 0x50c0:
+ // Watchdog reset
+ break;
+ default:
+ if( addr >= 0x5040 && addr < 0x5060 ) {
+ // Sound registers
+ //SOUND sound_chip_.setRegister( addr-0x5040, b );
+ }
+ else if( addr >= 0x5060 && addr < 0x5070 ) {
+ // Sprite coordinates, x/y pairs for 8 sprites
+ unsigned idx = (addr-0x5060) / 2;
+
+ if( addr & 1 ) {
+ sprites_[ idx ].y = 272 - b + 1;
+ }
+ else {
+ sprites_[ idx ].x = 240 - b - 1;
+
+ if( idx <= 2 ) {
+ // In Pacman the first few sprites must be further offset
+ // to the left to get a correct display (is this a hack?)
+ sprites_[ idx ].x -= 1;
+ }
+ }
+ }
+ break;
+ }
+ }
+}
+
+/*
+ For Z80 Environment: read from a port.
+
+ Note: all ports in Pacman are memory mapped so they are read with readByte().
+*/
+unsigned char readPort( unsigned port )
+{
+ (void)port;
+ return 0;
+}
+
+/*
+ For Z80 Environment: write to a port.
+*/
+void writePort( unsigned addr, unsigned char b )
+{
+ if( addr == 0 ) {
+ // Sets the interrupt vector for the next CPU interrupt
+ interrupt_vector_ = b;
+ }
+}
+
+void setOutputFlipFlop( unsigned char bit, unsigned char value )
+{
+ if( value ) {
+ output_devices_ |= bit;
+ }
+ else {
+ output_devices_ &= ~bit;
+ }
+}
diff --git a/apps/plugins/pacbox/hardware.h b/apps/plugins/pacbox/hardware.h
new file mode 100644
index 0000000..9b225ad
--- /dev/null
+++ b/apps/plugins/pacbox/hardware.h
@@ -0,0 +1,141 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#ifndef _HARDWARE_H
+#define _HARDWARE_H
+
+extern unsigned char ram_[20*1024]; // ROM (16K) and RAM (4K)
+extern unsigned char charset_rom_[4*1024]; // Character set ROM (4K)
+extern unsigned char spriteset_rom_[4*1024]; // Sprite set ROM (4K)
+extern unsigned char dirty_[1024];
+extern unsigned char video_mem_[1024]; // Video memory (1K)
+extern unsigned char color_mem_[1024]; // Color memory (1K)
+extern unsigned char charmap_[256*8*8]; /* Character data for 256 8x8 characters */
+extern unsigned char spritemap_[64*16*16]; /* Sprite data for 64 16x16 sprites */
+extern unsigned char output_devices_; /* Output flip-flops set by the game program */
+extern unsigned char interrupt_vector_;
+extern unsigned coin_counter_;
+extern unsigned char port1_;
+extern unsigned char port2_;
+extern unsigned char dip_switches_;
+
+/* Output flip-flops */
+enum {
+ FlipScreen = 0x01,
+ PlayerOneLight = 0x02,
+ PlayerTwoLight = 0x04,
+ InterruptEnabled = 0x08,
+ SoundEnabled = 0x10,
+ CoinLockout = 0x20,
+ CoinMeter = 0x40,
+ AuxBoardEnabled = 0x80
+};
+
+struct PacmanSprite
+{
+ int mode; /** Display mode (normal or flipped) */
+ int x; /** X coordinate */
+ int y; /** Y coordinate */
+ int n; /** Shape (from 0 to 63) */
+ int color; /** Base color (0=not visible) */
+};
+
+/* Internal tables and structures for faster access to data */
+extern struct PacmanSprite sprites_[8]; /* Sprites */
+extern short vchar_to_i_[1024];
+
+void writeByte(unsigned addr, unsigned char b);
+unsigned char readPort( unsigned port );
+void writePort( unsigned addr, unsigned char b );
+void setOutputFlipFlop( unsigned char bit, unsigned char value );
+
+/*
+ For Z80 Environment: read a byte from high memory addresses (i.e. the
+ memory-mapped registers)
+*/
+static inline unsigned char readByte( unsigned addr )
+{
+ addr &= 0xFFFF;
+
+ if (addr < sizeof(ram_))
+ return ram_[addr];
+
+ // Address is not in RAM, check to see if it's a memory mapped register
+ switch( addr & 0xFFC0 ) {
+ // IN0
+ case 0x5000:
+ // bit 0 : up
+ // bit 1 : left
+ // bit 2 : right
+ // bit 3 : down
+ // bit 4 : switch: advance to next level
+ // bit 5 : coin 1
+ // bit 6 : coin 2
+ // bit 7 : credit (same as coin but coin counter is not incremented)
+ return port1_;
+ // IN1
+ case 0x5040:
+ // bit 0 : up (2nd player)
+ // bit 1 : left (2nd player)
+ // bit 2 : right (2nd player)
+ // bit 3 : down (2nd player)
+ // bit 4 : switch: rack test -> 0x10=off, 0=on
+ // bit 5 : start 1
+ // bit 6 : start 2
+ // bit 7 : cabinet -> 0x80=upright, 0x00=table
+ return port2_;
+ // DSW1
+ case 0x5080:
+ // bits 0,1 : coinage -> 0=free play, 1=1 coin/play, 2=1 coin/2 play, 3=2 coin/1 play
+ // bits 2,3 : lives -> 0x0=1, 0x4=2, 0x8=3, 0xC=5
+ // bits 4,5 : bonus life -> 0=10000, 0x10=15000, 0x20=20000, 0x30=none
+ // bit 6 : jumper pad: difficulty -> 0x40=normal, 0=hard
+ // bit 7 : jumper pad: ghost name -> 0x80=normal, 0=alternate
+ return dip_switches_;
+ // Watchdog reset
+ case 0x50C0:
+ break;
+ }
+
+ return 0xFF;
+}
+
+/* Reads a 16 bit word from memory at the specified address. */
+static inline unsigned readWord( unsigned addr ) {
+ addr &= 0xFFFF;
+
+ if (addr < (sizeof(ram_)-1)) {
+ return ram_[addr] | ((ram_[addr+1]) << 8);
+ } else {
+ return readByte(addr) | (((unsigned)readByte(addr+1)) << 8);
+ }
+}
+
+/* Writes a 16 bit word to memory at the specified address. */
+static inline void writeWord( unsigned addr, unsigned value ) {
+ writeByte( addr, value & 0xFF );
+ writeByte( addr+1, (value >> 8) & 0xFF );
+}
+
+#endif
diff --git a/apps/plugins/pacbox/pacbox.c b/apps/plugins/pacbox/pacbox.c
new file mode 100644
index 0000000..b8625ee
--- /dev/null
+++ b/apps/plugins/pacbox/pacbox.c
@@ -0,0 +1,534 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#include "plugin.h"
+#include "arcade.h"
+
+PLUGIN_HEADER
+
+#ifdef USE_IRAM
+extern char iramcopy[];
+extern char iramstart[];
+extern char iramend[];
+extern char iedata[];
+extern char iend[];
+#endif
+
+/* How many video frames (out of a possible 60) we display each second */
+#define FPS 20
+
+#if CONFIG_KEYPAD == IPOD_4G_PAD
+
+#define PACMAN_UP BUTTON_RIGHT
+#define PACMAN_DOWN BUTTON_LEFT
+#define PACMAN_LEFT BUTTON_MENU
+#define PACMAN_RIGHT BUTTON_PLAY
+#define PACMAN_1UP BUTTON_SELECT
+#define PACMAN_COIN BUTTON_SELECT
+
+#elif CONFIG_KEYPAD == IRIVER_H100_PAD || CONFIG_KEYPAD == IRIVER_H300_PAD
+
+#define PACMAN_UP BUTTON_RIGHT
+#define PACMAN_DOWN BUTTON_LEFT
+#define PACMAN_LEFT BUTTON_UP
+#define PACMAN_RIGHT BUTTON_DOWN
+#define PACMAN_1UP BUTTON_SELECT
+#define PACMAN_2UP BUTTON_ON
+#define PACMAN_COIN BUTTON_REC
+#define PACMAN_MENU BUTTON_MODE
+
+#elif CONFIG_KEYPAD == GIGABEAT_PAD
+
+#define PACMAN_UP BUTTON_UP
+#define PACMAN_DOWN BUTTON_DOWN
+#define PACMAN_LEFT BUTTON_LEFT
+#define PACMAN_RIGHT BUTTON_RIGHT
+#define PACMAN_1UP BUTTON_SELECT
+#define PACMAN_2UP BUTTON_POWER
+#define PACMAN_COIN BUTTON_A
+#define PACMAN_MENU BUTTON_MENU
+
+#elif CONFIG_KEYPAD == IAUDIO_X5_PAD
+
+#define PACMAN_UP BUTTON_RIGHT
+#define PACMAN_DOWN BUTTON_LEFT
+#define PACMAN_LEFT BUTTON_UP
+#define PACMAN_RIGHT BUTTON_DOWN
+#define PACMAN_1UP BUTTON_SELECT
+#define PACMAN_2UP BUTTON_POWER
+#define PACMAN_COIN BUTTON_REC
+#define PACMAN_MENU BUTTON_PLAY
+
+#endif
+
+#if (LCD_HEIGHT >= 288)
+#define XOFS ((LCD_WIDTH-224)/2)
+#define YOFS ((LCD_HEIGHT-288)/2)
+#elif (LCD_WIDTH >= 288)
+#define XOFS ((LCD_WIDTH-288)/2)
+#define YOFS ((LCD_HEIGHT-224)/2)
+#elif (LCD_WIDTH >= 220)
+#define XOFS ((LCD_WIDTH-(288*3/4))/2)
+#define YOFS ((LCD_HEIGHT-(224*3/4))/2)
+#elif (LCD_WIDTH >= 144)
+#define XOFS ((LCD_WIDTH-288/2)/2)
+#define YOFS ((LCD_HEIGHT-224/2)/2)
+#endif
+
+struct plugin_api* rb;
+
+unsigned framesPerSecond = VideoFrequency;
+unsigned long frame_counter = 0;
+
+struct pacman_settings {
+ int difficulty;
+ int numlives;
+ int bonus;
+ int ghostnames;
+ int showfps;
+};
+
+struct pacman_settings settings;
+
+bool loadFile( const char * name, unsigned char * buf, int len )
+{
+ char filename[MAX_PATH];
+
+ rb->snprintf(filename,sizeof(filename),"/.rockbox/pacman/%s",name);
+
+ int fd = rb->open( filename, O_RDONLY);
+
+ if( fd < 0 ) {
+ return false;
+ }
+
+ int n = rb->read( fd, buf, len);
+
+ rb->close( fd );
+
+ if( n != len ) {
+ return false;
+ }
+
+ return true;
+}
+
+bool loadROMS( void )
+{
+ bool romsLoaded = false;
+
+ romsLoaded = loadFile( "pacman.6e", ram_, 0x1000) &&
+ loadFile( "pacman.6f", ram_+0x1000, 0x1000) &&
+ loadFile( "pacman.6h", ram_+0x2000, 0x1000) &&
+ loadFile( "pacman.6j", ram_+0x3000, 0x1000) &&
+ loadFile( "pacman.5e", charset_rom_, 0x1000) &&
+ loadFile( "pacman.5f", spriteset_rom_, 0x1000);
+
+ if( romsLoaded ) {
+ decodeROMs();
+ reset_PacmanMachine();
+ }
+
+ return romsLoaded;
+}
+
+/* A buffer to render Pacman's 244x288 screen into */
+unsigned char background[ScreenWidth*ScreenHeight] __attribute__ ((aligned (4)));
+unsigned char video_buffer[ScreenWidth*ScreenHeight] __attribute__ ((aligned (4)));
+
+long start_time;
+long sleep_counter = 0;
+long video_frames = 0;
+
+int dipDifficulty[] = { DipDifficulty_Normal, DipDifficulty_Hard };
+int dipLives[] = { DipLives_1, DipLives_2, DipLives_3, DipLives_5 };
+int dipBonus[] = { DipBonus_10000, DipBonus_15000, DipBonus_20000, DipBonus_None };
+int dipGhostNames[] = { DipGhostNames_Normal, DipGhostNames_Alternate };
+
+int settings_to_dip(struct pacman_settings settings)
+{
+ return ( DipPlay_OneCoinOneGame |
+ DipCabinet_Upright |
+ DipMode_Play |
+ DipRackAdvance_Off |
+
+ dipDifficulty[settings.difficulty] |
+ dipLives[settings.numlives] |
+ dipBonus[settings.bonus] |
+ dipGhostNames[settings.ghostnames]
+ );
+}
+
+
+
+int pacbox_menu_cb(int key, int m)
+{
+ (void)m;
+ switch(key)
+ {
+#ifdef MENU_ENTER2
+ case MENU_ENTER2:
+#endif
+ case MENU_ENTER:
+ key = BUTTON_NONE; /* eat the downpress, next menu reacts on release */
+ break;
+
+#ifdef MENU_ENTER2
+ case MENU_ENTER2 | BUTTON_REL:
+#endif
+ case MENU_ENTER | BUTTON_REL:
+ key = MENU_ENTER; /* fake downpress, next menu doesn't like release */
+ break;
+ }
+
+ return key;
+}
+
+bool pacbox_menu(void)
+{
+ int m;
+ int result;
+ int menu_quit=0;
+ int new_setting;
+ bool need_restart = false;
+
+ static const struct opt_items noyes[2] = {
+ { "No", NULL },
+ { "Yes", NULL },
+ };
+
+ static const struct opt_items difficulty_options[2] = {
+ { "Normal", NULL },
+ { "Harder", NULL },
+ };
+
+ static const struct opt_items numlives_options[4] = {
+ { "1", NULL },
+ { "2", NULL },
+ { "3", NULL },
+ { "5", NULL },
+ };
+
+ static const struct opt_items bonus_options[4] = {
+ { "10000 points", NULL },
+ { "15000 points", NULL },
+ { "20000 points", NULL },
+ { "No bonus", NULL },
+ };
+
+ static const struct opt_items ghostname_options[2] = {
+ { "Normal", NULL },
+ { "Alternate", NULL },
+ };
+
+ static const struct menu_item items[] = {
+ { "Difficulty", NULL },
+ { "Pacmen Per Game", NULL },
+ { "Bonus Life", NULL },
+ { "Ghost Names", NULL },
+ { "Display FPS", NULL },
+ { "Restart", NULL },
+ { "Quit", NULL },
+ };
+
+ m = rb->menu_init(items, sizeof(items) / sizeof(*items),
+ pacbox_menu_cb, NULL, NULL, NULL);
+
+ rb->button_clear_queue();
+
+ while (!menu_quit) {
+ result=rb->menu_show(m);
+
+ switch(result)
+ {
+ case 0:
+ new_setting=settings.difficulty;
+ rb->set_option("Difficulty", &new_setting, INT,
+ difficulty_options , 2, NULL);
+ if (new_setting != settings.difficulty) {
+ settings.difficulty=new_setting;
+ need_restart=true;
+ }
+ break;
+ case 1:
+ new_setting=settings.numlives;
+ rb->set_option("Pacmen Per Game", &new_setting, INT,
+ numlives_options , 4, NULL);
+ if (new_setting != settings.numlives) {
+ settings.numlives=new_setting;
+ need_restart=true;
+ }
+ break;
+ case 2:
+ new_setting=settings.bonus;
+ rb->set_option("Bonus Life", &new_setting, INT,
+ bonus_options , 4, NULL);
+ if (new_setting != settings.bonus) {
+ settings.bonus=new_setting;
+ need_restart=true;
+ }
+ break;
+ case 3:
+ new_setting=settings.ghostnames;
+ rb->set_option("Ghost Names", &new_setting, INT,
+ ghostname_options , 2, NULL);
+ if (new_setting != settings.ghostnames) {
+ settings.ghostnames=new_setting;
+ need_restart=true;
+ }
+ break;
+ case 4: /* Show FPS */
+ rb->set_option("Display FPS",&settings.showfps,INT, noyes, 2, NULL);
+ break;
+ case 5: /* Restart */
+ need_restart=true;
+ menu_quit=1;
+ break;
+ default:
+ menu_quit=1;
+ break;
+ }
+ }
+
+ rb->menu_exit(m);
+
+ if (need_restart) {
+ init_PacmanMachine(settings_to_dip(settings));
+ }
+
+ /* Possible results:
+ exit game
+ restart game
+ usb connected
+ */
+ return (result==6);
+}
+
+
+/*
+ Runs the game engine for one frame.
+*/
+int gameProc( void )
+{
+ int x,y;
+ int fps;
+ char str[80];
+ int status;
+ long end_time;
+ unsigned char* vbuf = video_buffer;
+ fb_data* dst;
+ fb_data* next_dst;
+
+ /* Run the machine for one frame (1/60th second) */
+ run();
+
+ frame_counter++;
+
+ /* Check the button status */
+ status = rb->button_status();
+
+#ifdef PACMAN_MENU
+ if (status & PACMAN_MENU) {
+#else
+ if (rb->button_hold()) {
+#endif
+ end_time = *rb->current_tick;
+ x = pacbox_menu();
+ rb->lcd_clear_display();
+#ifdef HAVE_REMOTE_LCD
+ rb->lcd_remote_clear_display();
+ rb->lcd_remote_update();
+#endif
+ if (x == 1) { return 1; }
+ start_time += *rb->current_tick-end_time;
+ }
+
+ setDeviceMode( Joy1_Left, (status & PACMAN_LEFT) ? DeviceOn : DeviceOff);
+ setDeviceMode( Joy1_Right, (status & PACMAN_RIGHT) ? DeviceOn : DeviceOff);
+ setDeviceMode( Joy1_Up, (status & PACMAN_UP) ? DeviceOn : DeviceOff);
+ setDeviceMode( Joy1_Down, (status & PACMAN_DOWN) ? DeviceOn : DeviceOff);
+ setDeviceMode( CoinSlot_1, (status & PACMAN_COIN) ? DeviceOn : DeviceOff);
+ setDeviceMode( Key_OnePlayer, (status & PACMAN_1UP) ? DeviceOn : DeviceOff);
+#ifdef PACMAN_2UP
+ setDeviceMode( Key_TwoPlayers, (status & PACMAN_2UP) ? DeviceOn : DeviceOff);
+#endif
+
+ /* We only update the screen every third frame - Pacman's native
+ framerate is 60fps, so we are attempting to display 20fps */
+ if( (frame_counter % (60/FPS)) == 0) {
+
+ video_frames++;
+
+ /* The following functions render the Pacman screen from the contents
+ of the video and color ram. We first update the background, and
+ then draw the Sprites on top.
+
+ Note that we only redraw the parts of the background that have
+ changed, which is why we need to keep a copy of the background without
+ the sprites on top. Even with the memcpy, this is faster than redrawing
+ the whole background.
+ */
+ renderBackground( background );
+ rb->memcpy(video_buffer,background,sizeof(video_buffer));
+ renderSprites( video_buffer );
+
+#ifdef HAVE_LCD_COLOR
+#if (LCD_WIDTH >= 224) && (LCD_HEIGHT >= 288)
+ /* Native resolution = 224x288 */
+ (void)next_dst;
+ dst=&rb->lcd_framebuffer[YOFS*LCD_WIDTH+XOFS];
+ for (y=0;y<ScreenHeight;y++) {
+ for (x=0;x<ScreenWidth;x++) {
+ *(dst++) = palette[*(vbuf++)];
+ }
+ dst += XOFS*2;
+ }
+#elif (LCD_WIDTH >= 288) && (LCD_HEIGHT >= 224)
+ /* Native resolution - rotated 90 degrees = 288x224 */
+ next_dst=&rb->lcd_framebuffer[YOFS*LCD_WIDTH+XOFS+ScreenHeight-1];
+ for( y=ScreenHeight-1; y>=0; y-- ) {
+ dst = (next_dst--);
+ for( x=0; x<ScreenWidth; x++ ) {
+ *dst = palette[*(vbuf++)];
+ dst+=LCD_WIDTH;
+ }
+ }
+#elif (LCD_WIDTH >= 216) && (LCD_HEIGHT >= 168)
+ /* 0.75 scaling - display 3 out of 4 pixels = 216x168
+ Skipping pixel #2 out of 4 seems to give the most legible display
+ */
+ next_dst=&rb->lcd_framebuffer[YOFS*LCD_WIDTH+XOFS+((ScreenHeight*3)/4)-1];
+ for (y=ScreenHeight-1;y >= 0; y--) {
+ if ((y & 3) != 1) {
+ dst = (next_dst--);
+ for (x=0;x<ScreenWidth;x++) {
+ if ((x & 3) == 1) { vbuf++; }
+ else {
+ *dst = palette[*(vbuf++)];
+ dst+=LCD_WIDTH;
+ }
+ }
+ } else {
+ vbuf+=ScreenWidth;
+ }
+ }
+#elif (LCD_WIDTH >= 144) && (LCD_HEIGHT >= 112)
+ /* 0.5 scaling - display every other pixel = 144x112 */
+ next_dst=&rb->lcd_framebuffer[YOFS*LCD_WIDTH+XOFS+ScreenHeight/2-1];
+ for (y=(ScreenHeight/2)-1;y >= 0; y--) {
+ dst = (next_dst--);
+ for (x=0;x<ScreenWidth/2;x++) {
+ *dst = palette[*(vbuf)];
+ vbuf+=2;
+ dst+=LCD_WIDTH;
+ }
+ vbuf+=ScreenWidth;
+ }
+#endif
+#else /* Greyscale LCDs */
+#if (LCD_WIDTH >= 144) && (LCD_HEIGHT >= 112)
+#if LCD_PIXELFORMAT == VERTICAL_PACKING
+ /* 0.5 scaling - display every other pixel = 144x112 */
+ next_dst=&rb->lcd_framebuffer[YOFS/4*LCD_WIDTH+XOFS+ScreenHeight/2-1];
+ for (y=(ScreenHeight/2)-1;y >= 0; y--) {
+ dst = (next_dst--);
+ for (x=0;x<ScreenWidth/8;x++) {
+ *dst = (palette[*(vbuf+6)]<<6) | (palette[*(vbuf+4)] << 4) | (palette[*(vbuf+2)] << 2) | palette[*(vbuf)];
+ vbuf+=8;
+ dst+=LCD_WIDTH;
+ }
+ vbuf+=ScreenWidth;
+ }
+#endif /* Vertical Packing */
+#endif /* Size >= 144x112 */
+#endif /* Not Colour */
+
+ if (settings.showfps) {
+ fps = (video_frames*HZ*100) / (*rb->current_tick-start_time);
+ rb->snprintf(str,sizeof(str),"%d.%02d / %d fps ",fps/100,fps%100,
+ FPS);
+ rb->lcd_putsxy(0,0,str);
+ }
+
+ rb->lcd_update();
+
+#ifdef SIMULATOR
+ /* Keep the framerate at Pacman's 60fps */
+ end_time = start_time + (video_frames*HZ)/FPS;
+ while (TIME_BEFORE(*rb->current_tick,end_time)) {
+ rb->sleep(1);
+ }
+#endif
+ }
+
+ return 0;
+}
+
+enum plugin_status plugin_start(struct plugin_api* api, void* parameter)
+{
+ (void)parameter;
+ int status;
+
+ rb = api;
+
+#ifdef USE_IRAM
+ rb->memcpy(iramstart, iramcopy, iramend-iramstart);
+ rb->memset(iedata, 0, iend - iedata);
+#endif
+
+#ifdef HAVE_ADJUSTABLE_CPU_FREQ
+ rb->cpu_boost(true);
+#endif
+
+ rb->lcd_set_foreground(LCD_WHITE);
+ rb->lcd_set_background(LCD_BLACK);
+ rb->lcd_clear_display();
+ rb->lcd_update();
+
+ /* Set the default settings (we should load these from a file) */
+ settings.difficulty = 0; /* Normal */
+ settings.numlives = 2; /* 3 lives */
+ settings.bonus = 0; /* 10000 points */
+ settings.ghostnames = 0; /* Normal names */
+ settings.showfps = 0; /* Do not show FPS */
+
+ /* Initialise the hardware */
+ init_PacmanMachine(settings_to_dip(settings));
+
+ /* Load the romset */
+ if (loadROMS()) {
+ start_time = *rb->current_tick-1;
+ do {
+ status = gameProc();
+ } while (!status);
+ } else {
+ rb->splash(HZ*2,true,"No ROMs in /.rockbox/pacman/");
+ }
+
+#ifdef HAVE_ADJUSTABLE_CPU_FREQ
+ rb->cpu_boost(false);
+#endif
+
+ return PLUGIN_OK;
+}
diff --git a/apps/plugins/pacbox/readme.txt b/apps/plugins/pacbox/readme.txt
new file mode 100644
index 0000000..41fc89e
--- /dev/null
+++ b/apps/plugins/pacbox/readme.txt
@@ -0,0 +1,13 @@
+Pacbox is based on PIE - the Pacman Instructional Emulator written by
+Alessandro Scotti. PIE is a Pacman arcade machine emulator licensed
+under the GNU GPL and is available from http://www.ascotti.org/
+
+PIE is a Windows application written in C++ - all the Windows-specific
+code was stripped out and the emulator converted to C for use in
+Rockbox.
+
+The version of PIE used as the basis of the port was v1.11
+
+
+Dave Chapman
+March 2006
diff --git a/apps/plugins/pacbox/z80.c b/apps/plugins/pacbox/z80.c
new file mode 100644
index 0000000..b489682
--- /dev/null
+++ b/apps/plugins/pacbox/z80.c
@@ -0,0 +1,8058 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#include "plugin.h"
+#include "hardware.h"
+#include "z80.h"
+#include "z80_internal.h"
+
+// Table with parity, sign and zero flags precomputed for each byte value
+unsigned char PSZ_[256] = {
+ Zero|Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
+ 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
+ 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
+ Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
+ 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
+ Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
+ Parity, 0, 0, Parity, 0, Parity, Parity, 0, 0, Parity, Parity, 0, Parity, 0, 0, Parity,
+ 0, Parity, Parity, 0, Parity, 0, 0, Parity, Parity, 0, 0, Parity, 0, Parity, Parity, 0,
+ Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
+ Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity,
+ Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity,
+ Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
+ Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity,
+ Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
+ Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign,
+ Sign|Parity, Sign, Sign, Sign|Parity, Sign, Sign|Parity, Sign|Parity, Sign, Sign, Sign|Parity, Sign|Parity, Sign, Sign|Parity, Sign, Sign, Sign|Parity
+};
+
+// Interrupt flags
+enum {
+ IFF1 = 0x40, // Interrupts enabled/disabled
+ IFF2 = 0x20, // Copy of IFF1 (used by non-maskable interrupts)
+ Halted = 0x10 // Internal use: signals that the CPU is halted
+};
+
+// Implements an opcode
+typedef void (OpcodeHandler)(void);
+
+typedef struct {
+ OpcodeHandler* handler;
+ unsigned cycles;
+} OpcodeInfo;
+
+// Implements an opcode for instructions that use the form (IX/IY + b)
+typedef void (OpcodeHandlerXY)( unsigned );
+
+typedef struct {
+ OpcodeHandlerXY* handler;
+ unsigned cycles;
+} OpcodeInfoXY;
+
+/** */
+void do_opcode_xy( OpcodeInfo * );
+
+/** */
+unsigned do_opcode_xycb( unsigned xy );
+
+unsigned iflags_; // Interrupt mode (bits 0 and 1) and flags
+unsigned cycles_; // Number of CPU cycles elapsed so far
+
+
+// Registers
+unsigned char B; //@- B register
+unsigned char C; //@- C register
+unsigned char D; //@- D register
+unsigned char E; //@- E register
+unsigned char H; //@- H register
+unsigned char L; //@- L register
+unsigned char A; //@- A register (accumulator)
+unsigned char F; //@- Flags register
+unsigned char B1; //@- Alternate B register (B')
+unsigned char C1; //@- Alternate C register (C')
+unsigned char D1; //@- Alternate D register (D')
+unsigned char E1; //@- Alternate E register (E')
+unsigned char H1; //@- Alternate H register (H')
+unsigned char L1; //@- Alternate L register (L')
+unsigned char A1; //@- Alternate A register (A')
+unsigned char F1; //@- Alternate flags register (F')
+unsigned IX; //@- Index register X
+unsigned IY; //@- Index register Y
+unsigned PC; //@- Program counter
+unsigned SP; //@- Stack pointer
+unsigned char I; //@- Interrupt register
+unsigned char R; //@- Refresh register
+
+
+/** Returns the 16 bit register BC. */
+#define BC() (((unsigned)B << 8) | C)
+#define DE() (((unsigned)D << 8) | E)
+#define HL() (((unsigned)H << 8) | L)
+
+/**
+ Returns the number of Z80 CPU cycles elapsed so far.
+
+ The cycle count is reset to zero when reset() is called, or
+ it can be set to any value with setCycles(). It is updated after
+ a CPU instruction is executed, for example by calling step()
+ or interrupt().
+*/
+unsigned getCycles(void) {
+ return cycles_;
+}
+
+/** Sets the CPU cycle counter to the specified value. */
+void setCycles( unsigned value ) {
+ cycles_ = value;
+}
+
+/** Returns the current interrupt mode. */
+unsigned getInterruptMode(void) {
+ return iflags_ & 0x03;
+}
+
+/** Sets the interrupt mode to the specified value. */
+void setInterruptMode( unsigned mode );
+
+/** Returns non-zero if the CPU is halted, otherwise zero. */
+int isHalted(void) {
+ return iflags_ & Halted;
+}
+
+/*
+ Sets the interrupt mode to IM0, IM1 or IM2.
+*/
+void setInterruptMode( unsigned mode )
+{
+ if( mode <= 2 ) {
+ iflags_ = (iflags_ & ~0x03) | mode;
+ }
+}
+
+/*
+ Calls a subroutine at the specified address.
+*/
+void callSub( unsigned addr )
+{
+ SP -= 2;
+ writeWord( SP, PC ); // Save current program counter in the stack
+ PC = addr & 0xFFFF; // Jump to the specified address
+}
+
+/*
+ Decrements a byte value by one.
+ Note that this is different from subtracting one from the byte value,
+ because flags behave differently.
+*/
+static inline unsigned char decByte( unsigned char b )
+{
+ F = Subtraction | (F & Carry); // Preserve the carry flag
+ if( (b & 0x0F) == 0 ) F |= Halfcarry;
+ --b;
+ if( b == 0x7F ) F |= Overflow;
+ if( b & 0x80 ) F |= Sign;
+ if( b == 0 ) F |= Zero;
+
+ return b;
+}
+
+/*
+ Increments a byte value by one.
+ Note that this is different from adding one to the byte value,
+ because flags behave differently.
+*/
+static inline unsigned char incByte( unsigned char b )
+{
+ ++b;
+ F &= Carry; // Preserve the carry flag
+ if( ! (b & 0x0F) ) F |= Halfcarry;
+ if( b == 0x80 ) F |= Overflow;
+ if( b & 0x80 ) F |= Sign;
+ if( b == 0 ) F |= Zero;
+
+ return b;
+}
+
+/*
+ Reads one byte from port C, updating flags according to the rules of "IN r,(C)".
+*/
+static inline unsigned char inpReg(void)
+{
+ unsigned char r = readPort( C );
+
+ F = (F & Carry) | PSZ_[r];
+
+ return r;
+}
+
+/*
+ Performs a relative jump to the specified offset.
+*/
+static inline void relJump( unsigned char o )
+{
+ int offset = (int)((signed char)o);
+
+ PC = (unsigned)((int)PC + offset) & 0xFFFF;
+ cycles_++;
+}
+
+/*
+ Returns from a subroutine, popping the saved Program Counter from the stack.
+*/
+static inline void retFromSub(void)
+{
+ PC = readWord( SP );
+ SP += 2;
+}
+
+/*
+ Rotates left one byte thru the carry flag.
+*/
+static inline unsigned char rotateLeft( unsigned char op )
+{
+ unsigned char f = F;
+
+ F = 0;
+ if( op & 0x80 ) F |= Carry;
+ op <<= 1;
+ if( f & Carry ) op |= 0x01;
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Rotates left one byte copying the most significant bit (bit 7) in the carry flag.
+*/
+static inline unsigned char rotateLeftCarry( unsigned char op )
+{
+ F = 0;
+ if( op & 0x80 ) F |= Carry;
+ op = (op << 1) | (op >> 7);
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Rotates right one byte thru the carry flag.
+*/
+static inline unsigned char rotateRight( unsigned char op )
+{
+ unsigned char f = F;
+
+ F = 0;
+ if( op & 0x01 ) F |= Carry;
+ op >>= 1;
+ if( f & Carry ) op |= 0x80;
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Rotates right one byte copying the least significant bit (bit 0) in the carry flag.
+*/
+static inline unsigned char rotateRightCarry( unsigned char op )
+{
+ F = 0;
+ if( op & 0x01 ) F |= Carry;
+ op = (op >> 1) | (op << 7);
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Shifts left one byte.
+*/
+static inline unsigned char shiftLeft( unsigned char op )
+{
+ F = 0;
+ if( op & 0x80 ) F |= Carry;
+ op <<= 1;
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Shifts right one byte, preserving its sign (most significant bit).
+*/
+static inline unsigned char shiftRightArith( unsigned char op )
+{
+ F = 0;
+ if( op & 0x01 ) F |= Carry;
+ op = (op >> 1) | (op & 0x80);
+
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Shifts right one byte.
+*/
+static inline unsigned char shiftRightLogical( unsigned char op )
+{
+ F = 0;
+ if( op & 0x01 ) F |= Carry;
+ op >>= 1;
+
+ F |= PSZ_[op];
+
+ return op;
+}
+
+/*
+ Tests whether the specified bit of op is set.
+*/
+static inline void testBit( unsigned char bit, unsigned char op )
+{
+ // Flags for a bit test operation are:
+ // S, P: unknown
+ // Z: set if bit is zero, reset otherwise
+ // N: reset
+ // H: set
+ // C: unaffected
+ // However, it seems that parity is always set like Z, so we emulate that as well.
+ F = (F & (Carry | Sign)) | Halfcarry;
+
+ if( (op & (1 << bit)) == 0 ) {
+ // Bit is not set, so set the zero flag
+ F |= Zero | Parity;
+ }
+}
+
+/*
+ Adds the specified byte op to the accumulator, adding
+ carry.
+*/
+static inline void addByte( unsigned char op, unsigned char cf )
+{
+ unsigned x = A + op;
+
+ if( cf ) x++; // Add carry
+
+ F = 0;
+ if( !(x & 0xFF) ) F |= Zero;
+ if( x & 0x80 ) F |= Sign;
+ if( x >= 0x100 ) F |= Carry;
+
+ /*
+ Halfcarry is set on carry from the low order four bits.
+
+ To see how to compute it, let's take a look at the following table, which
+ shows the binary addition of two binary numbers:
+
+ A B A+B
+ -----------
+ 0 0 0
+ 0 1 1
+ 1 0 1
+ 1 1 0
+
+ Note that if only the lowest bit is used, then A+B, A-B and A^B yield the same
+ value. If we know A, B and the sum A+B+C, then C is easily derived:
+ C = A+B+C - A - B, that is
+ C = A+B+C ^ A ^ B.
+
+ For the halfcarry, A and B above are the fifth bit of a byte, which corresponds
+ to the value 0x10. So:
+
+ Halfcarry = ((accumulator+operand+halfcarry) ^ accumulator ^ operand) & 0x10
+
+ Note that masking off all bits but one is important because we have worked all
+ the math by using one bit only.
+ */
+ if( (A ^ op ^ x) & 0x10 ) F |= Halfcarry;
+
+ /*
+ The overflow bit is set when the result is too large to fit into the destination
+ register, causing a change in the sign bit.
+
+ For a sum, we can only have overflow when adding two numbers that are both positive
+ or both negative. For example 0x5E + 0x4B (94 + 75) yields 0xA9 (169), which fits
+ into an 8-bit register only if it is interpreted as an unsigned number. If we
+ consider the result as a signed integer, then 0xA9 corresponds to decimal -87 and
+ we have overflow.
+ Note that if we add two signed numbers of opposite sign then we cannot overflow
+ the destination register, because the absolute value of the result will always fit
+ in 7 bits, leaving the most significant bit free for use as a sign bit.
+
+ We can code all the above concisely by noting that:
+
+ ~(A ^ op) & 0x80
+
+ is true if and only if A and op have the same sign. Also:
+
+ (x ^ op) & 0x80
+
+ is true if and only if the sum of A and op has taken a sign opposite to that
+ of its operands.
+
+ Thus the expression:
+
+ ~(A ^ op) & (x ^ op) & 0x80
+
+ reads "A has the same sign as op, and the opposite as x", where x is the sum of
+ A and op (and an optional carry).
+ */
+ if( ~(A ^ op) & (x ^ op) & 0x80 ) F |= Overflow;
+
+ A = x;
+}
+
+/*
+ Subtracts the specified byte op from the accumulator, using carry as
+ borrow from a previous operation.
+*/
+static inline unsigned char subByte( unsigned char op, unsigned char cf )
+{
+ unsigned char x = A - op;
+
+ if( cf ) x--;
+
+ F = Subtraction;
+ if( x == 0 ) F |= Zero;
+ if( x & 0x80 ) F |= Sign;
+ if( (x >= A) && (op | cf)) F |= Carry;
+
+ // See addByte() for an explanation of the halfcarry bit
+ if( (A ^ op ^ x) & 0x10 ) F |= Halfcarry;
+
+ // See addByte() for an explanation of the overflow bit. The only difference here
+ // is that for a subtraction we must check that the two operands have different
+ // sign, because in fact A-B is A+(-B). Note however that since subtraction is not
+ // symmetric, we have to use (x ^ A) to get the correct result, whereas for the
+ // addition (x ^ A) is equivalent to (x ^ op)
+ if( (A ^ op) & (x ^ A) & 0x80 ) F |= Overflow;
+
+ return x;
+}
+
+static inline unsigned addDispl( unsigned addr, unsigned char displ ) {
+ return (unsigned)((int)addr + (int)(signed char)displ);
+}
+
+/** Compares the accumulator and the specified operand (CP op) */
+static inline void cmpByte( unsigned char op ) {
+ subByte( op, 0 );
+}
+
+/** Fetches a byte from the program counter location */
+static inline unsigned char fetchByte(void) {
+ return readByte( PC++ );
+}
+
+/** Fetches a 16 bit word from the program counter location */
+static inline unsigned fetchWord(void) {
+ unsigned x = readWord( PC );
+ PC += 2;
+ return x;
+}
+
+/** Sets the parity, sign and zero flags from the accumulator value */
+static inline void setFlagsPSZ(void) {
+ F = Halfcarry | PSZ_[A];
+}
+
+/** Sets the parity, sign, zero, 3rd and 5th flag bits from the accumulator value */
+static inline void setFlags35PSZ(void) {
+ F = (F & (Carry | Halfcarry | Subtraction)) | PSZ_[A];
+}
+
+/** */
+static inline void setFlags35PSZ000(void) {
+ F = PSZ_[A];
+}
+
+/* Resets the CPU */
+void z80_reset()
+{
+ PC = 0; // Program counter is zero
+ I = 0; // Interrupt register cleared
+ R = 0; // Memory refresh register cleared
+ iflags_ = 0; // IFF1 and IFF2 cleared, IM0 enabled
+ cycles_ = 0; // Could that be 2 (according to some Zilog docs)?
+
+ // There is no official documentation for the following!
+ B = B1 = 0;
+ C = C1 = 0;
+ D = D1 = 0;
+ E = E1 = 0;
+ H = H1 = 0;
+ L = L1 = 0;
+ A = A1 = 0;
+ F = F1 = 0;
+ IX = 0;
+ IY = 0;
+ SP = 0xF000;
+}
+
+unsigned z80_getSizeOfSnapshotBuffer(void)
+{
+ unsigned result =
+ 8*2 + // 8-bit registers
+ 1 + // I
+ 1 + // R
+ 2 + // IX
+ 2 + // IY
+ 2 + // PC
+ 2 + // SP
+ 4 + // iflags_
+ 4; // cycles_
+
+ return result;
+}
+
+static unsigned saveUint16( unsigned char * buffer, unsigned u )
+{
+ *buffer++ = (unsigned char) (u >> 8);
+ *buffer = (unsigned char) (u);
+
+ return 2;
+}
+
+unsigned z80_takeSnapshot( unsigned char * buffer )
+{
+ unsigned char * buf = buffer;
+
+ *buf++ = A; *buf++ = A1;
+ *buf++ = B; *buf++ = B1;
+ *buf++ = C; *buf++ = C1;
+ *buf++ = D; *buf++ = D1;
+ *buf++ = E; *buf++ = E1;
+ *buf++ = H; *buf++ = H1;
+ *buf++ = L; *buf++ = L1;
+ *buf++ = F; *buf++ = F1;
+
+ *buf++ = I;
+ *buf++ = R;
+
+ buf += saveUint16( buf, IX );
+ buf += saveUint16( buf, IY );
+ buf += saveUint16( buf, PC );
+ buf += saveUint16( buf, SP );
+
+ buf += saveUint16( buf, iflags_ >> 16 );
+ buf += saveUint16( buf, iflags_ );
+ buf += saveUint16( buf, cycles_ >> 16 );
+ buf += saveUint16( buf, cycles_ );
+
+ return buffer - buf;
+}
+
+static unsigned loadUint16( unsigned char ** buffer )
+{
+ unsigned char * buf = *buffer;
+ unsigned result = *buf++;
+
+ result = (result << 8) | *buf++;
+
+ *buffer = buf;
+
+ return result;
+}
+
+unsigned z80_restoreSnapshot( unsigned char * buffer )
+{
+ unsigned char * buf = buffer;
+
+ A = *buf++; A1 = *buf++;
+ B = *buf++; B1 = *buf++;
+ C = *buf++; C1 = *buf++;
+ D = *buf++; D1 = *buf++;
+ E = *buf++; E1 = *buf++;
+ H = *buf++; H1 = *buf++;
+ L = *buf++; L1 = *buf++;
+ F = *buf++; F1 = *buf++;
+
+ I = *buf++;
+ R = *buf++;
+
+ IX = loadUint16( &buf );
+ IY = loadUint16( &buf );
+ PC = loadUint16( &buf );
+ SP = loadUint16( &buf );
+
+ iflags_ = loadUint16( &buf );
+ iflags_ = (iflags_ << 16) | loadUint16(&buf);
+ cycles_ = loadUint16( &buf );
+ cycles_ = (cycles_ << 16) | loadUint16(&buf);
+
+ return buf - buffer;
+}
+
+OpcodeInfo OpInfoCB_[256] = {
+ { &opcode_cb_00, 8 }, // RLC B
+ { &opcode_cb_01, 8 }, // RLC C
+ { &opcode_cb_02, 8 }, // RLC D
+ { &opcode_cb_03, 8 }, // RLC E
+ { &opcode_cb_04, 8 }, // RLC H
+ { &opcode_cb_05, 8 }, // RLC L
+ { &opcode_cb_06, 15 }, // RLC (HL)
+ { &opcode_cb_07, 8 }, // RLC A
+ { &opcode_cb_08, 8 }, // RRC B
+ { &opcode_cb_09, 8 }, // RRC C
+ { &opcode_cb_0a, 8 }, // RRC D
+ { &opcode_cb_0b, 8 }, // RRC E
+ { &opcode_cb_0c, 8 }, // RRC H
+ { &opcode_cb_0d, 8 }, // RRC L
+ { &opcode_cb_0e, 15 }, // RRC (HL)
+ { &opcode_cb_0f, 8 }, // RRC A
+ { &opcode_cb_10, 8 }, // RL B
+ { &opcode_cb_11, 8 }, // RL C
+ { &opcode_cb_12, 8 }, // RL D
+ { &opcode_cb_13, 8 }, // RL E
+ { &opcode_cb_14, 8 }, // RL H
+ { &opcode_cb_15, 8 }, // RL L
+ { &opcode_cb_16, 15 }, // RL (HL)
+ { &opcode_cb_17, 8 }, // RL A
+ { &opcode_cb_18, 8 }, // RR B
+ { &opcode_cb_19, 8 }, // RR C
+ { &opcode_cb_1a, 8 }, // RR D
+ { &opcode_cb_1b, 8 }, // RR E
+ { &opcode_cb_1c, 8 }, // RR H
+ { &opcode_cb_1d, 8 }, // RR L
+ { &opcode_cb_1e, 15 }, // RR (HL)
+ { &opcode_cb_1f, 8 }, // RR A
+ { &opcode_cb_20, 8 }, // SLA B
+ { &opcode_cb_21, 8 }, // SLA C
+ { &opcode_cb_22, 8 }, // SLA D
+ { &opcode_cb_23, 8 }, // SLA E
+ { &opcode_cb_24, 8 }, // SLA H
+ { &opcode_cb_25, 8 }, // SLA L
+ { &opcode_cb_26, 15 }, // SLA (HL)
+ { &opcode_cb_27, 8 }, // SLA A
+ { &opcode_cb_28, 8 }, // SRA B
+ { &opcode_cb_29, 8 }, // SRA C
+ { &opcode_cb_2a, 8 }, // SRA D
+ { &opcode_cb_2b, 8 }, // SRA E
+ { &opcode_cb_2c, 8 }, // SRA H
+ { &opcode_cb_2d, 8 }, // SRA L
+ { &opcode_cb_2e, 15 }, // SRA (HL)
+ { &opcode_cb_2f, 8 }, // SRA A
+ { &opcode_cb_30, 8 }, // SLL B
+ { &opcode_cb_31, 8 }, // SLL C
+ { &opcode_cb_32, 8 }, // SLL D
+ { &opcode_cb_33, 8 }, // SLL E
+ { &opcode_cb_34, 8 }, // SLL H
+ { &opcode_cb_35, 8 }, // SLL L
+ { &opcode_cb_36, 15 }, // SLL (HL)
+ { &opcode_cb_37, 8 }, // SLL A
+ { &opcode_cb_38, 8 }, // SRL B
+ { &opcode_cb_39, 8 }, // SRL C
+ { &opcode_cb_3a, 8 }, // SRL D
+ { &opcode_cb_3b, 8 }, // SRL E
+ { &opcode_cb_3c, 8 }, // SRL H
+ { &opcode_cb_3d, 8 }, // SRL L
+ { &opcode_cb_3e, 15 }, // SRL (HL)
+ { &opcode_cb_3f, 8 }, // SRL A
+ { &opcode_cb_40, 8 }, // BIT 0, B
+ { &opcode_cb_41, 8 }, // BIT 0, C
+ { &opcode_cb_42, 8 }, // BIT 0, D
+ { &opcode_cb_43, 8 }, // BIT 0, E
+ { &opcode_cb_44, 8 }, // BIT 0, H
+ { &opcode_cb_45, 8 }, // BIT 0, L
+ { &opcode_cb_46, 12 }, // BIT 0, (HL)
+ { &opcode_cb_47, 8 }, // BIT 0, A
+ { &opcode_cb_48, 8 }, // BIT 1, B
+ { &opcode_cb_49, 8 }, // BIT 1, C
+ { &opcode_cb_4a, 8 }, // BIT 1, D
+ { &opcode_cb_4b, 8 }, // BIT 1, E
+ { &opcode_cb_4c, 8 }, // BIT 1, H
+ { &opcode_cb_4d, 8 }, // BIT 1, L
+ { &opcode_cb_4e, 12 }, // BIT 1, (HL)
+ { &opcode_cb_4f, 8 }, // BIT 1, A
+ { &opcode_cb_50, 8 }, // BIT 2, B
+ { &opcode_cb_51, 8 }, // BIT 2, C
+ { &opcode_cb_52, 8 }, // BIT 2, D
+ { &opcode_cb_53, 8 }, // BIT 2, E
+ { &opcode_cb_54, 8 }, // BIT 2, H
+ { &opcode_cb_55, 8 }, // BIT 2, L
+ { &opcode_cb_56, 12 }, // BIT 2, (HL)
+ { &opcode_cb_57, 8 }, // BIT 2, A
+ { &opcode_cb_58, 8 }, // BIT 3, B
+ { &opcode_cb_59, 8 }, // BIT 3, C
+ { &opcode_cb_5a, 8 }, // BIT 3, D
+ { &opcode_cb_5b, 8 }, // BIT 3, E
+ { &opcode_cb_5c, 8 }, // BIT 3, H
+ { &opcode_cb_5d, 8 }, // BIT 3, L
+ { &opcode_cb_5e, 12 }, // BIT 3, (HL)
+ { &opcode_cb_5f, 8 }, // BIT 3, A
+ { &opcode_cb_60, 8 }, // BIT 4, B
+ { &opcode_cb_61, 8 }, // BIT 4, C
+ { &opcode_cb_62, 8 }, // BIT 4, D
+ { &opcode_cb_63, 8 }, // BIT 4, E
+ { &opcode_cb_64, 8 }, // BIT 4, H
+ { &opcode_cb_65, 8 }, // BIT 4, L
+ { &opcode_cb_66, 12 }, // BIT 4, (HL)
+ { &opcode_cb_67, 8 }, // BIT 4, A
+ { &opcode_cb_68, 8 }, // BIT 5, B
+ { &opcode_cb_69, 8 }, // BIT 5, C
+ { &opcode_cb_6a, 8 }, // BIT 5, D
+ { &opcode_cb_6b, 8 }, // BIT 5, E
+ { &opcode_cb_6c, 8 }, // BIT 5, H
+ { &opcode_cb_6d, 8 }, // BIT 5, L
+ { &opcode_cb_6e, 12 }, // BIT 5, (HL)
+ { &opcode_cb_6f, 8 }, // BIT 5, A
+ { &opcode_cb_70, 8 }, // BIT 6, B
+ { &opcode_cb_71, 8 }, // BIT 6, C
+ { &opcode_cb_72, 8 }, // BIT 6, D
+ { &opcode_cb_73, 8 }, // BIT 6, E
+ { &opcode_cb_74, 8 }, // BIT 6, H
+ { &opcode_cb_75, 8 }, // BIT 6, L
+ { &opcode_cb_76, 12 }, // BIT 6, (HL)
+ { &opcode_cb_77, 8 }, // BIT 6, A
+ { &opcode_cb_78, 8 }, // BIT 7, B
+ { &opcode_cb_79, 8 }, // BIT 7, C
+ { &opcode_cb_7a, 8 }, // BIT 7, D
+ { &opcode_cb_7b, 8 }, // BIT 7, E
+ { &opcode_cb_7c, 8 }, // BIT 7, H
+ { &opcode_cb_7d, 8 }, // BIT 7, L
+ { &opcode_cb_7e, 12 }, // BIT 7, (HL)
+ { &opcode_cb_7f, 8 }, // BIT 7, A
+ { &opcode_cb_80, 8 }, // RES 0, B
+ { &opcode_cb_81, 8 }, // RES 0, C
+ { &opcode_cb_82, 8 }, // RES 0, D
+ { &opcode_cb_83, 8 }, // RES 0, E
+ { &opcode_cb_84, 8 }, // RES 0, H
+ { &opcode_cb_85, 8 }, // RES 0, L
+ { &opcode_cb_86, 15 }, // RES 0, (HL)
+ { &opcode_cb_87, 8 }, // RES 0, A
+ { &opcode_cb_88, 8 }, // RES 1, B
+ { &opcode_cb_89, 8 }, // RES 1, C
+ { &opcode_cb_8a, 8 }, // RES 1, D
+ { &opcode_cb_8b, 8 }, // RES 1, E
+ { &opcode_cb_8c, 8 }, // RES 1, H
+ { &opcode_cb_8d, 8 }, // RES 1, L
+ { &opcode_cb_8e, 15 }, // RES 1, (HL)
+ { &opcode_cb_8f, 8 }, // RES 1, A
+ { &opcode_cb_90, 8 }, // RES 2, B
+ { &opcode_cb_91, 8 }, // RES 2, C
+ { &opcode_cb_92, 8 }, // RES 2, D
+ { &opcode_cb_93, 8 }, // RES 2, E
+ { &opcode_cb_94, 8 }, // RES 2, H
+ { &opcode_cb_95, 8 }, // RES 2, L
+ { &opcode_cb_96, 15 }, // RES 2, (HL)
+ { &opcode_cb_97, 8 }, // RES 2, A
+ { &opcode_cb_98, 8 }, // RES 3, B
+ { &opcode_cb_99, 8 }, // RES 3, C
+ { &opcode_cb_9a, 8 }, // RES 3, D
+ { &opcode_cb_9b, 8 }, // RES 3, E
+ { &opcode_cb_9c, 8 }, // RES 3, H
+ { &opcode_cb_9d, 8 }, // RES 3, L
+ { &opcode_cb_9e, 15 }, // RES 3, (HL)
+ { &opcode_cb_9f, 8 }, // RES 3, A
+ { &opcode_cb_a0, 8 }, // RES 4, B
+ { &opcode_cb_a1, 8 }, // RES 4, C
+ { &opcode_cb_a2, 8 }, // RES 4, D
+ { &opcode_cb_a3, 8 }, // RES 4, E
+ { &opcode_cb_a4, 8 }, // RES 4, H
+ { &opcode_cb_a5, 8 }, // RES 4, L
+ { &opcode_cb_a6, 15 }, // RES 4, (HL)
+ { &opcode_cb_a7, 8 }, // RES 4, A
+ { &opcode_cb_a8, 8 }, // RES 5, B
+ { &opcode_cb_a9, 8 }, // RES 5, C
+ { &opcode_cb_aa, 8 }, // RES 5, D
+ { &opcode_cb_ab, 8 }, // RES 5, E
+ { &opcode_cb_ac, 8 }, // RES 5, H
+ { &opcode_cb_ad, 8 }, // RES 5, L
+ { &opcode_cb_ae, 15 }, // RES 5, (HL)
+ { &opcode_cb_af, 8 }, // RES 5, A
+ { &opcode_cb_b0, 8 }, // RES 6, B
+ { &opcode_cb_b1, 8 }, // RES 6, C
+ { &opcode_cb_b2, 8 }, // RES 6, D
+ { &opcode_cb_b3, 8 }, // RES 6, E
+ { &opcode_cb_b4, 8 }, // RES 6, H
+ { &opcode_cb_b5, 8 }, // RES 6, L
+ { &opcode_cb_b6, 15 }, // RES 6, (HL)
+ { &opcode_cb_b7, 8 }, // RES 6, A
+ { &opcode_cb_b8, 8 }, // RES 7, B
+ { &opcode_cb_b9, 8 }, // RES 7, C
+ { &opcode_cb_ba, 8 }, // RES 7, D
+ { &opcode_cb_bb, 8 }, // RES 7, E
+ { &opcode_cb_bc, 8 }, // RES 7, H
+ { &opcode_cb_bd, 8 }, // RES 7, L
+ { &opcode_cb_be, 15 }, // RES 7, (HL)
+ { &opcode_cb_bf, 8 }, // RES 7, A
+ { &opcode_cb_c0, 8 }, // SET 0, B
+ { &opcode_cb_c1, 8 }, // SET 0, C
+ { &opcode_cb_c2, 8 }, // SET 0, D
+ { &opcode_cb_c3, 8 }, // SET 0, E
+ { &opcode_cb_c4, 8 }, // SET 0, H
+ { &opcode_cb_c5, 8 }, // SET 0, L
+ { &opcode_cb_c6, 15 }, // SET 0, (HL)
+ { &opcode_cb_c7, 8 }, // SET 0, A
+ { &opcode_cb_c8, 8 }, // SET 1, B
+ { &opcode_cb_c9, 8 }, // SET 1, C
+ { &opcode_cb_ca, 8 }, // SET 1, D
+ { &opcode_cb_cb, 8 }, // SET 1, E
+ { &opcode_cb_cc, 8 }, // SET 1, H
+ { &opcode_cb_cd, 8 }, // SET 1, L
+ { &opcode_cb_ce, 15 }, // SET 1, (HL)
+ { &opcode_cb_cf, 8 }, // SET 1, A
+ { &opcode_cb_d0, 8 }, // SET 2, B
+ { &opcode_cb_d1, 8 }, // SET 2, C
+ { &opcode_cb_d2, 8 }, // SET 2, D
+ { &opcode_cb_d3, 8 }, // SET 2, E
+ { &opcode_cb_d4, 8 }, // SET 2, H
+ { &opcode_cb_d5, 8 }, // SET 2, L
+ { &opcode_cb_d6, 15 }, // SET 2, (HL)
+ { &opcode_cb_d7, 8 }, // SET 2, A
+ { &opcode_cb_d8, 8 }, // SET 3, B
+ { &opcode_cb_d9, 8 }, // SET 3, C
+ { &opcode_cb_da, 8 }, // SET 3, D
+ { &opcode_cb_db, 8 }, // SET 3, E
+ { &opcode_cb_dc, 8 }, // SET 3, H
+ { &opcode_cb_dd, 8 }, // SET 3, L
+ { &opcode_cb_de, 15 }, // SET 3, (HL)
+ { &opcode_cb_df, 8 }, // SET 3, A
+ { &opcode_cb_e0, 8 }, // SET 4, B
+ { &opcode_cb_e1, 8 }, // SET 4, C
+ { &opcode_cb_e2, 8 }, // SET 4, D
+ { &opcode_cb_e3, 8 }, // SET 4, E
+ { &opcode_cb_e4, 8 }, // SET 4, H
+ { &opcode_cb_e5, 8 }, // SET 4, L
+ { &opcode_cb_e6, 15 }, // SET 4, (HL)
+ { &opcode_cb_e7, 8 }, // SET 4, A
+ { &opcode_cb_e8, 8 }, // SET 5, B
+ { &opcode_cb_e9, 8 }, // SET 5, C
+ { &opcode_cb_ea, 8 }, // SET 5, D
+ { &opcode_cb_eb, 8 }, // SET 5, E
+ { &opcode_cb_ec, 8 }, // SET 5, H
+ { &opcode_cb_ed, 8 }, // SET 5, L
+ { &opcode_cb_ee, 15 }, // SET 5, (HL)
+ { &opcode_cb_ef, 8 }, // SET 5, A
+ { &opcode_cb_f0, 8 }, // SET 6, B
+ { &opcode_cb_f1, 8 }, // SET 6, C
+ { &opcode_cb_f2, 8 }, // SET 6, D
+ { &opcode_cb_f3, 8 }, // SET 6, E
+ { &opcode_cb_f4, 8 }, // SET 6, H
+ { &opcode_cb_f5, 8 }, // SET 6, L
+ { &opcode_cb_f6, 15 }, // SET 6, (HL)
+ { &opcode_cb_f7, 8 }, // SET 6, A
+ { &opcode_cb_f8, 8 }, // SET 7, B
+ { &opcode_cb_f9, 8 }, // SET 7, C
+ { &opcode_cb_fa, 8 }, // SET 7, D
+ { &opcode_cb_fb, 8 }, // SET 7, E
+ { &opcode_cb_fc, 8 }, // SET 7, H
+ { &opcode_cb_fd, 8 }, // SET 7, L
+ { &opcode_cb_fe, 15 }, // SET 7, (HL)
+ { &opcode_cb_ff, 8 } // SET 7, A
+};
+
+void opcode_cb_00() // RLC B
+{
+ B = rotateLeftCarry( B );
+}
+
+void opcode_cb_01() // RLC C
+{
+ C = rotateLeftCarry( C );
+}
+
+void opcode_cb_02() // RLC D
+{
+ D = rotateLeftCarry( D );
+}
+
+void opcode_cb_03() // RLC E
+{
+ E = rotateLeftCarry( E );
+}
+
+void opcode_cb_04() // RLC H
+{
+ H = rotateLeftCarry( H );
+}
+
+void opcode_cb_05() // RLC L
+{
+ L = rotateLeftCarry( L );
+}
+
+void opcode_cb_06() // RLC (HL)
+{
+ writeByte( HL(), rotateLeftCarry( readByte( HL() ) ) );
+}
+
+void opcode_cb_07() // RLC A
+{
+ A = rotateLeftCarry( A );
+}
+
+void opcode_cb_08() // RRC B
+{
+ B = rotateRightCarry( B );
+}
+
+void opcode_cb_09() // RRC C
+{
+ C = rotateLeftCarry( C );
+}
+
+void opcode_cb_0a() // RRC D
+{
+ D = rotateLeftCarry( D );
+}
+
+void opcode_cb_0b() // RRC E
+{
+ E = rotateLeftCarry( E );
+}
+
+void opcode_cb_0c() // RRC H
+{
+ H = rotateLeftCarry( H );
+}
+
+void opcode_cb_0d() // RRC L
+{
+ L = rotateLeftCarry( L );
+}
+
+void opcode_cb_0e() // RRC (HL)
+{
+ writeByte( HL(), rotateRightCarry( readByte( HL() ) ) );
+}
+
+void opcode_cb_0f() // RRC A
+{
+ A = rotateLeftCarry( A );
+}
+
+void opcode_cb_10() // RL B
+{
+ B = rotateLeft( B );
+}
+
+void opcode_cb_11() // RL C
+{
+ C = rotateLeft( C );
+}
+
+void opcode_cb_12() // RL D
+{
+ D = rotateLeft( D );
+}
+
+void opcode_cb_13() // RL E
+{
+ E = rotateLeft( E );
+}
+
+void opcode_cb_14() // RL H
+{
+ H = rotateLeft( H );
+}
+
+void opcode_cb_15() // RL L
+{
+ L = rotateLeft( L );
+}
+
+void opcode_cb_16() // RL (HL)
+{
+ writeByte( HL(), rotateLeft( readByte( HL() ) ) );
+}
+
+void opcode_cb_17() // RL A
+{
+ A = rotateLeft( A );
+}
+
+void opcode_cb_18() // RR B
+{
+ B = rotateRight( B );
+}
+
+void opcode_cb_19() // RR C
+{
+ C = rotateRight( C );
+}
+
+void opcode_cb_1a() // RR D
+{
+ D = rotateRight( D );
+}
+
+void opcode_cb_1b() // RR E
+{
+ E = rotateRight( E );
+}
+
+void opcode_cb_1c() // RR H
+{
+ H = rotateRight( H );
+}
+
+void opcode_cb_1d() // RR L
+{
+ L = rotateRight( L );
+}
+
+void opcode_cb_1e() // RR (HL)
+{
+ writeByte( HL(), rotateRight( readByte( HL() ) ) );
+}
+
+void opcode_cb_1f() // RR A
+{
+ A = rotateRight( A );
+}
+
+void opcode_cb_20() // SLA B
+{
+ B = shiftLeft( B );
+}
+
+void opcode_cb_21() // SLA C
+{
+ C = shiftLeft( C );
+}
+
+void opcode_cb_22() // SLA D
+{
+ D = shiftLeft( D );
+}
+
+void opcode_cb_23() // SLA E
+{
+ E = shiftLeft( E );
+}
+
+void opcode_cb_24() // SLA H
+{
+ H = shiftLeft( H );
+}
+
+void opcode_cb_25() // SLA L
+{
+ L = shiftLeft( L );
+}
+
+void opcode_cb_26() // SLA (HL)
+{
+ writeByte( HL(), shiftLeft( readByte( HL() ) ) );
+}
+
+void opcode_cb_27() // SLA A
+{
+ A = shiftLeft( A );
+}
+
+void opcode_cb_28() // SRA B
+{
+ B = shiftRightArith( B );
+}
+
+void opcode_cb_29() // SRA C
+{
+ C = shiftRightArith( C );
+}
+
+void opcode_cb_2a() // SRA D
+{
+ D = shiftRightArith( D );
+}
+
+void opcode_cb_2b() // SRA E
+{
+ E = shiftRightArith( E );
+}
+
+void opcode_cb_2c() // SRA H
+{
+ H = shiftRightArith( H );
+}
+
+void opcode_cb_2d() // SRA L
+{
+ L = shiftRightArith( L );
+}
+
+void opcode_cb_2e() // SRA (HL)
+{
+ writeByte( HL(), shiftRightArith( readByte( HL() ) ) );
+}
+
+void opcode_cb_2f() // SRA A
+{
+ A = shiftRightArith( A );
+}
+
+void opcode_cb_30() // SLL B
+{
+ B = shiftLeft( B ) | 0x01;
+}
+
+void opcode_cb_31() // SLL C
+{
+ C = shiftLeft( C ) | 0x01;
+}
+
+void opcode_cb_32() // SLL D
+{
+ D = shiftLeft( D ) | 0x01;
+}
+
+void opcode_cb_33() // SLL E
+{
+ E = shiftLeft( E ) | 0x01;
+}
+
+void opcode_cb_34() // SLL H
+{
+ H = shiftLeft( H ) | 0x01;
+}
+
+void opcode_cb_35() // SLL L
+{
+ L = shiftLeft( L ) | 0x01;
+}
+
+void opcode_cb_36() // SLL (HL)
+{
+ writeByte( HL(), shiftLeft( readByte( HL() ) ) | 0x01 );
+}
+
+void opcode_cb_37() // SLL A
+{
+ A = shiftLeft( A ) | 0x01;
+}
+
+void opcode_cb_38() // SRL B
+{
+ B = shiftRightLogical( B );
+}
+
+void opcode_cb_39() // SRL C
+{
+ C = shiftRightLogical( C );
+}
+
+void opcode_cb_3a() // SRL D
+{
+ D = shiftRightLogical( D );
+}
+
+void opcode_cb_3b() // SRL E
+{
+ E = shiftRightLogical( E );
+}
+
+void opcode_cb_3c() // SRL H
+{
+ H = shiftRightLogical( H );
+}
+
+void opcode_cb_3d() // SRL L
+{
+ L = shiftRightLogical( L );
+}
+
+void opcode_cb_3e() // SRL (HL)
+{
+ writeByte( HL(), shiftRightLogical( readByte( HL() ) ) );
+}
+
+void opcode_cb_3f() // SRL A
+{
+ A = shiftRightLogical( A );
+}
+
+void opcode_cb_40() // BIT 0, B
+{
+ testBit( 0, B );
+}
+
+void opcode_cb_41() // BIT 0, C
+{
+ testBit( 0, C );
+}
+
+void opcode_cb_42() // BIT 0, D
+{
+ testBit( 0, D );
+}
+
+void opcode_cb_43() // BIT 0, E
+{
+ testBit( 0, E );
+}
+
+void opcode_cb_44() // BIT 0, H
+{
+ testBit( 0, H );
+}
+
+void opcode_cb_45() // BIT 0, L
+{
+ testBit( 0, L );
+}
+
+void opcode_cb_46() // BIT 0, (HL)
+{
+ testBit( 0, readByte( HL() ) );
+}
+
+void opcode_cb_47() // BIT 0, A
+{
+ testBit( 0, A );
+}
+
+void opcode_cb_48() // BIT 1, B
+{
+ testBit( 1, B );
+}
+
+void opcode_cb_49() // BIT 1, C
+{
+ testBit( 1, C );
+}
+
+void opcode_cb_4a() // BIT 1, D
+{
+ testBit( 1, D );
+}
+
+void opcode_cb_4b() // BIT 1, E
+{
+ testBit( 1, E );
+}
+
+void opcode_cb_4c() // BIT 1, H
+{
+ testBit( 1, H );
+}
+
+void opcode_cb_4d() // BIT 1, L
+{
+ testBit( 1, L );
+}
+
+void opcode_cb_4e() // BIT 1, (HL)
+{
+ testBit( 1, readByte( HL() ) );
+}
+
+void opcode_cb_4f() // BIT 1, A
+{
+ testBit( 1, A );
+}
+
+void opcode_cb_50() // BIT 2, B
+{
+ testBit( 2, B );
+}
+
+void opcode_cb_51() // BIT 2, C
+{
+ testBit( 2, C );
+}
+
+void opcode_cb_52() // BIT 2, D
+{
+ testBit( 2, D );
+}
+
+void opcode_cb_53() // BIT 2, E
+{
+ testBit( 2, E );
+}
+
+void opcode_cb_54() // BIT 2, H
+{
+ testBit( 2, H );
+}
+
+void opcode_cb_55() // BIT 2, L
+{
+ testBit( 2, L );
+}
+
+void opcode_cb_56() // BIT 2, (HL)
+{
+ testBit( 2, readByte( HL() ) );
+}
+
+void opcode_cb_57() // BIT 2, A
+{
+ testBit( 2, A );
+}
+
+void opcode_cb_58() // BIT 3, B
+{
+ testBit( 3, B );
+}
+
+void opcode_cb_59() // BIT 3, C
+{
+ testBit( 3, C );
+}
+
+void opcode_cb_5a() // BIT 3, D
+{
+ testBit( 3, D );
+}
+
+void opcode_cb_5b() // BIT 3, E
+{
+ testBit( 3, E );
+}
+
+void opcode_cb_5c() // BIT 3, H
+{
+ testBit( 3, H );
+}
+
+void opcode_cb_5d() // BIT 3, L
+{
+ testBit( 3, L );
+}
+
+void opcode_cb_5e() // BIT 3, (HL)
+{
+ testBit( 3, readByte( HL() ) );
+}
+
+void opcode_cb_5f() // BIT 3, A
+{
+ testBit( 3, A );
+}
+
+void opcode_cb_60() // BIT 4, B
+{
+ testBit( 4, B );
+}
+
+void opcode_cb_61() // BIT 4, C
+{
+ testBit( 4, C );
+}
+
+void opcode_cb_62() // BIT 4, D
+{
+ testBit( 4, D );
+}
+
+void opcode_cb_63() // BIT 4, E
+{
+ testBit( 4, E );
+}
+
+void opcode_cb_64() // BIT 4, H
+{
+ testBit( 4, H );
+}
+
+void opcode_cb_65() // BIT 4, L
+{
+ testBit( 4, L );
+}
+
+void opcode_cb_66() // BIT 4, (HL)
+{
+ testBit( 4, readByte( HL() ) );
+}
+
+void opcode_cb_67() // BIT 4, A
+{
+ testBit( 4, A );
+}
+
+void opcode_cb_68() // BIT 5, B
+{
+ testBit( 5, B );
+}
+
+void opcode_cb_69() // BIT 5, C
+{
+ testBit( 5, C );
+}
+
+void opcode_cb_6a() // BIT 5, D
+{
+ testBit( 5, D );
+}
+
+void opcode_cb_6b() // BIT 5, E
+{
+ testBit( 5, E );
+}
+
+void opcode_cb_6c() // BIT 5, H
+{
+ testBit( 5, H );
+}
+
+void opcode_cb_6d() // BIT 5, L
+{
+ testBit( 5, L );
+}
+
+void opcode_cb_6e() // BIT 5, (HL)
+{
+ testBit( 5, readByte( HL() ) );
+}
+
+void opcode_cb_6f() // BIT 5, A
+{
+ testBit( 5, A );
+}
+
+void opcode_cb_70() // BIT 6, B
+{
+ testBit( 6, B );
+}
+
+void opcode_cb_71() // BIT 6, C
+{
+ testBit( 6, C );
+}
+
+void opcode_cb_72() // BIT 6, D
+{
+ testBit( 6, D );
+}
+
+void opcode_cb_73() // BIT 6, E
+{
+ testBit( 6, E );
+}
+
+void opcode_cb_74() // BIT 6, H
+{
+ testBit( 6, H );
+}
+
+void opcode_cb_75() // BIT 6, L
+{
+ testBit( 6, L );
+}
+
+void opcode_cb_76() // BIT 6, (HL)
+{
+ testBit( 6, readByte( HL() ) );
+}
+
+void opcode_cb_77() // BIT 6, A
+{
+ testBit( 6, A );
+}
+
+void opcode_cb_78() // BIT 7, B
+{
+ testBit( 7, B );
+}
+
+void opcode_cb_79() // BIT 7, C
+{
+ testBit( 7, C );
+}
+
+void opcode_cb_7a() // BIT 7, D
+{
+ testBit( 7, D );
+}
+
+void opcode_cb_7b() // BIT 7, E
+{
+ testBit( 7, E );
+}
+
+void opcode_cb_7c() // BIT 7, H
+{
+ testBit( 7, H );
+}
+
+void opcode_cb_7d() // BIT 7, L
+{
+ testBit( 7, L );
+}
+
+void opcode_cb_7e() // BIT 7, (HL)
+{
+ testBit( 7, readByte( HL() ) );
+}
+
+void opcode_cb_7f() // BIT 7, A
+{
+ testBit( 7, A );
+}
+
+void opcode_cb_80() // RES 0, B
+{
+ B &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_81() // RES 0, C
+{
+ C &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_82() // RES 0, D
+{
+ D &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_83() // RES 0, E
+{
+ E &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_84() // RES 0, H
+{
+ H &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_85() // RES 0, L
+{
+ L &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_86() // RES 0, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 0) );
+}
+
+void opcode_cb_87() // RES 0, A
+{
+ A &= ~(unsigned char) (1 << 0);
+}
+
+void opcode_cb_88() // RES 1, B
+{
+ B &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_89() // RES 1, C
+{
+ C &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_8a() // RES 1, D
+{
+ D &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_8b() // RES 1, E
+{
+ E &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_8c() // RES 1, H
+{
+ H &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_8d() // RES 1, L
+{
+ L &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_8e() // RES 1, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 1) );
+}
+
+void opcode_cb_8f() // RES 1, A
+{
+ A &= ~(unsigned char) (1 << 1);
+}
+
+void opcode_cb_90() // RES 2, B
+{
+ B &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_91() // RES 2, C
+{
+ C &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_92() // RES 2, D
+{
+ D &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_93() // RES 2, E
+{
+ E &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_94() // RES 2, H
+{
+ H &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_95() // RES 2, L
+{
+ L &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_96() // RES 2, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 2) );
+}
+
+void opcode_cb_97() // RES 2, A
+{
+ A &= ~(unsigned char) (1 << 2);
+}
+
+void opcode_cb_98() // RES 3, B
+{
+ B &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_99() // RES 3, C
+{
+ C &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_9a() // RES 3, D
+{
+ D &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_9b() // RES 3, E
+{
+ E &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_9c() // RES 3, H
+{
+ H &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_9d() // RES 3, L
+{
+ L &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_9e() // RES 3, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 3) );
+}
+
+void opcode_cb_9f() // RES 3, A
+{
+ A &= ~(unsigned char) (1 << 3);
+}
+
+void opcode_cb_a0() // RES 4, B
+{
+ B &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a1() // RES 4, C
+{
+ C &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a2() // RES 4, D
+{
+ D &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a3() // RES 4, E
+{
+ E &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a4() // RES 4, H
+{
+ H &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a5() // RES 4, L
+{
+ L &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a6() // RES 4, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 4) );
+}
+
+void opcode_cb_a7() // RES 4, A
+{
+ A &= ~(unsigned char) (1 << 4);
+}
+
+void opcode_cb_a8() // RES 5, B
+{
+ B &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_a9() // RES 5, C
+{
+ C &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_aa() // RES 5, D
+{
+ D &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_ab() // RES 5, E
+{
+ E &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_ac() // RES 5, H
+{
+ H &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_ad() // RES 5, L
+{
+ L &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_ae() // RES 5, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 5) );
+}
+
+void opcode_cb_af() // RES 5, A
+{
+ A &= ~(unsigned char) (1 << 5);
+}
+
+void opcode_cb_b0() // RES 6, B
+{
+ B &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b1() // RES 6, C
+{
+ C &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b2() // RES 6, D
+{
+ D &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b3() // RES 6, E
+{
+ E &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b4() // RES 6, H
+{
+ H &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b5() // RES 6, L
+{
+ L &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b6() // RES 6, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 6) );
+}
+
+void opcode_cb_b7() // RES 6, A
+{
+ A &= ~(unsigned char) (1 << 6);
+}
+
+void opcode_cb_b8() // RES 7, B
+{
+ B &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_b9() // RES 7, C
+{
+ C &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_ba() // RES 7, D
+{
+ D &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_bb() // RES 7, E
+{
+ E &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_bc() // RES 7, H
+{
+ H &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_bd() // RES 7, L
+{
+ L &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_be() // RES 7, (HL)
+{
+ writeByte( HL(), readByte( HL() ) & (unsigned char) ~(unsigned char) (1 << 7) );
+}
+
+void opcode_cb_bf() // RES 7, A
+{
+ A &= ~(unsigned char) (1 << 7);
+}
+
+void opcode_cb_c0() // SET 0, B
+{
+ B |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c1() // SET 0, C
+{
+ C |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c2() // SET 0, D
+{
+ D |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c3() // SET 0, E
+{
+ E |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c4() // SET 0, H
+{
+ H |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c5() // SET 0, L
+{
+ L |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c6() // SET 0, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 0) );
+}
+
+void opcode_cb_c7() // SET 0, A
+{
+ A |= (unsigned char) (1 << 0);
+}
+
+void opcode_cb_c8() // SET 1, B
+{
+ B |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_c9() // SET 1, C
+{
+ C |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_ca() // SET 1, D
+{
+ D |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_cb() // SET 1, E
+{
+ E |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_cc() // SET 1, H
+{
+ H |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_cd() // SET 1, L
+{
+ L |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_ce() // SET 1, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 1) );
+}
+
+void opcode_cb_cf() // SET 1, A
+{
+ A |= (unsigned char) (1 << 1);
+}
+
+void opcode_cb_d0() // SET 2, B
+{
+ B |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d1() // SET 2, C
+{
+ C |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d2() // SET 2, D
+{
+ D |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d3() // SET 2, E
+{
+ E |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d4() // SET 2, H
+{
+ H |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d5() // SET 2, L
+{
+ L |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d6() // SET 2, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 2) );
+}
+
+void opcode_cb_d7() // SET 2, A
+{
+ A |= (unsigned char) (1 << 2);
+}
+
+void opcode_cb_d8() // SET 3, B
+{
+ B |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_d9() // SET 3, C
+{
+ C |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_da() // SET 3, D
+{
+ D |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_db() // SET 3, E
+{
+ E |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_dc() // SET 3, H
+{
+ H |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_dd() // SET 3, L
+{
+ L |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_de() // SET 3, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 3) );
+}
+
+void opcode_cb_df() // SET 3, A
+{
+ A |= (unsigned char) (1 << 3);
+}
+
+void opcode_cb_e0() // SET 4, B
+{
+ B |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e1() // SET 4, C
+{
+ C |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e2() // SET 4, D
+{
+ D |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e3() // SET 4, E
+{
+ E |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e4() // SET 4, H
+{
+ H |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e5() // SET 4, L
+{
+ L |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e6() // SET 4, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 4) );
+}
+
+void opcode_cb_e7() // SET 4, A
+{
+ A |= (unsigned char) (1 << 4);
+}
+
+void opcode_cb_e8() // SET 5, B
+{
+ B |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_e9() // SET 5, C
+{
+ C |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_ea() // SET 5, D
+{
+ D |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_eb() // SET 5, E
+{
+ E |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_ec() // SET 5, H
+{
+ H |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_ed() // SET 5, L
+{
+ L |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_ee() // SET 5, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 5) );
+}
+
+void opcode_cb_ef() // SET 5, A
+{
+ A |= (unsigned char) (1 << 5);
+}
+
+void opcode_cb_f0() // SET 6, B
+{
+ B |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f1() // SET 6, C
+{
+ C |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f2() // SET 6, D
+{
+ D |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f3() // SET 6, E
+{
+ E |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f4() // SET 6, H
+{
+ H |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f5() // SET 6, L
+{
+ L |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f6() // SET 6, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 6) );
+}
+
+void opcode_cb_f7() // SET 6, A
+{
+ A |= (unsigned char) (1 << 6);
+}
+
+void opcode_cb_f8() // SET 7, B
+{
+ B |= (unsigned char) (1 << 7);
+}
+
+void opcode_cb_f9() // SET 7, C
+{
+ C |= (unsigned char) (1 << 7);
+}
+
+void opcode_cb_fa() // SET 7, D
+{
+ D |= (unsigned char) (1 << 7);
+}
+
+void opcode_cb_fb() // SET 7, E
+{
+ E |= (unsigned char) (1 << 7);
+}
+
+void opcode_cb_fc() // SET 7, H
+{
+ H |= (unsigned char) (1 << 7);
+}
+
+void opcode_cb_fd() // SET 7, L
+{
+ L |= (unsigned char) (1 << 7);
+}
+
+void opcode_cb_fe() // SET 7, (HL)
+{
+ writeByte( HL(), readByte( HL() ) | (unsigned char) (1 << 7) );
+}
+
+void opcode_cb_ff() // SET 7, A
+{
+ A |= (unsigned char) (1 << 7);
+}
+
+OpcodeInfo OpInfoDD_[256] = {
+ { 0, 0 }, // 0x00
+ { 0, 0 }, // 0x01
+ { 0, 0 }, // 0x02
+ { 0, 0 }, // 0x03
+ { 0, 0 }, // 0x04
+ { 0, 0 }, // 0x05
+ { 0, 0 }, // 0x06
+ { 0, 0 }, // 0x07
+ { 0, 0 }, // 0x08
+ { &opcode_dd_09, 15 }, // ADD IX, BC
+ { 0, 0 }, // 0x0A
+ { 0, 0 }, // 0x0B
+ { 0, 0 }, // 0x0C
+ { 0, 0 }, // 0x0D
+ { 0, 0 }, // 0x0E
+ { 0, 0 }, // 0x0F
+ { 0, 0 }, // 0x10
+ { 0, 0 }, // 0x11
+ { 0, 0 }, // 0x12
+ { 0, 0 }, // 0x13
+ { 0, 0 }, // 0x14
+ { 0, 0 }, // 0x15
+ { 0, 0 }, // 0x16
+ { 0, 0 }, // 0x17
+ { 0, 0 }, // 0x18
+ { &opcode_dd_19, 15 }, // ADD IX, DE
+ { 0, 0 }, // 0x1A
+ { 0, 0 }, // 0x1B
+ { 0, 0 }, // 0x1C
+ { 0, 0 }, // 0x1D
+ { 0, 0 }, // 0x1E
+ { 0, 0 }, // 0x1F
+ { 0, 0 }, // 0x20
+ { &opcode_dd_21, 14 }, // LD IX, nn
+ { &opcode_dd_22, 20 }, // LD (nn), IX
+ { &opcode_dd_23, 10 }, // INC IX
+ { &opcode_dd_24, 9 }, // INC IXH
+ { &opcode_dd_25, 9 }, // DEC IXH
+ { &opcode_dd_26, 9 }, // LD IXH, n
+ { 0, 0 }, // 0x27
+ { 0, 0 }, // 0x28
+ { &opcode_dd_29, 15 }, // ADD IX, IX
+ { &opcode_dd_2a, 20 }, // LD IX, (nn)
+ { &opcode_dd_2b, 10 }, // DEC IX
+ { &opcode_dd_2c, 9 }, // INC IXL
+ { &opcode_dd_2d, 9 }, // DEC IXL
+ { &opcode_dd_2e, 9 }, // LD IXL, n
+ { 0, 0 }, // 0x2F
+ { 0, 0 }, // 0x30
+ { 0, 0 }, // 0x31
+ { 0, 0 }, // 0x32
+ { 0, 0 }, // 0x33
+ { &opcode_dd_34, 23 }, // INC (IX + d)
+ { &opcode_dd_35, 23 }, // DEC (IX + d)
+ { &opcode_dd_36, 19 }, // LD (IX + d), n
+ { 0, 0 }, // 0x37
+ { 0, 0 }, // 0x38
+ { &opcode_dd_39, 15 }, // ADD IX, SP
+ { 0, 0 }, // 0x3A
+ { 0, 0 }, // 0x3B
+ { 0, 0 }, // 0x3C
+ { 0, 0 }, // 0x3D
+ { 0, 0 }, // 0x3E
+ { 0, 0 }, // 0x3F
+ { 0, 0 }, // 0x40
+ { 0, 0 }, // 0x41
+ { 0, 0 }, // 0x42
+ { 0, 0 }, // 0x43
+ { &opcode_dd_44, 9 }, // LD B, IXH
+ { &opcode_dd_45, 9 }, // LD B, IXL
+ { &opcode_dd_46, 19 }, // LD B, (IX + d)
+ { 0, 0 }, // 0x47
+ { 0, 0 }, // 0x48
+ { 0, 0 }, // 0x49
+ { 0, 0 }, // 0x4A
+ { 0, 0 }, // 0x4B
+ { &opcode_dd_4c, 9 }, // LD C, IXH
+ { &opcode_dd_4d, 9 }, // LD C, IXL
+ { &opcode_dd_4e, 19 }, // LD C, (IX + d)
+ { 0, 0 }, // 0x4F
+ { 0, 0 }, // 0x50
+ { 0, 0 }, // 0x51
+ { 0, 0 }, // 0x52
+ { 0, 0 }, // 0x53
+ { &opcode_dd_54, 9 }, // LD D, IXH
+ { &opcode_dd_55, 9 }, // LD D, IXL
+ { &opcode_dd_56, 19 }, // LD D, (IX + d)
+ { 0, 0 }, // 0x57
+ { 0, 0 }, // 0x58
+ { 0, 0 }, // 0x59
+ { 0, 0 }, // 0x5A
+ { 0, 0 }, // 0x5B
+ { &opcode_dd_5c, 9 }, // LD E, IXH
+ { &opcode_dd_5d, 9 }, // LD E, IXL
+ { &opcode_dd_5e, 19 }, // LD E, (IX + d)
+ { 0, 0 }, // 0x5F
+ { &opcode_dd_60, 9 }, // LD IXH, B
+ { &opcode_dd_61, 9 }, // LD IXH, C
+ { &opcode_dd_62, 9 }, // LD IXH, D
+ { &opcode_dd_63, 9 }, // LD IXH, E
+ { &opcode_dd_64, 9 }, // LD IXH, IXH
+ { &opcode_dd_65, 9 }, // LD IXH, IXL
+ { &opcode_dd_66, 9 }, // LD H, (IX + d)
+ { &opcode_dd_67, 9 }, // LD IXH, A
+ { &opcode_dd_68, 9 }, // LD IXL, B
+ { &opcode_dd_69, 9 }, // LD IXL, C
+ { &opcode_dd_6a, 9 }, // LD IXL, D
+ { &opcode_dd_6b, 9 }, // LD IXL, E
+ { &opcode_dd_6c, 9 }, // LD IXL, IXH
+ { &opcode_dd_6d, 9 }, // LD IXL, IXL
+ { &opcode_dd_6e, 9 }, // LD L, (IX + d)
+ { &opcode_dd_6f, 9 }, // LD IXL, A
+ { &opcode_dd_70, 19 }, // LD (IX + d), B
+ { &opcode_dd_71, 19 }, // LD (IX + d), C
+ { &opcode_dd_72, 19 }, // LD (IX + d), D
+ { &opcode_dd_73, 19 }, // LD (IX + d), E
+ { &opcode_dd_74, 19 }, // LD (IX + d), H
+ { &opcode_dd_75, 19 }, // LD (IX + d), L
+ { 0,19 }, // 0x76
+ { &opcode_dd_77, 19 }, // LD (IX + d), A
+ { 0, 0 }, // 0x78
+ { 0, 0 }, // 0x79
+ { 0, 0 }, // 0x7A
+ { 0, 0 }, // 0x7B
+ { &opcode_dd_7c, 9 }, // LD A, IXH
+ { &opcode_dd_7d, 9 }, // LD A, IXL
+ { &opcode_dd_7e, 19 }, // LD A, (IX + d)
+ { 0, 0 }, // 0x7F
+ { 0, 0 }, // 0x80
+ { 0, 0 }, // 0x81
+ { 0, 0 }, // 0x82
+ { 0, 0 }, // 0x83
+ { &opcode_dd_84, 9 }, // ADD A, IXH
+ { &opcode_dd_85, 9 }, // ADD A, IXL
+ { &opcode_dd_86, 19 }, // ADD A, (IX + d)
+ { 0, 0 }, // 0x87
+ { 0, 0 }, // 0x88
+ { 0, 0 }, // 0x89
+ { 0, 0 }, // 0x8A
+ { 0, 0 }, // 0x8B
+ { &opcode_dd_8c, 9 }, // ADC A, IXH
+ { &opcode_dd_8d, 9 }, // ADC A, IXL
+ { &opcode_dd_8e, 19 }, // ADC A, (IX + d)
+ { 0, 0 }, // 0x8F
+ { 0, 0 }, // 0x90
+ { 0, 0 }, // 0x91
+ { 0, 0 }, // 0x92
+ { 0, 0 }, // 0x93
+ { &opcode_dd_94, 9 }, // SUB IXH
+ { &opcode_dd_95, 9 }, // SUB IXL
+ { &opcode_dd_96, 19 }, // SUB (IX + d)
+ { 0, 0 }, // 0x97
+ { 0, 0 }, // 0x98
+ { 0, 0 }, // 0x99
+ { 0, 0 }, // 0x9A
+ { 0, 0 }, // 0x9B
+ { &opcode_dd_9c, 9 }, // SBC A, IXH
+ { &opcode_dd_9d, 9 }, // SBC A, IXL
+ { &opcode_dd_9e, 19 }, // SBC A, (IX + d)
+ { 0, 0 }, // 0x9F
+ { 0, 0 }, // 0xA0
+ { 0, 0 }, // 0xA1
+ { 0, 0 }, // 0xA2
+ { 0, 0 }, // 0xA3
+ { &opcode_dd_a4, 9 }, // AND IXH
+ { &opcode_dd_a5, 9 }, // AND IXL
+ { &opcode_dd_a6, 19 }, // AND (IX + d)
+ { 0, 0 }, // 0xA7
+ { 0, 0 }, // 0xA8
+ { 0, 0 }, // 0xA9
+ { 0, 0 }, // 0xAA
+ { 0, 0 }, // 0xAB
+ { &opcode_dd_ac, 9 }, // XOR IXH
+ { &opcode_dd_ad, 9 }, // XOR IXL
+ { &opcode_dd_ae, 19 }, // XOR (IX + d)
+ { 0, 0 }, // 0xAF
+ { 0, 0 }, // 0xB0
+ { 0, 0 }, // 0xB1
+ { 0, 0 }, // 0xB2
+ { 0, 0 }, // 0xB3
+ { &opcode_dd_b4, 9 }, // OR IXH
+ { &opcode_dd_b5, 9 }, // OR IXL
+ { &opcode_dd_b6, 19 }, // OR (IX + d)
+ { 0, 0 }, // 0xB7
+ { 0, 0 }, // 0xB8
+ { 0, 0 }, // 0xB9
+ { 0, 0 }, // 0xBA
+ { 0, 0 }, // 0xBB
+ { &opcode_dd_bc, 9 }, // CP IXH
+ { &opcode_dd_bd, 9 }, // CP IXL
+ { &opcode_dd_be, 19 }, // CP (IX + d)
+ { 0, 0 }, // 0xBF
+ { 0, 0 }, // 0xC0
+ { 0, 0 }, // 0xC1
+ { 0, 0 }, // 0xC2
+ { 0, 0 }, // 0xC3
+ { 0, 0 }, // 0xC4
+ { 0, 0 }, // 0xC5
+ { 0, 0 }, // 0xC6
+ { 0, 0 }, // 0xC7
+ { 0, 0 }, // 0xC8
+ { 0, 0 }, // 0xC9
+ { 0, 0 }, // 0xCA
+ { &opcode_dd_cb, 0 }, //
+ { 0, 0 }, // 0xCC
+ { 0, 0 }, // 0xCD
+ { 0, 0 }, // 0xCE
+ { 0, 0 }, // 0xCF
+ { 0, 0 }, // 0xD0
+ { 0, 0 }, // 0xD1
+ { 0, 0 }, // 0xD2
+ { 0, 0 }, // 0xD3
+ { 0, 0 }, // 0xD4
+ { 0, 0 }, // 0xD5
+ { 0, 0 }, // 0xD6
+ { 0, 0 }, // 0xD7
+ { 0, 0 }, // 0xD8
+ { 0, 0 }, // 0xD9
+ { 0, 0 }, // 0xDA
+ { 0, 0 }, // 0xDB
+ { 0, 0 }, // 0xDC
+ { 0, 0 }, // 0xDD
+ { 0, 0 }, // 0xDE
+ { 0, 0 }, // 0xDF
+ { 0, 0 }, // 0xE0
+ { &opcode_dd_e1, 14 }, // POP IX
+ { 0, 0 }, // 0xE2
+ { &opcode_dd_e3, 23 }, // EX (SP), IX
+ { 0, 0 }, // 0xE4
+ { &opcode_dd_e5, 15 }, // PUSH IX
+ { 0, 0 }, // 0xE6
+ { 0, 0 }, // 0xE7
+ { 0, 0 }, // 0xE8
+ { &opcode_dd_e9, 8 }, // JP (IX)
+ { 0, 0 }, // 0xEA
+ { 0, 0 }, // 0xEB
+ { 0, 0 }, // 0xEC
+ { 0, 0 }, // 0xED
+ { 0, 0 }, // 0xEE
+ { 0, 0 }, // 0xEF
+ { 0, 0 }, // 0xF0
+ { 0, 0 }, // 0xF1
+ { 0, 0 }, // 0xF2
+ { 0, 0 }, // 0xF3
+ { 0, 0 }, // 0xF4
+ { 0, 0 }, // 0xF5
+ { 0, 0 }, // 0xF6
+ { 0, 0 }, // 0xF7
+ { 0, 0 }, // 0xF8
+ { &opcode_dd_f9, 10 }, // LD SP, IX
+ { 0, 0 }, // 0xFA
+ { 0, 0 }, // 0xFB
+ { 0, 0 }, // 0xFC
+ { 0, 0 }, // 0xFD
+ { 0, 0 }, // 0xFE
+ { 0, 0 } // 0xFF
+};
+
+void opcode_dd_09() // ADD IX, BC
+{
+ unsigned rr = BC();
+
+ F &= (Zero | Sign | Parity);
+ if( ((IX & 0xFFF)+(rr & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+ IX += rr;
+ if( IX & 0x10000 ) F |= Carry;
+}
+
+void opcode_dd_19() // ADD IX, DE
+{
+ unsigned rr = DE();
+
+ F &= (Zero | Sign | Parity);
+ if( ((IX & 0xFFF)+(rr & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+ IX += rr;
+ if( IX & 0x10000 ) F |= Carry;
+}
+
+void opcode_dd_21() // LD IX, nn
+{
+ IX = fetchWord();
+}
+
+void opcode_dd_22() // LD (nn), IX
+{
+ writeWord( fetchWord(), IX );
+}
+
+void opcode_dd_23() // INC IX
+{
+ IX++;
+}
+
+void opcode_dd_24() // INC IXH
+{
+ IX = (IX & 0xFF) | ((unsigned)incByte( IX >> 8 ) << 8);
+}
+
+void opcode_dd_25() // DEC IXH
+{
+ IX = (IX & 0xFF) | ((unsigned)decByte( IX >> 8 ) << 8);
+}
+
+void opcode_dd_26() // LD IXH, n
+{
+ IX = (IX & 0xFF) | ((unsigned)fetchByte() << 8);
+}
+
+void opcode_dd_29() // ADD IX, IX
+{
+ F &= (Zero | Sign | Parity);
+ if( IX & 0x800 ) F |= Halfcarry;
+ IX += IX;
+ if( IX & 0x10000 ) F |= Carry;
+}
+
+void opcode_dd_2a() // LD IX, (nn)
+{
+ IX = readWord( fetchWord() );
+}
+
+void opcode_dd_2b() // DEC IX
+{
+ IX--;
+}
+
+void opcode_dd_2c() // INC IXL
+{
+ IX = (IX & 0xFF00) | incByte( IX & 0xFF );
+}
+
+void opcode_dd_2d() // DEC IXL
+{
+ IX = (IX & 0xFF00) | decByte( IX & 0xFF );
+}
+
+void opcode_dd_2e() // LD IXL, n
+{
+ IX = (IX & 0xFF00) | fetchByte();
+}
+
+void opcode_dd_34() // INC (IX + d)
+{
+ unsigned addr = addDispl( IX, fetchByte() );
+
+ writeByte( addr, incByte( readByte( addr ) ) );
+}
+
+void opcode_dd_35() // DEC (IX + d)
+{
+ unsigned addr = addDispl( IX, fetchByte() );
+
+ writeByte( addr, decByte( readByte( addr ) ) );
+}
+
+void opcode_dd_36() // LD (IX + d), n
+{
+ unsigned addr = addDispl( IX, fetchByte() );
+
+ writeByte( addr, fetchByte() );
+}
+
+void opcode_dd_39() // ADD IX, SP
+{
+ F &= (Zero | Sign | Parity);
+ if( ((IX & 0xFFF)+(SP & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+ IX += SP;
+ if( IX & 0x10000 ) F |= Carry;
+}
+
+void opcode_dd_44() // LD B, IXH
+{
+ B = IX >> 8;
+}
+
+void opcode_dd_45() // LD B, IXL
+{
+ B = IX & 0xFF;
+}
+
+void opcode_dd_46() // LD B, (IX + d)
+{
+ B = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_4c() // LD C, IXH
+{
+ C = IX >> 8;
+}
+
+void opcode_dd_4d() // LD C, IXL
+{
+ C = IX & 0xFF;
+}
+
+void opcode_dd_4e() // LD C, (IX + d)
+{
+ C = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_54() // LD D, IXH
+{
+ D = IX >> 8;
+}
+
+void opcode_dd_55() // LD D, IXL
+{
+ D = IX & 0xFF;
+}
+
+void opcode_dd_56() // LD D, (IX + d)
+{
+ D = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_5c() // LD E, IXH
+{
+ E = IX >> 8;
+}
+
+void opcode_dd_5d() // LD E, IXL
+{
+ E = IX & 0xFF;
+}
+
+void opcode_dd_5e() // LD E, (IX + d)
+{
+ E = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_60() // LD IXH, B
+{
+ IX = (IX & 0xFF) | ((unsigned)B << 8);
+}
+
+void opcode_dd_61() // LD IXH, C
+{
+ IX = (IX & 0xFF) | ((unsigned)C << 8);
+}
+
+void opcode_dd_62() // LD IXH, D
+{
+ IX = (IX & 0xFF) | ((unsigned)D << 8);
+}
+
+void opcode_dd_63() // LD IXH, E
+{
+ IX = (IX & 0xFF) | ((unsigned)E << 8);
+}
+
+void opcode_dd_64() // LD IXH, IXH
+{
+}
+
+void opcode_dd_65() // LD IXH, IXL
+{
+ IX = (IX & 0xFF) | ((IX << 8) & 0xFF00);
+}
+
+void opcode_dd_66() // LD H, (IX + d)
+{
+ H = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_67() // LD IXH, A
+{
+ IX = (IX & 0xFF) | ((unsigned)A << 8);
+}
+
+void opcode_dd_68() // LD IXL, B
+{
+ IX = (IX & 0xFF00) | B;
+}
+
+void opcode_dd_69() // LD IXL, C
+{
+ IX = (IX & 0xFF00) | C;
+}
+
+void opcode_dd_6a() // LD IXL, D
+{
+ IX = (IX & 0xFF00) | D;
+}
+
+void opcode_dd_6b() // LD IXL, E
+{
+ IX = (IX & 0xFF00) | E;
+}
+
+void opcode_dd_6c() // LD IXL, IXH
+{
+ IX = (IX & 0xFF00) | ((IX >> 8) & 0xFF);
+}
+
+void opcode_dd_6d() // LD IXL, IXL
+{
+}
+
+void opcode_dd_6e() // LD L, (IX + d)
+{
+ L = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_6f() // LD IXL, A
+{
+ IX = (IX & 0xFF00) | A;
+}
+
+void opcode_dd_70() // LD (IX + d), B
+{
+ writeByte( addDispl(IX,fetchByte()), B );
+}
+
+void opcode_dd_71() // LD (IX + d), C
+{
+ writeByte( addDispl(IX,fetchByte()), C );
+}
+
+void opcode_dd_72() // LD (IX + d), D
+{
+ writeByte( addDispl(IX,fetchByte()), D );
+}
+
+void opcode_dd_73() // LD (IX + d), E
+{
+ writeByte( addDispl(IX,fetchByte()), E );
+}
+
+void opcode_dd_74() // LD (IX + d), H
+{
+ writeByte( addDispl(IX,fetchByte()), H );
+}
+
+void opcode_dd_75() // LD (IX + d), L
+{
+ writeByte( addDispl(IX,fetchByte()), L );
+}
+
+void opcode_dd_77() // LD (IX + d), A
+{
+ writeByte( addDispl(IX,fetchByte()), A );
+}
+
+void opcode_dd_7c() // LD A, IXH
+{
+ A = IX >> 8;
+}
+
+void opcode_dd_7d() // LD A, IXL
+{
+ A = IX & 0xFF;
+}
+
+void opcode_dd_7e() // LD A, (IX + d)
+{
+ A = readByte( addDispl(IX,fetchByte()) );
+}
+
+void opcode_dd_84() // ADD A, IXH
+{
+ addByte( IX >> 8, 0 );
+}
+
+void opcode_dd_85() // ADD A, IXL
+{
+ addByte( IX & 0xFF, 0 );
+}
+
+void opcode_dd_86() // ADD A, (IX + d)
+{
+ addByte( readByte( addDispl(IX,fetchByte()) ), 0 );
+}
+
+void opcode_dd_8c() // ADC A, IXH
+{
+ addByte( IX >> 8, F & Carry );
+}
+
+void opcode_dd_8d() // ADC A, IXL
+{
+ addByte( IX & 0xFF, F & Carry );
+}
+
+void opcode_dd_8e() // ADC A, (IX + d)
+{
+ addByte( readByte( addDispl(IX,fetchByte()) ), F & Carry );
+}
+
+void opcode_dd_94() // SUB IXH
+{
+ A = subByte( IX >> 8, 0 );
+}
+
+void opcode_dd_95() // SUB IXL
+{
+ A = subByte( IX & 0xFF, 0 );
+}
+
+void opcode_dd_96() // SUB (IX + d)
+{
+ A = subByte( readByte( addDispl(IX,fetchByte()) ), 0 );
+}
+
+void opcode_dd_9c() // SBC A, IXH
+{
+ A = subByte( IX >> 8, F & Carry );
+}
+
+void opcode_dd_9d() // SBC A, IXL
+{
+ A = subByte( IX & 0xFF, F & Carry );
+}
+
+void opcode_dd_9e() // SBC A, (IX + d)
+{
+ A = subByte( readByte( addDispl(IX,fetchByte()) ), F & Carry );
+}
+
+void opcode_dd_a4() // AND IXH
+{
+ A &= IX >> 8;
+ setFlags35PSZ000();
+ F |= Halfcarry;
+}
+
+void opcode_dd_a5() // AND IXL
+{
+ A &= IX & 0xFF;
+ setFlags35PSZ000();
+ F |= Halfcarry;
+}
+
+void opcode_dd_a6() // AND (IX + d)
+{
+ A &= readByte( addDispl(IX,fetchByte()) );
+ setFlags35PSZ000();
+ F |= Halfcarry;
+}
+
+void opcode_dd_ac() // XOR IXH
+{
+ A ^= IX >> 8;
+ setFlags35PSZ000();
+}
+
+void opcode_dd_ad() // XOR IXL
+{
+ A ^= IX & 0xFF;
+ setFlags35PSZ000();
+}
+
+void opcode_dd_ae() // XOR (IX + d)
+{
+ A ^= readByte( addDispl(IX,fetchByte()) );
+ setFlags35PSZ000();
+}
+
+void opcode_dd_b4() // OR IXH
+{
+ A |= IX >> 8;
+ setFlags35PSZ000();
+}
+
+void opcode_dd_b5() // OR IXL
+{
+ A |= IX & 0xFF;
+ setFlags35PSZ000();
+}
+
+void opcode_dd_b6() // OR (IX + d)
+{
+ A |= readByte( addDispl(IX,fetchByte()) );
+ setFlags35PSZ000();
+}
+
+void opcode_dd_bc() // CP IXH
+{
+ cmpByte( IX >> 8 );
+}
+
+void opcode_dd_bd() // CP IXL
+{
+ cmpByte( IX & 0xFF );
+}
+
+void opcode_dd_be() // CP (IX + d)
+{
+ cmpByte( readByte( addDispl(IX,fetchByte()) ) );
+}
+
+void opcode_dd_cb() //
+{
+ do_opcode_xycb( IX );
+}
+
+void opcode_dd_e1() // POP IX
+{
+ IX = readWord( SP );
+ SP += 2;
+}
+
+void opcode_dd_e3() // EX (SP), IX
+{
+ unsigned ix = IX;
+
+ IX = readWord( SP );
+ writeWord( SP, ix );
+}
+
+void opcode_dd_e5() // PUSH IX
+{
+ SP -= 2;
+ writeWord( SP, IX );
+}
+
+void opcode_dd_e9() // JP (IX)
+{
+ PC = IX;
+}
+
+void opcode_dd_f9() // LD SP, IX
+{
+ SP = IX;
+}
+
+OpcodeInfo OpInfoED_[256] = {
+ { 0, 0 }, // 0x00
+ { 0, 0 }, // 0x01
+ { 0, 0 }, // 0x02
+ { 0, 0 }, // 0x03
+ { 0, 0 }, // 0x04
+ { 0, 0 }, // 0x05
+ { 0, 0 }, // 0x06
+ { 0, 0 }, // 0x07
+ { 0, 0 }, // 0x08
+ { 0, 0 }, // 0x09
+ { 0, 0 }, // 0x0A
+ { 0, 0 }, // 0x0B
+ { 0, 0 }, // 0x0C
+ { 0, 0 }, // 0x0D
+ { 0, 0 }, // 0x0E
+ { 0, 0 }, // 0x0F
+ { 0, 0 }, // 0x10
+ { 0, 0 }, // 0x11
+ { 0, 0 }, // 0x12
+ { 0, 0 }, // 0x13
+ { 0, 0 }, // 0x14
+ { 0, 0 }, // 0x15
+ { 0, 0 }, // 0x16
+ { 0, 0 }, // 0x17
+ { 0, 0 }, // 0x18
+ { 0, 0 }, // 0x19
+ { 0, 0 }, // 0x1A
+ { 0, 0 }, // 0x1B
+ { 0, 0 }, // 0x1C
+ { 0, 0 }, // 0x1D
+ { 0, 0 }, // 0x1E
+ { 0, 0 }, // 0x1F
+ { 0, 0 }, // 0x20
+ { 0, 0 }, // 0x21
+ { 0, 0 }, // 0x22
+ { 0, 0 }, // 0x23
+ { 0, 0 }, // 0x24
+ { 0, 0 }, // 0x25
+ { 0, 0 }, // 0x26
+ { 0, 0 }, // 0x27
+ { 0, 0 }, // 0x28
+ { 0, 0 }, // 0x29
+ { 0, 0 }, // 0x2A
+ { 0, 0 }, // 0x2B
+ { 0, 0 }, // 0x2C
+ { 0, 0 }, // 0x2D
+ { 0, 0 }, // 0x2E
+ { 0, 0 }, // 0x2F
+ { 0, 0 }, // 0x30
+ { 0, 0 }, // 0x31
+ { 0, 0 }, // 0x32
+ { 0, 0 }, // 0x33
+ { 0, 0 }, // 0x34
+ { 0, 0 }, // 0x35
+ { 0, 0 }, // 0x36
+ { 0, 0 }, // 0x37
+ { 0, 0 }, // 0x38
+ { 0, 0 }, // 0x39
+ { 0, 0 }, // 0x3A
+ { 0, 0 }, // 0x3B
+ { 0, 0 }, // 0x3C
+ { 0, 0 }, // 0x3D
+ { 0, 0 }, // 0x3E
+ { 0, 0 }, // 0x3F
+ { &opcode_ed_40, 12 }, // IN B, (C)
+ { &opcode_ed_41, 12 }, // OUT (C), B
+ { &opcode_ed_42, 15 }, // SBC HL, BC
+ { &opcode_ed_43, 20 }, // LD (nn), BC
+ { &opcode_ed_44, 8 }, // NEG
+ { &opcode_ed_45, 14 }, // RETN
+ { &opcode_ed_46, 8 }, // IM 0
+ { &opcode_ed_47, 9 }, // LD I, A
+ { &opcode_ed_48, 12 }, // IN C, (C)
+ { &opcode_ed_49, 12 }, // OUT (C), C
+ { &opcode_ed_4a, 15 }, // ADC HL, BC
+ { &opcode_ed_4b, 20 }, // LD BC, (nn)
+ { &opcode_ed_4c, 8 }, // NEG
+ { &opcode_ed_4d, 14 }, // RETI
+ { &opcode_ed_4e, 8 }, // IM 0/1
+ { &opcode_ed_4f, 9 }, // LD R, A
+ { &opcode_ed_50, 12 }, // IN D, (C)
+ { &opcode_ed_51, 12 }, // OUT (C), D
+ { &opcode_ed_52, 15 }, // SBC HL, DE
+ { &opcode_ed_53, 20 }, // LD (nn), DE
+ { &opcode_ed_54, 8 }, // NEG
+ { &opcode_ed_55, 14 }, // RETN
+ { &opcode_ed_56, 8 }, // IM 1
+ { &opcode_ed_57, 9 }, // LD A, I
+ { &opcode_ed_58, 12 }, // IN E, (C)
+ { &opcode_ed_59, 12 }, // OUT (C), E
+ { &opcode_ed_5a, 15 }, // ADC HL, DE
+ { &opcode_ed_5b, 20 }, // LD DE, (nn)
+ { &opcode_ed_5c, 8 }, // NEG
+ { &opcode_ed_5d, 14 }, // RETN
+ { &opcode_ed_5e, 8 }, // IM 2
+ { &opcode_ed_5f, 9 }, // LD A, R
+ { &opcode_ed_60, 12 }, // IN H, (C)
+ { &opcode_ed_61, 12 }, // OUT (C), H
+ { &opcode_ed_62, 15 }, // SBC HL, HL
+ { &opcode_ed_63, 20 }, // LD (nn), HL
+ { &opcode_ed_64, 8 }, // NEG
+ { &opcode_ed_65, 14 }, // RETN
+ { &opcode_ed_66, 8 }, // IM 0
+ { &opcode_ed_67, 18 }, // RRD
+ { &opcode_ed_68, 12 }, // IN L, (C)
+ { &opcode_ed_69, 12 }, // OUT (C), L
+ { &opcode_ed_6a, 15 }, // ADC HL, HL
+ { &opcode_ed_6b, 20 }, // LD HL, (nn)
+ { &opcode_ed_6c, 8 }, // NEG
+ { &opcode_ed_6d, 14 }, // RETN
+ { &opcode_ed_6e, 8 }, // IM 0/1
+ { &opcode_ed_6f, 18 }, // RLD
+ { &opcode_ed_70, 12 }, // IN (C) / IN F, (C)
+ { &opcode_ed_71, 12 }, // OUT (C), 0
+ { &opcode_ed_72, 15 }, // SBC HL, SP
+ { &opcode_ed_73, 20 }, // LD (nn), SP
+ { &opcode_ed_74, 8 }, // NEG
+ { &opcode_ed_75, 14 }, // RETN
+ { &opcode_ed_76, 8 }, // IM 1
+ { 0, 0 }, // 0x77
+ { &opcode_ed_78, 12 }, // IN A, (C)
+ { &opcode_ed_79, 12 }, // OUT (C), A
+ { &opcode_ed_7a, 15 }, // ADC HL, SP
+ { &opcode_ed_7b, 20 }, // LD SP, (nn)
+ { &opcode_ed_7c, 8 }, // NEG
+ { &opcode_ed_7d, 14 }, // RETN
+ { &opcode_ed_7e, 8 }, // IM 2
+ { 0, 0 }, // 0x7F
+ { 0, 0 }, // 0x80
+ { 0, 0 }, // 0x81
+ { 0, 0 }, // 0x82
+ { 0, 0 }, // 0x83
+ { 0, 0 }, // 0x84
+ { 0, 0 }, // 0x85
+ { 0, 0 }, // 0x86
+ { 0, 0 }, // 0x87
+ { 0, 0 }, // 0x88
+ { 0, 0 }, // 0x89
+ { 0, 0 }, // 0x8A
+ { 0, 0 }, // 0x8B
+ { 0, 0 }, // 0x8C
+ { 0, 0 }, // 0x8D
+ { 0, 0 }, // 0x8E
+ { 0, 0 }, // 0x8F
+ { 0, 0 }, // 0x90
+ { 0, 0 }, // 0x91
+ { 0, 0 }, // 0x92
+ { 0, 0 }, // 0x93
+ { 0, 0 }, // 0x94
+ { 0, 0 }, // 0x95
+ { 0, 0 }, // 0x96
+ { 0, 0 }, // 0x97
+ { 0, 0 }, // 0x98
+ { 0, 0 }, // 0x99
+ { 0, 0 }, // 0x9A
+ { 0, 0 }, // 0x9B
+ { 0, 0 }, // 0x9C
+ { 0, 0 }, // 0x9D
+ { 0, 0 }, // 0x9E
+ { 0, 0 }, // 0x9F
+ { &opcode_ed_a0, 16 }, // LDI
+ { &opcode_ed_a1, 16 }, // CPI
+ { &opcode_ed_a2, 16 }, // INI
+ { &opcode_ed_a3, 16 }, // OUTI
+ { 0, 0 }, // 0xA4
+ { 0, 0 }, // 0xA5
+ { 0, 0 }, // 0xA6
+ { 0, 0 }, // 0xA7
+ { &opcode_ed_a8, 16 }, // LDD
+ { &opcode_ed_a9, 16 }, // CPD
+ { &opcode_ed_aa, 16 }, // IND
+ { &opcode_ed_ab, 16 }, // OUTD
+ { 0, 0 }, // 0xAC
+ { 0, 0 }, // 0xAD
+ { 0, 0 }, // 0xAE
+ { 0, 0 }, // 0xAF
+ { &opcode_ed_b0, 0 }, // LDIR
+ { &opcode_ed_b1, 0 }, // CPIR
+ { &opcode_ed_b2, 0 }, // INIR
+ { &opcode_ed_b3, 0 }, // OTIR
+ { 0, 0 }, // 0xB4
+ { 0, 0 }, // 0xB5
+ { 0, 0 }, // 0xB6
+ { 0, 0 }, // 0xB7
+ { &opcode_ed_b8, 0 }, // LDDR
+ { &opcode_ed_b9, 0 }, // CPDR
+ { &opcode_ed_ba, 0 }, // INDR
+ { &opcode_ed_bb, 0 }, // OTDR
+ { 0, 0 }, // 0xBC
+ { 0, 0 }, // 0xBD
+ { 0, 0 }, // 0xBE
+ { 0, 0 }, // 0xBF
+ { 0, 0 }, // 0xC0
+ { 0, 0 }, // 0xC1
+ { 0, 0 }, // 0xC2
+ { 0, 0 }, // 0xC3
+ { 0, 0 }, // 0xC4
+ { 0, 0 }, // 0xC5
+ { 0, 0 }, // 0xC6
+ { 0, 0 }, // 0xC7
+ { 0, 0 }, // 0xC8
+ { 0, 0 }, // 0xC9
+ { 0, 0 }, // 0xCA
+ { 0, 0 }, // 0xCB
+ { 0, 0 }, // 0xCC
+ { 0, 0 }, // 0xCD
+ { 0, 0 }, // 0xCE
+ { 0, 0 }, // 0xCF
+ { 0, 0 }, // 0xD0
+ { 0, 0 }, // 0xD1
+ { 0, 0 }, // 0xD2
+ { 0, 0 }, // 0xD3
+ { 0, 0 }, // 0xD4
+ { 0, 0 }, // 0xD5
+ { 0, 0 }, // 0xD6
+ { 0, 0 }, // 0xD7
+ { 0, 0 }, // 0xD8
+ { 0, 0 }, // 0xD9
+ { 0, 0 }, // 0xDA
+ { 0, 0 }, // 0xDB
+ { 0, 0 }, // 0xDC
+ { 0, 0 }, // 0xDD
+ { 0, 0 }, // 0xDE
+ { 0, 0 }, // 0xDF
+ { 0, 0 }, // 0xE0
+ { 0, 0 }, // 0xE1
+ { 0, 0 }, // 0xE2
+ { 0, 0 }, // 0xE3
+ { 0, 0 }, // 0xE4
+ { 0, 0 }, // 0xE5
+ { 0, 0 }, // 0xE6
+ { 0, 0 }, // 0xE7
+ { 0, 0 }, // 0xE8
+ { 0, 0 }, // 0xE9
+ { 0, 0 }, // 0xEA
+ { 0, 0 }, // 0xEB
+ { 0, 0 }, // 0xEC
+ { 0, 0 }, // 0xED
+ { 0, 0 }, // 0xEE
+ { 0, 0 }, // 0xEF
+ { 0, 0 }, // 0xF0
+ { 0, 0 }, // 0xF1
+ { 0, 0 }, // 0xF2
+ { 0, 0 }, // 0xF3
+ { 0, 0 }, // 0xF4
+ { 0, 0 }, // 0xF5
+ { 0, 0 }, // 0xF6
+ { 0, 0 }, // 0xF7
+ { 0, 0 }, // 0xF8
+ { 0, 0 }, // 0xF9
+ { 0, 0 }, // 0xFA
+ { 0, 0 }, // 0xFB
+ { 0, 0 }, // 0xFC
+ { 0, 0 }, // 0xFD
+ { 0, 0 }, // 0xFE
+ { 0, 0 } // 0xFF
+};
+
+void opcode_ed_40() // IN B, (C)
+{
+ B = inpReg();
+}
+
+void opcode_ed_41() // OUT (C), B
+{
+ writePort( C, B );
+}
+
+void opcode_ed_42() // SBC HL, BC
+{
+ unsigned char a;
+
+ a = A;
+ A = L; L = subByte( C, F & Carry );
+ A = H; H = subByte( B, F & Carry );
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_43() // LD (nn), BC
+{
+ unsigned addr = fetchWord();
+
+ writeByte( addr, C );
+ writeByte( addr+1, B );
+}
+
+void opcode_ed_44() // NEG
+{
+ unsigned char a = A;
+
+ A = 0;
+ A = subByte( a, 0 );
+}
+
+void opcode_ed_45() // RETN
+{
+ retFromSub();
+ iflags_ &= ~IFF1;
+ if( iflags_ & IFF2 ) iflags_ |= IFF1;
+}
+
+void opcode_ed_46() // IM 0
+{
+ setInterruptMode( 0 );
+}
+
+void opcode_ed_47() // LD I, A
+{
+ I = A;
+}
+
+void opcode_ed_48() // IN C, (C)
+{
+ C = inpReg();
+}
+
+void opcode_ed_49() // OUT (C), C
+{
+ writePort( C, C );
+}
+
+void opcode_ed_4a() // ADC HL, BC
+{
+ unsigned char a;
+
+ a = A;
+ A = L; addByte( C, F & Carry ); L = A;
+ A = H; addByte( B, F & Carry ); H = A;
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_4b() // LD BC, (nn)
+{
+ unsigned addr = fetchWord();
+
+ C = readByte( addr );
+ B = readByte( addr+1 );
+}
+
+void opcode_ed_4c() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_4d() // RETI
+{
+ retFromSub();
+ //onReturnFromInterrupt();
+}
+
+void opcode_ed_4e() // IM 0/1
+{
+ setInterruptMode( 0 );
+}
+
+void opcode_ed_4f() // LD R, A
+{
+ R = A;
+}
+
+void opcode_ed_50() // IN D, (C)
+{
+ D = inpReg();
+}
+
+void opcode_ed_51() // OUT (C), D
+{
+ writePort( C, D );
+}
+
+void opcode_ed_52() // SBC HL, DE
+{
+ unsigned char a;
+
+ a = A;
+ A = L; L = subByte( E, F & Carry );
+ A = H; H = subByte( D, F & Carry );
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_53() // LD (nn), DE
+{
+ unsigned addr = fetchWord();
+
+ writeByte( addr, E );
+ writeByte( addr+1, D );
+}
+
+void opcode_ed_54() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_55() // RETN
+{
+ opcode_ed_45();
+}
+
+void opcode_ed_56() // IM 1
+{
+ setInterruptMode( 1 );
+}
+
+void opcode_ed_57() // LD A, I
+{
+ A = I;
+ setFlags35PSZ();
+ F &= ~(Halfcarry | Parity | AddSub);
+ if( iflags_ & IFF2 ) F |= Parity;
+}
+
+void opcode_ed_58() // IN E, (C)
+{
+ E = inpReg();
+}
+
+void opcode_ed_59() // OUT (C), E
+{
+ writePort( C, E );
+}
+
+void opcode_ed_5a() // ADC HL, DE
+{
+ unsigned char a;
+
+ a = A;
+ A = L; addByte( E, F & Carry ); L = A;
+ A = H; addByte( D, F & Carry ); H = A;
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_5b() // LD DE, (nn)
+{
+ unsigned addr = fetchWord();
+
+ E = readByte( addr );
+ D = readByte( addr+1 );
+}
+
+void opcode_ed_5c() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_5d() // RETN
+{
+ opcode_ed_45();
+}
+
+void opcode_ed_5e() // IM 2
+{
+ setInterruptMode( 2 );
+}
+
+void opcode_ed_5f() // LD A, R
+{
+ A = R;
+ setFlags35PSZ();
+ F &= ~(Halfcarry | Parity | AddSub);
+ if( iflags_ & IFF2 ) F |= Parity;
+}
+
+void opcode_ed_60() // IN H, (C)
+{
+ H = inpReg();
+}
+
+void opcode_ed_61() // OUT (C), H
+{
+ writePort( C, H );
+}
+
+void opcode_ed_62() // SBC HL, HL
+{
+ unsigned char a;
+
+ a = A;
+ A = L; L = subByte( L, F & Carry );
+ A = H; H = subByte( H, F & Carry );
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_63() // LD (nn), HL
+{
+ unsigned addr = fetchWord();
+
+ writeByte( addr, L );
+ writeByte( addr+1, H );
+}
+
+void opcode_ed_64() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_65() // RETN
+{
+ opcode_ed_45();
+}
+
+void opcode_ed_66() // IM 0
+{
+ setInterruptMode( 0 );
+}
+
+void opcode_ed_67() // RRD
+{
+ unsigned char x = readByte( HL() );
+
+ writeByte( HL(), (A << 4) | (x >> 4) );
+ A = (A & 0xF0) | (x & 0x0F);
+ setFlags35PSZ();
+ F &= ~(Halfcarry | AddSub);
+}
+
+void opcode_ed_68() // IN L, (C)
+{
+ L = inpReg();
+}
+
+void opcode_ed_69() // OUT (C), L
+{
+ writePort( C, L );
+}
+
+void opcode_ed_6a() // ADC HL, HL
+{
+ unsigned char a;
+
+ a = A;
+ A = L; addByte( L, F & Carry ); L = A;
+ A = H; addByte( H, F & Carry ); H = A;
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_6b() // LD HL, (nn)
+{
+ unsigned addr = fetchWord();
+
+ L = readByte( addr );
+ H = readByte( addr+1 );
+}
+
+void opcode_ed_6c() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_6d() // RETN
+{
+ opcode_ed_45();
+}
+
+void opcode_ed_6e() // IM 0/1
+{
+ setInterruptMode( 0 );
+}
+
+void opcode_ed_6f() // RLD
+{
+ unsigned char x = readByte( HL() );
+
+ writeByte( HL(), (x << 4) | (A & 0x0F) );
+ A = (A & 0xF0) | (x >> 4);
+ setFlags35PSZ();
+ F &= ~(Halfcarry | AddSub);
+}
+
+void opcode_ed_70() // IN (C) / IN F, (C)
+{
+ inpReg();
+}
+
+void opcode_ed_71() // OUT (C), 0
+{
+ writePort( C, 0 );
+}
+
+void opcode_ed_72() // SBC HL, SP
+{
+ unsigned char a;
+
+ a = A;
+ A = L; L = subByte( SP & 0xFF, F & Carry );
+ A = H; H = subByte( (SP >> 8) & 0xFF, F & Carry );
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_73() // LD (nn), SP
+{
+ writeWord( fetchWord(), SP );
+}
+
+void opcode_ed_74() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_75() // RETN
+{
+ opcode_ed_45();
+}
+
+void opcode_ed_76() // IM 1
+{
+ setInterruptMode( 1 );
+}
+
+void opcode_ed_78() // IN A, (C)
+{
+ A = inpReg();
+}
+
+void opcode_ed_79() // OUT (C), A
+{
+ writePort( C, A );
+}
+
+void opcode_ed_7a() // ADC HL, SP
+{
+ unsigned char a;
+
+ a = A;
+ A = L; addByte( SP & 0xFF, F & Carry ); L = A;
+ A = H; addByte( (SP >> 8) & 0xFF, F & Carry ); H = A;
+ A = a;
+ if( HL() == 0 ) F |= Zero; else F &= ~Zero;
+}
+
+void opcode_ed_7b() // LD SP, (nn)
+{
+ SP = readWord( fetchWord() );
+}
+
+void opcode_ed_7c() // NEG
+{
+ opcode_ed_44();
+}
+
+void opcode_ed_7d() // RETN
+{
+ opcode_ed_45();
+}
+
+void opcode_ed_7e() // IM 2
+{
+ setInterruptMode( 2 );
+}
+
+void opcode_ed_a0() // LDI
+{
+ writeByte( DE(), readByte( HL() ) );
+ if( ++L == 0 ) ++H; // HL++
+ if( ++E == 0 ) ++D; // DE++
+ if( C-- == 0 ) --B; // BC--
+ F &= ~(Halfcarry | Subtraction | Parity);
+ if( BC() ) F |= Parity;
+}
+
+void opcode_ed_a1() // CPI
+{
+ unsigned char f = F;
+
+ cmpByte( readByte( HL() ) );
+ if( ++L == 0 ) ++H; // HL++
+ if( C-- == 0 ) --B; // BC--
+ F = (F & ~(Carry | Parity)) | (f & Carry);
+ if( BC() ) F |= Parity;
+}
+
+void opcode_ed_a2() // INI
+{
+ writeByte( HL(), readPort( C ) );
+ if( ++L == 0 ) ++H; // HL++
+ B = decByte( B );
+}
+
+void opcode_ed_a3() // OUTI
+{
+ writePort( C, readByte( HL() ) );
+ if( ++L == 0 ) ++H; // HL++
+ B = decByte( B );
+}
+
+void opcode_ed_a8() // LDD
+{
+ writeByte( DE(), readByte( HL() ) );
+ if( L-- == 0 ) --H; // HL--
+ if( E-- == 0 ) --D; // DE--
+ if( C-- == 0 ) --B; // BC--
+ F &= ~(Halfcarry | Subtraction | Parity);
+ if( BC() ) F |= Parity;
+}
+
+void opcode_ed_a9() // CPD
+{
+ unsigned char f = F;
+
+ cmpByte( readByte( HL() ) );
+ if( L-- == 0 ) --H; // HL--
+ if( C-- == 0 ) --B; // BC--
+ F = (F & ~(Carry | Parity)) | (f & Carry);
+ if( BC() ) F |= Parity;
+}
+
+void opcode_ed_aa() // IND
+{
+ writeByte( HL(), readPort( C ) );
+ if( L-- == 0 ) --H; // HL--
+ B = decByte( B );
+}
+
+void opcode_ed_ab() // OUTD
+{
+ writePort( C, readByte( HL() ) );
+ if( L-- == 0 ) --H; // HL--
+ B = decByte( B );
+}
+
+void opcode_ed_b0() // LDIR
+{
+ opcode_ed_a0(); // LDI
+ if( F & Parity ) { // After LDI, the Parity flag will be zero when BC=0
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_b1() // CPIR
+{
+ opcode_ed_a1(); // CPI
+ if( (F & Parity) && !(F & Zero) ) { // Parity clear when BC=0, Zero set when A=(HL)
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_b2() // INIR
+{
+ opcode_ed_a2(); // INI
+ if( B != 0 ) {
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_b3() // OTIR
+{
+ opcode_ed_a3(); // OUTI
+ if( B != 0 ) {
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_b8() // LDDR
+{
+ opcode_ed_a8(); // LDD
+ if( F & Parity ) { // After LDD, the Parity flag will be zero when BC=0
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_b9() // CPDR
+{
+ opcode_ed_a9(); // CPD
+ if( (F & Parity) && !(F & Zero) ) { // Parity clear when BC=0, Zero set when A=(HL)
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_ba() // INDR
+{
+ opcode_ed_aa(); // IND
+ if( B != 0 ) {
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+void opcode_ed_bb() // OTDR
+{
+ opcode_ed_ab(); // OUTD
+ if( B != 0 ) {
+ cycles_ += 5;
+ PC -= 2; // Decrement PC so that instruction is re-executed at next step (this allows interrupts to occur)
+ }
+}
+
+OpcodeInfo OpInfoFD_[256] = {
+ { 0, 0 }, // 0x00
+ { 0, 0 }, // 0x01
+ { 0, 0 }, // 0x02
+ { 0, 0 }, // 0x03
+ { 0, 0 }, // 0x04
+ { 0, 0 }, // 0x05
+ { 0, 0 }, // 0x06
+ { 0, 0 }, // 0x07
+ { 0, 0 }, // 0x08
+ { &opcode_fd_09, 15 }, // ADD IY, BC
+ { 0, 0 }, // 0x0A
+ { 0, 0 }, // 0x0B
+ { 0, 0 }, // 0x0C
+ { 0, 0 }, // 0x0D
+ { 0, 0 }, // 0x0E
+ { 0, 0 }, // 0x0F
+ { 0, 0 }, // 0x10
+ { 0, 0 }, // 0x11
+ { 0, 0 }, // 0x12
+ { 0, 0 }, // 0x13
+ { 0, 0 }, // 0x14
+ { 0, 0 }, // 0x15
+ { 0, 0 }, // 0x16
+ { 0, 0 }, // 0x17
+ { 0, 0 }, // 0x18
+ { &opcode_fd_19, 15 }, // ADD IY, DE
+ { 0, 0 }, // 0x1A
+ { 0, 0 }, // 0x1B
+ { 0, 0 }, // 0x1C
+ { 0, 0 }, // 0x1D
+ { 0, 0 }, // 0x1E
+ { 0, 0 }, // 0x1F
+ { 0, 0 }, // 0x20
+ { &opcode_fd_21, 14 }, // LD IY, nn
+ { &opcode_fd_22, 20 }, // LD (nn), IY
+ { &opcode_fd_23, 10 }, // INC IY
+ { &opcode_fd_24, 9 }, // INC IYH
+ { &opcode_fd_25, 9 }, // DEC IYH
+ { &opcode_fd_26, 9 }, // LD IYH, n
+ { 0, 0 }, // 0x27
+ { 0, 0 }, // 0x28
+ { &opcode_fd_29, 15 }, // ADD IY, IY
+ { &opcode_fd_2a, 20 }, // LD IY, (nn)
+ { &opcode_fd_2b, 10 }, // DEC IY
+ { &opcode_fd_2c, 9 }, // INC IYL
+ { &opcode_fd_2d, 9 }, // DEC IYL
+ { &opcode_fd_2e, 9 }, // LD IYL, n
+ { 0, 0 }, // 0x2F
+ { 0, 0 }, // 0x30
+ { 0, 0 }, // 0x31
+ { 0, 0 }, // 0x32
+ { 0, 0 }, // 0x33
+ { &opcode_fd_34, 23 }, // INC (IY + d)
+ { &opcode_fd_35, 23 }, // DEC (IY + d)
+ { &opcode_fd_36, 19 }, // LD (IY + d), n
+ { 0, 0 }, // 0x37
+ { 0, 0 }, // 0x38
+ { &opcode_fd_39, 15 }, // ADD IY, SP
+ { 0, 0 }, // 0x3A
+ { 0, 0 }, // 0x3B
+ { 0, 0 }, // 0x3C
+ { 0, 0 }, // 0x3D
+ { 0, 0 }, // 0x3E
+ { 0, 0 }, // 0x3F
+ { 0, 0 }, // 0x40
+ { 0, 0 }, // 0x41
+ { 0, 0 }, // 0x42
+ { 0, 0 }, // 0x43
+ { &opcode_fd_44, 9 }, // LD B, IYH
+ { &opcode_fd_45, 9 }, // LD B, IYL
+ { &opcode_fd_46, 19 }, // LD B, (IY + d)
+ { 0, 0 }, // 0x47
+ { 0, 0 }, // 0x48
+ { 0, 0 }, // 0x49
+ { 0, 0 }, // 0x4A
+ { 0, 0 }, // 0x4B
+ { &opcode_fd_4c, 9 }, // LD C, IYH
+ { &opcode_fd_4d, 9 }, // LD C, IYL
+ { &opcode_fd_4e, 19 }, // LD C, (IY + d)
+ { 0, 0 }, // 0x4F
+ { 0, 0 }, // 0x50
+ { 0, 0 }, // 0x51
+ { 0, 0 }, // 0x52
+ { 0, 0 }, // 0x53
+ { &opcode_fd_54, 9 }, // LD D, IYH
+ { &opcode_fd_55, 9 }, // LD D, IYL
+ { &opcode_fd_56, 19 }, // LD D, (IY + d)
+ { 0, 0 }, // 0x57
+ { 0, 0 }, // 0x58
+ { 0, 0 }, // 0x59
+ { 0, 0 }, // 0x5A
+ { 0, 0 }, // 0x5B
+ { &opcode_fd_5c, 9 }, // LD E, IYH
+ { &opcode_fd_5d, 9 }, // LD E, IYL
+ { &opcode_fd_5e, 19 }, // LD E, (IY + d)
+ { 0, 0 }, // 0x5F
+ { &opcode_fd_60, 9 }, // LD IYH, B
+ { &opcode_fd_61, 9 }, // LD IYH, C
+ { &opcode_fd_62, 9 }, // LD IYH, D
+ { &opcode_fd_63, 9 }, // LD IYH, E
+ { &opcode_fd_64, 9 }, // LD IYH, IYH
+ { &opcode_fd_65, 9 }, // LD IYH, IYL
+ { &opcode_fd_66, 9 }, // LD H, (IY + d)
+ { &opcode_fd_67, 9 }, // LD IYH, A
+ { &opcode_fd_68, 9 }, // LD IYL, B
+ { &opcode_fd_69, 9 }, // LD IYL, C
+ { &opcode_fd_6a, 9 }, // LD IYL, D
+ { &opcode_fd_6b, 9 }, // LD IYL, E
+ { &opcode_fd_6c, 9 }, // LD IYL, IYH
+ { &opcode_fd_6d, 9 }, // LD IYL, IYL
+ { &opcode_fd_6e, 9 }, // LD L, (IY + d)
+ { &opcode_fd_6f, 9 }, // LD IYL, A
+ { &opcode_fd_70, 19 }, // LD (IY + d), B
+ { &opcode_fd_71, 19 }, // LD (IY + d), C
+ { &opcode_fd_72, 19 }, // LD (IY + d), D
+ { &opcode_fd_73, 19 }, // LD (IY + d), E
+ { &opcode_fd_74, 19 }, // LD (IY + d), H
+ { &opcode_fd_75, 19 }, // LD (IY + d), L
+ { 0,19 }, // 0x76
+ { &opcode_fd_77, 19 }, // LD (IY + d), A
+ { 0, 0 }, // 0x78
+ { 0, 0 }, // 0x79
+ { 0, 0 }, // 0x7A
+ { 0, 0 }, // 0x7B
+ { &opcode_fd_7c, 9 }, // LD A, IYH
+ { &opcode_fd_7d, 9 }, // LD A, IYL
+ { &opcode_fd_7e, 19 }, // LD A, (IY + d)
+ { 0, 0 }, // 0x7F
+ { 0, 0 }, // 0x80
+ { 0, 0 }, // 0x81
+ { 0, 0 }, // 0x82
+ { 0, 0 }, // 0x83
+ { &opcode_fd_84, 9 }, // ADD A, IYH
+ { &opcode_fd_85, 9 }, // ADD A, IYL
+ { &opcode_fd_86, 19 }, // ADD A, (IY + d)
+ { 0, 0 }, // 0x87
+ { 0, 0 }, // 0x88
+ { 0, 0 }, // 0x89
+ { 0, 0 }, // 0x8A
+ { 0, 0 }, // 0x8B
+ { &opcode_fd_8c, 9 }, // ADC A, IYH
+ { &opcode_fd_8d, 9 }, // ADC A, IYL
+ { &opcode_fd_8e, 19 }, // ADC A, (IY + d)
+ { 0, 0 }, // 0x8F
+ { 0, 0 }, // 0x90
+ { 0, 0 }, // 0x91
+ { 0, 0 }, // 0x92
+ { 0, 0 }, // 0x93
+ { &opcode_fd_94, 9 }, // SUB IYH
+ { &opcode_fd_95, 9 }, // SUB IYL
+ { &opcode_fd_96, 19 }, // SUB (IY + d)
+ { 0, 0 }, // 0x97
+ { 0, 0 }, // 0x98
+ { 0, 0 }, // 0x99
+ { 0, 0 }, // 0x9A
+ { 0, 0 }, // 0x9B
+ { &opcode_fd_9c, 9 }, // SBC A, IYH
+ { &opcode_fd_9d, 9 }, // SBC A, IYL
+ { &opcode_fd_9e, 19 }, // SBC A, (IY + d)
+ { 0, 0 }, // 0x9F
+ { 0, 0 }, // 0xA0
+ { 0, 0 }, // 0xA1
+ { 0, 0 }, // 0xA2
+ { 0, 0 }, // 0xA3
+ { &opcode_fd_a4, 9 }, // AND IYH
+ { &opcode_fd_a5, 9 }, // AND IYL
+ { &opcode_fd_a6, 19 }, // AND (IY + d)
+ { 0, 0 }, // 0xA7
+ { 0, 0 }, // 0xA8
+ { 0, 0 }, // 0xA9
+ { 0, 0 }, // 0xAA
+ { 0, 0 }, // 0xAB
+ { &opcode_fd_ac, 9 }, // XOR IYH
+ { &opcode_fd_ad, 9 }, // XOR IYL
+ { &opcode_fd_ae, 19 }, // XOR (IY + d)
+ { 0, 0 }, // 0xAF
+ { 0, 0 }, // 0xB0
+ { 0, 0 }, // 0xB1
+ { 0, 0 }, // 0xB2
+ { 0, 0 }, // 0xB3
+ { &opcode_fd_b4, 9 }, // OR IYH
+ { &opcode_fd_b5, 9 }, // OR IYL
+ { &opcode_fd_b6, 19 }, // OR (IY + d)
+ { 0, 0 }, // 0xB7
+ { 0, 0 }, // 0xB8
+ { 0, 0 }, // 0xB9
+ { 0, 0 }, // 0xBA
+ { 0, 0 }, // 0xBB
+ { &opcode_fd_bc, 9 }, // CP IYH
+ { &opcode_fd_bd, 9 }, // CP IYL
+ { &opcode_fd_be, 19 }, // CP (IY + d)
+ { 0, 0 }, // 0xBF
+ { 0, 0 }, // 0xC0
+ { 0, 0 }, // 0xC1
+ { 0, 0 }, // 0xC2
+ { 0, 0 }, // 0xC3
+ { 0, 0 }, // 0xC4
+ { 0, 0 }, // 0xC5
+ { 0, 0 }, // 0xC6
+ { 0, 0 }, // 0xC7
+ { 0, 0 }, // 0xC8
+ { 0, 0 }, // 0xC9
+ { 0, 0 }, // 0xCA
+ { &opcode_fd_cb, 0 }, //
+ { 0, 0 }, // 0xCC
+ { 0, 0 }, // 0xCD
+ { 0, 0 }, // 0xCE
+ { 0, 0 }, // 0xCF
+ { 0, 0 }, // 0xD0
+ { 0, 0 }, // 0xD1
+ { 0, 0 }, // 0xD2
+ { 0, 0 }, // 0xD3
+ { 0, 0 }, // 0xD4
+ { 0, 0 }, // 0xD5
+ { 0, 0 }, // 0xD6
+ { 0, 0 }, // 0xD7
+ { 0, 0 }, // 0xD8
+ { 0, 0 }, // 0xD9
+ { 0, 0 }, // 0xDA
+ { 0, 0 }, // 0xDB
+ { 0, 0 }, // 0xDC
+ { 0, 0 }, // 0xDD
+ { 0, 0 }, // 0xDE
+ { 0, 0 }, // 0xDF
+ { 0, 0 }, // 0xE0
+ { &opcode_fd_e1, 14 }, // POP IY
+ { 0, 0 }, // 0xE2
+ { &opcode_fd_e3, 23 }, // EX (SP), IY
+ { 0, 0 }, // 0xE4
+ { &opcode_fd_e5, 15 }, // PUSH IY
+ { 0, 0 }, // 0xE6
+ { 0, 0 }, // 0xE7
+ { 0, 0 }, // 0xE8
+ { &opcode_fd_e9, 8 }, // JP (IY)
+ { 0, 0 }, // 0xEA
+ { 0, 0 }, // 0xEB
+ { 0, 0 }, // 0xEC
+ { 0, 0 }, // 0xED
+ { 0, 0 }, // 0xEE
+ { 0, 0 }, // 0xEF
+ { 0, 0 }, // 0xF0
+ { 0, 0 }, // 0xF1
+ { 0, 0 }, // 0xF2
+ { 0, 0 }, // 0xF3
+ { 0, 0 }, // 0xF4
+ { 0, 0 }, // 0xF5
+ { 0, 0 }, // 0xF6
+ { 0, 0 }, // 0xF7
+ { 0, 0 }, // 0xF8
+ { &opcode_fd_f9, 10 }, // LD SP, IY
+ { 0, 0 }, // 0xFA
+ { 0, 0 }, // 0xFB
+ { 0, 0 }, // 0xFC
+ { 0, 0 }, // 0xFD
+ { 0, 0 }, // 0xFE
+ { 0, 0 } // 0xFF
+};
+
+void opcode_fd_09() // ADD IY, BC
+{
+ unsigned rr = BC();
+
+ F &= (Zero | Sign | Parity);
+ if( ((IY & 0xFFF)+(rr & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+ IY += rr;
+ if( IY & 0x10000 ) F |= Carry;
+}
+
+void opcode_fd_19() // ADD IY, DE
+{
+ unsigned rr = DE();
+
+ F &= (Zero | Sign | Parity);
+ if( ((IY & 0xFFF)+(rr & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+ IY += rr;
+ if( IY & 0x10000 ) F |= Carry;
+}
+
+void opcode_fd_21() // LD IY, nn
+{
+ IY = fetchWord();
+}
+
+void opcode_fd_22() // LD (nn), IY
+{
+ writeWord( fetchWord(), IY );
+}
+
+void opcode_fd_23() // INC IY
+{
+ IY++;
+}
+
+void opcode_fd_24() // INC IYH
+{
+ IY = (IY & 0xFF) | ((unsigned)incByte( IY >> 8 ) << 8);
+}
+
+void opcode_fd_25() // DEC IYH
+{
+ IY = (IY & 0xFF) | ((unsigned)decByte( IY >> 8 ) << 8);
+}
+
+void opcode_fd_26() // LD IYH, n
+{
+ IY = (IY & 0xFF) | ((unsigned)fetchByte() << 8);
+}
+
+void opcode_fd_29() // ADD IY, IY
+{
+ F &= (Zero | Sign | Parity);
+ if( IY & 0x800 ) F |= Halfcarry;
+ IY += IY;
+ if( IY & 0x10000 ) F |= Carry;
+}
+
+void opcode_fd_2a() // LD IY, (nn)
+{
+ IY = readWord( fetchWord() );
+}
+
+void opcode_fd_2b() // DEC IY
+{
+ IY--;
+}
+
+void opcode_fd_2c() // INC IYL
+{
+ IY = (IY & 0xFF00) | incByte( IY & 0xFF );
+}
+
+void opcode_fd_2d() // DEC IYL
+{
+ IY = (IY & 0xFF00) | decByte( IY & 0xFF );
+}
+
+void opcode_fd_2e() // LD IYL, n
+{
+ IY = (IY & 0xFF00) | fetchByte();
+}
+
+void opcode_fd_34() // INC (IY + d)
+{
+ unsigned addr = addDispl( IY, fetchByte() );
+
+ writeByte( addr, incByte( readByte( addr ) ) );
+}
+
+void opcode_fd_35() // DEC (IY + d)
+{
+ unsigned addr = addDispl( IY, fetchByte() );
+
+ writeByte( addr, decByte( readByte( addr ) ) );
+}
+
+void opcode_fd_36() // LD (IY + d), n
+{
+ unsigned addr = addDispl( IY, fetchByte() );
+
+ writeByte( addr, fetchByte() );
+}
+
+void opcode_fd_39() // ADD IY, SP
+{
+ F &= (Zero | Sign | Parity);
+ if( ((IY & 0xFFF)+(SP & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+ IY += SP;
+ if( IY & 0x10000 ) F |= Carry;
+}
+
+void opcode_fd_44() // LD B, IYH
+{
+ B = IY >> 8;
+}
+
+void opcode_fd_45() // LD B, IYL
+{
+ B = IY & 0xFF;
+}
+
+void opcode_fd_46() // LD B, (IY + d)
+{
+ B = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_4c() // LD C, IYH
+{
+ C = IY >> 8;
+}
+
+void opcode_fd_4d() // LD C, IYL
+{
+ C = IY & 0xFF;
+}
+
+void opcode_fd_4e() // LD C, (IY + d)
+{
+ C = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_54() // LD D, IYH
+{
+ D = IY >> 8;
+}
+
+void opcode_fd_55() // LD D, IYL
+{
+ D = IY & 0xFF;
+}
+
+void opcode_fd_56() // LD D, (IY + d)
+{
+ D = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_5c() // LD E, IYH
+{
+ E = IY >> 8;
+}
+
+void opcode_fd_5d() // LD E, IYL
+{
+ E = IY & 0xFF;
+}
+
+void opcode_fd_5e() // LD E, (IY + d)
+{
+ E = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_60() // LD IYH, B
+{
+ IY = (IY & 0xFF) | ((unsigned)B << 8);
+}
+
+void opcode_fd_61() // LD IYH, C
+{
+ IY = (IY & 0xFF) | ((unsigned)C << 8);
+}
+
+void opcode_fd_62() // LD IYH, D
+{
+ IY = (IY & 0xFF) | ((unsigned)D << 8);
+}
+
+void opcode_fd_63() // LD IYH, E
+{
+ IY = (IY & 0xFF) | ((unsigned)E << 8);
+}
+
+void opcode_fd_64() // LD IYH, IYH
+{
+}
+
+void opcode_fd_65() // LD IYH, IYL
+{
+ IY = (IY & 0xFF) | ((IY << 8) & 0xFF00);
+}
+
+void opcode_fd_66() // LD H, (IY + d)
+{
+ H = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_67() // LD IYH, A
+{
+ IY = (IY & 0xFF) | ((unsigned)A << 8);
+}
+
+void opcode_fd_68() // LD IYL, B
+{
+ IY = (IY & 0xFF00) | B;
+}
+
+void opcode_fd_69() // LD IYL, C
+{
+ IY = (IY & 0xFF00) | C;
+}
+
+void opcode_fd_6a() // LD IYL, D
+{
+ IY = (IY & 0xFF00) | D;
+}
+
+void opcode_fd_6b() // LD IYL, E
+{
+ IY = (IY & 0xFF00) | E;
+}
+
+void opcode_fd_6c() // LD IYL, IYH
+{
+ IY = (IY & 0xFF00) | ((IY >> 8) & 0xFF);
+}
+
+void opcode_fd_6d() // LD IYL, IYL
+{
+}
+
+void opcode_fd_6e() // LD L, (IY + d)
+{
+ L = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_6f() // LD IYL, A
+{
+ IY = (IY & 0xFF00) | A;
+}
+
+void opcode_fd_70() // LD (IY + d), B
+{
+ writeByte( addDispl(IY,fetchByte()), B );
+}
+
+void opcode_fd_71() // LD (IY + d), C
+{
+ writeByte( addDispl(IY,fetchByte()), C );
+}
+
+void opcode_fd_72() // LD (IY + d), D
+{
+ writeByte( addDispl(IY,fetchByte()), D );
+}
+
+void opcode_fd_73() // LD (IY + d), E
+{
+ writeByte( addDispl(IY,fetchByte()), E );
+}
+
+void opcode_fd_74() // LD (IY + d), H
+{
+ writeByte( addDispl(IY,fetchByte()), H );
+}
+
+void opcode_fd_75() // LD (IY + d), L
+{
+ writeByte( addDispl(IY,fetchByte()), L );
+}
+
+void opcode_fd_77() // LD (IY + d), A
+{
+ writeByte( addDispl(IY,fetchByte()), A );
+}
+
+void opcode_fd_7c() // LD A, IYH
+{
+ A = IY >> 8;
+}
+
+void opcode_fd_7d() // LD A, IYL
+{
+ A = IY & 0xFF;
+}
+
+void opcode_fd_7e() // LD A, (IY + d)
+{
+ A = readByte( addDispl(IY,fetchByte()) );
+}
+
+void opcode_fd_84() // ADD A, IYH
+{
+ addByte( IY >> 8, 0 );
+}
+
+void opcode_fd_85() // ADD A, IYL
+{
+ addByte( IY & 0xFF, 0 );
+}
+
+void opcode_fd_86() // ADD A, (IY + d)
+{
+ addByte( readByte( addDispl(IY,fetchByte()) ), 0 );
+}
+
+void opcode_fd_8c() // ADC A, IYH
+{
+ addByte( IY >> 8, F & Carry );
+}
+
+void opcode_fd_8d() // ADC A, IYL
+{
+ addByte( IY & 0xFF, F & Carry );
+}
+
+void opcode_fd_8e() // ADC A, (IY + d)
+{
+ addByte( readByte( addDispl(IY,fetchByte()) ), F & Carry );
+}
+
+void opcode_fd_94() // SUB IYH
+{
+ A = subByte( IY >> 8, 0 );
+}
+
+void opcode_fd_95() // SUB IYL
+{
+ A = subByte( IY & 0xFF, 0 );
+}
+
+void opcode_fd_96() // SUB (IY + d)
+{
+ A = subByte( readByte( addDispl(IY,fetchByte()) ), 0 );
+}
+
+void opcode_fd_9c() // SBC A, IYH
+{
+ A = subByte( IY >> 8, F & Carry );
+}
+
+void opcode_fd_9d() // SBC A, IYL
+{
+ A = subByte( IY & 0xFF, F & Carry );
+}
+
+void opcode_fd_9e() // SBC A, (IY + d)
+{
+ A = subByte( readByte( addDispl(IY,fetchByte()) ), F & Carry );
+}
+
+void opcode_fd_a4() // AND IYH
+{
+ A &= IY >> 8;
+ setFlags35PSZ000();
+ F |= Halfcarry;
+}
+
+void opcode_fd_a5() // AND IYL
+{
+ A &= IY & 0xFF;
+ setFlags35PSZ000();
+ F |= Halfcarry;
+}
+
+void opcode_fd_a6() // AND (IY + d)
+{
+ A &= readByte( addDispl(IY,fetchByte()) );
+ setFlags35PSZ000();
+ F |= Halfcarry;
+}
+
+void opcode_fd_ac() // XOR IYH
+{
+ A ^= IY >> 8;
+ setFlags35PSZ000();
+}
+
+void opcode_fd_ad() // XOR IYL
+{
+ A ^= IY & 0xFF;
+ setFlags35PSZ000();
+}
+
+void opcode_fd_ae() // XOR (IY + d)
+{
+ A ^= readByte( addDispl(IY,fetchByte()) );
+ setFlags35PSZ000();
+}
+
+void opcode_fd_b4() // OR IYH
+{
+ A |= IY >> 8;
+ setFlags35PSZ000();
+}
+
+void opcode_fd_b5() // OR IYL
+{
+ A |= IY & 0xFF;
+ setFlags35PSZ000();
+}
+
+void opcode_fd_b6() // OR (IY + d)
+{
+ A |= readByte( addDispl(IY,fetchByte()) );
+ setFlags35PSZ000();
+}
+
+void opcode_fd_bc() // CP IYH
+{
+ cmpByte( IY >> 8 );
+}
+
+void opcode_fd_bd() // CP IYL
+{
+ cmpByte( IY & 0xFF );
+}
+
+void opcode_fd_be() // CP (IY + d)
+{
+ cmpByte( readByte( addDispl(IY,fetchByte()) ) );
+}
+
+void opcode_fd_cb() //
+{
+ do_opcode_xycb( IY );
+}
+
+void opcode_fd_e1() // POP IY
+{
+ IY = readWord( SP );
+ SP += 2;
+}
+
+void opcode_fd_e3() // EX (SP), IY
+{
+ unsigned iy = IY;
+
+ IY = readWord( SP );
+ writeWord( SP, iy );
+}
+
+void opcode_fd_e5() // PUSH IY
+{
+ SP -= 2;
+ writeWord( SP, IY );
+}
+
+void opcode_fd_e9() // JP (IY)
+{
+ PC = IY;
+}
+
+void opcode_fd_f9() // LD SP, IY
+{
+ SP = IY;
+}
+
+OpcodeInfoXY OpInfoXYCB_[256] = {
+ { &opcode_xycb_00, 20 }, // LD B, RLC (IX + d)
+ { &opcode_xycb_01, 20 }, // LD C, RLC (IX + d)
+ { &opcode_xycb_02, 20 }, // LD D, RLC (IX + d)
+ { &opcode_xycb_03, 20 }, // LD E, RLC (IX + d)
+ { &opcode_xycb_04, 20 }, // LD H, RLC (IX + d)
+ { &opcode_xycb_05, 20 }, // LD L, RLC (IX + d)
+ { &opcode_xycb_06, 20 }, // RLC (IX + d)
+ { &opcode_xycb_07, 20 }, // LD A, RLC (IX + d)
+ { &opcode_xycb_08, 20 }, // LD B, RRC (IX + d)
+ { &opcode_xycb_09, 20 }, // LD C, RRC (IX + d)
+ { &opcode_xycb_0a, 20 }, // LD D, RRC (IX + d)
+ { &opcode_xycb_0b, 20 }, // LD E, RRC (IX + d)
+ { &opcode_xycb_0c, 20 }, // LD H, RRC (IX + d)
+ { &opcode_xycb_0d, 20 }, // LD L, RRC (IX + d)
+ { &opcode_xycb_0e, 20 }, // RRC (IX + d)
+ { &opcode_xycb_0f, 20 }, // LD A, RRC (IX + d)
+ { &opcode_xycb_10, 20 }, // LD B, RL (IX + d)
+ { &opcode_xycb_11, 20 }, // LD C, RL (IX + d)
+ { &opcode_xycb_12, 20 }, // LD D, RL (IX + d)
+ { &opcode_xycb_13, 20 }, // LD E, RL (IX + d)
+ { &opcode_xycb_14, 20 }, // LD H, RL (IX + d)
+ { &opcode_xycb_15, 20 }, // LD L, RL (IX + d)
+ { &opcode_xycb_16, 20 }, // RL (IX + d)
+ { &opcode_xycb_17, 20 }, // LD A, RL (IX + d)
+ { &opcode_xycb_18, 20 }, // LD B, RR (IX + d)
+ { &opcode_xycb_19, 20 }, // LD C, RR (IX + d)
+ { &opcode_xycb_1a, 20 }, // LD D, RR (IX + d)
+ { &opcode_xycb_1b, 20 }, // LD E, RR (IX + d)
+ { &opcode_xycb_1c, 20 }, // LD H, RR (IX + d)
+ { &opcode_xycb_1d, 20 }, // LD L, RR (IX + d)
+ { &opcode_xycb_1e, 20 }, // RR (IX + d)
+ { &opcode_xycb_1f, 20 }, // LD A, RR (IX + d)
+ { &opcode_xycb_20, 20 }, // LD B, SLA (IX + d)
+ { &opcode_xycb_21, 20 }, // LD C, SLA (IX + d)
+ { &opcode_xycb_22, 20 }, // LD D, SLA (IX + d)
+ { &opcode_xycb_23, 20 }, // LD E, SLA (IX + d)
+ { &opcode_xycb_24, 20 }, // LD H, SLA (IX + d)
+ { &opcode_xycb_25, 20 }, // LD L, SLA (IX + d)
+ { &opcode_xycb_26, 20 }, // SLA (IX + d)
+ { &opcode_xycb_27, 20 }, // LD A, SLA (IX + d)
+ { &opcode_xycb_28, 20 }, // LD B, SRA (IX + d)
+ { &opcode_xycb_29, 20 }, // LD C, SRA (IX + d)
+ { &opcode_xycb_2a, 20 }, // LD D, SRA (IX + d)
+ { &opcode_xycb_2b, 20 }, // LD E, SRA (IX + d)
+ { &opcode_xycb_2c, 20 }, // LD H, SRA (IX + d)
+ { &opcode_xycb_2d, 20 }, // LD L, SRA (IX + d)
+ { &opcode_xycb_2e, 20 }, // SRA (IX + d)
+ { &opcode_xycb_2f, 20 }, // LD A, SRA (IX + d)
+ { &opcode_xycb_30, 20 }, // LD B, SLL (IX + d)
+ { &opcode_xycb_31, 20 }, // LD C, SLL (IX + d)
+ { &opcode_xycb_32, 20 }, // LD D, SLL (IX + d)
+ { &opcode_xycb_33, 20 }, // LD E, SLL (IX + d)
+ { &opcode_xycb_34, 20 }, // LD H, SLL (IX + d)
+ { &opcode_xycb_35, 20 }, // LD L, SLL (IX + d)
+ { &opcode_xycb_36, 20 }, // SLL (IX + d)
+ { &opcode_xycb_37, 20 }, // LD A, SLL (IX + d)
+ { &opcode_xycb_38, 20 }, // LD B, SRL (IX + d)
+ { &opcode_xycb_39, 20 }, // LD C, SRL (IX + d)
+ { &opcode_xycb_3a, 20 }, // LD D, SRL (IX + d)
+ { &opcode_xycb_3b, 20 }, // LD E, SRL (IX + d)
+ { &opcode_xycb_3c, 20 }, // LD H, SRL (IX + d)
+ { &opcode_xycb_3d, 20 }, // LD L, SRL (IX + d)
+ { &opcode_xycb_3e, 20 }, // SRL (IX + d)
+ { &opcode_xycb_3f, 20 }, // LD A, SRL (IX + d)
+ { &opcode_xycb_40, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_41, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_42, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_43, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_44, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_45, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_46, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_47, 20 }, // BIT 0, (IX + d)
+ { &opcode_xycb_48, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_49, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_4a, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_4b, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_4c, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_4d, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_4e, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_4f, 20 }, // BIT 1, (IX + d)
+ { &opcode_xycb_50, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_51, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_52, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_53, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_54, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_55, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_56, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_57, 20 }, // BIT 2, (IX + d)
+ { &opcode_xycb_58, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_59, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_5a, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_5b, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_5c, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_5d, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_5e, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_5f, 20 }, // BIT 3, (IX + d)
+ { &opcode_xycb_60, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_61, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_62, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_63, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_64, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_65, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_66, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_67, 20 }, // BIT 4, (IX + d)
+ { &opcode_xycb_68, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_69, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_6a, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_6b, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_6c, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_6d, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_6e, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_6f, 20 }, // BIT 5, (IX + d)
+ { &opcode_xycb_70, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_71, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_72, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_73, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_74, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_75, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_76, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_77, 20 }, // BIT 6, (IX + d)
+ { &opcode_xycb_78, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_79, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_7a, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_7b, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_7c, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_7d, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_7e, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_7f, 20 }, // BIT 7, (IX + d)
+ { &opcode_xycb_80, 20 }, // LD B, RES 0, (IX + d)
+ { &opcode_xycb_81, 20 }, // LD C, RES 0, (IX + d)
+ { &opcode_xycb_82, 20 }, // LD D, RES 0, (IX + d)
+ { &opcode_xycb_83, 20 }, // LD E, RES 0, (IX + d)
+ { &opcode_xycb_84, 20 }, // LD H, RES 0, (IX + d)
+ { &opcode_xycb_85, 20 }, // LD L, RES 0, (IX + d)
+ { &opcode_xycb_86, 20 }, // RES 0, (IX + d)
+ { &opcode_xycb_87, 20 }, // LD A, RES 0, (IX + d)
+ { &opcode_xycb_88, 20 }, // LD B, RES 1, (IX + d)
+ { &opcode_xycb_89, 20 }, // LD C, RES 1, (IX + d)
+ { &opcode_xycb_8a, 20 }, // LD D, RES 1, (IX + d)
+ { &opcode_xycb_8b, 20 }, // LD E, RES 1, (IX + d)
+ { &opcode_xycb_8c, 20 }, // LD H, RES 1, (IX + d)
+ { &opcode_xycb_8d, 20 }, // LD L, RES 1, (IX + d)
+ { &opcode_xycb_8e, 20 }, // RES 1, (IX + d)
+ { &opcode_xycb_8f, 20 }, // LD A, RES 1, (IX + d)
+ { &opcode_xycb_90, 20 }, // LD B, RES 2, (IX + d)
+ { &opcode_xycb_91, 20 }, // LD C, RES 2, (IX + d)
+ { &opcode_xycb_92, 20 }, // LD D, RES 2, (IX + d)
+ { &opcode_xycb_93, 20 }, // LD E, RES 2, (IX + d)
+ { &opcode_xycb_94, 20 }, // LD H, RES 2, (IX + d)
+ { &opcode_xycb_95, 20 }, // LD L, RES 2, (IX + d)
+ { &opcode_xycb_96, 20 }, // RES 2, (IX + d)
+ { &opcode_xycb_97, 20 }, // LD A, RES 2, (IX + d)
+ { &opcode_xycb_98, 20 }, // LD B, RES 3, (IX + d)
+ { &opcode_xycb_99, 20 }, // LD C, RES 3, (IX + d)
+ { &opcode_xycb_9a, 20 }, // LD D, RES 3, (IX + d)
+ { &opcode_xycb_9b, 20 }, // LD E, RES 3, (IX + d)
+ { &opcode_xycb_9c, 20 }, // LD H, RES 3, (IX + d)
+ { &opcode_xycb_9d, 20 }, // LD L, RES 3, (IX + d)
+ { &opcode_xycb_9e, 20 }, // RES 3, (IX + d)
+ { &opcode_xycb_9f, 20 }, // LD A, RES 3, (IX + d)
+ { &opcode_xycb_a0, 20 }, // LD B, RES 4, (IX + d)
+ { &opcode_xycb_a1, 20 }, // LD C, RES 4, (IX + d)
+ { &opcode_xycb_a2, 20 }, // LD D, RES 4, (IX + d)
+ { &opcode_xycb_a3, 20 }, // LD E, RES 4, (IX + d)
+ { &opcode_xycb_a4, 20 }, // LD H, RES 4, (IX + d)
+ { &opcode_xycb_a5, 20 }, // LD L, RES 4, (IX + d)
+ { &opcode_xycb_a6, 20 }, // RES 4, (IX + d)
+ { &opcode_xycb_a7, 20 }, // LD A, RES 4, (IX + d)
+ { &opcode_xycb_a8, 20 }, // LD B, RES 5, (IX + d)
+ { &opcode_xycb_a9, 20 }, // LD C, RES 5, (IX + d)
+ { &opcode_xycb_aa, 20 }, // LD D, RES 5, (IX + d)
+ { &opcode_xycb_ab, 20 }, // LD E, RES 5, (IX + d)
+ { &opcode_xycb_ac, 20 }, // LD H, RES 5, (IX + d)
+ { &opcode_xycb_ad, 20 }, // LD L, RES 5, (IX + d)
+ { &opcode_xycb_ae, 20 }, // RES 5, (IX + d)
+ { &opcode_xycb_af, 20 }, // LD A, RES 5, (IX + d)
+ { &opcode_xycb_b0, 20 }, // LD B, RES 6, (IX + d)
+ { &opcode_xycb_b1, 20 }, // LD C, RES 6, (IX + d)
+ { &opcode_xycb_b2, 20 }, // LD D, RES 6, (IX + d)
+ { &opcode_xycb_b3, 20 }, // LD E, RES 6, (IX + d)
+ { &opcode_xycb_b4, 20 }, // LD H, RES 6, (IX + d)
+ { &opcode_xycb_b5, 20 }, // LD L, RES 6, (IX + d)
+ { &opcode_xycb_b6, 20 }, // RES 6, (IX + d)
+ { &opcode_xycb_b7, 20 }, // LD A, RES 6, (IX + d)
+ { &opcode_xycb_b8, 20 }, // LD B, RES 7, (IX + d)
+ { &opcode_xycb_b9, 20 }, // LD C, RES 7, (IX + d)
+ { &opcode_xycb_ba, 20 }, // LD D, RES 7, (IX + d)
+ { &opcode_xycb_bb, 20 }, // LD E, RES 7, (IX + d)
+ { &opcode_xycb_bc, 20 }, // LD H, RES 7, (IX + d)
+ { &opcode_xycb_bd, 20 }, // LD L, RES 7, (IX + d)
+ { &opcode_xycb_be, 20 }, // RES 7, (IX + d)
+ { &opcode_xycb_bf, 20 }, // LD A, RES 7, (IX + d)
+ { &opcode_xycb_c0, 20 }, // LD B, SET 0, (IX + d)
+ { &opcode_xycb_c1, 20 }, // LD C, SET 0, (IX + d)
+ { &opcode_xycb_c2, 20 }, // LD D, SET 0, (IX + d)
+ { &opcode_xycb_c3, 20 }, // LD E, SET 0, (IX + d)
+ { &opcode_xycb_c4, 20 }, // LD H, SET 0, (IX + d)
+ { &opcode_xycb_c5, 20 }, // LD L, SET 0, (IX + d)
+ { &opcode_xycb_c6, 20 }, // SET 0, (IX + d)
+ { &opcode_xycb_c7, 20 }, // LD A, SET 0, (IX + d)
+ { &opcode_xycb_c8, 20 }, // LD B, SET 1, (IX + d)
+ { &opcode_xycb_c9, 20 }, // LD C, SET 1, (IX + d)
+ { &opcode_xycb_ca, 20 }, // LD D, SET 1, (IX + d)
+ { &opcode_xycb_cb, 20 }, // LD E, SET 1, (IX + d)
+ { &opcode_xycb_cc, 20 }, // LD H, SET 1, (IX + d)
+ { &opcode_xycb_cd, 20 }, // LD L, SET 1, (IX + d)
+ { &opcode_xycb_ce, 20 }, // SET 1, (IX + d)
+ { &opcode_xycb_cf, 20 }, // LD A, SET 1, (IX + d)
+ { &opcode_xycb_d0, 20 }, // LD B, SET 2, (IX + d)
+ { &opcode_xycb_d1, 20 }, // LD C, SET 2, (IX + d)
+ { &opcode_xycb_d2, 20 }, // LD D, SET 2, (IX + d)
+ { &opcode_xycb_d3, 20 }, // LD E, SET 2, (IX + d)
+ { &opcode_xycb_d4, 20 }, // LD H, SET 2, (IX + d)
+ { &opcode_xycb_d5, 20 }, // LD L, SET 2, (IX + d)
+ { &opcode_xycb_d6, 20 }, // SET 2, (IX + d)
+ { &opcode_xycb_d7, 20 }, // LD A, SET 2, (IX + d)
+ { &opcode_xycb_d8, 20 }, // LD B, SET 3, (IX + d)
+ { &opcode_xycb_d9, 20 }, // LD C, SET 3, (IX + d)
+ { &opcode_xycb_da, 20 }, // LD D, SET 3, (IX + d)
+ { &opcode_xycb_db, 20 }, // LD E, SET 3, (IX + d)
+ { &opcode_xycb_dc, 20 }, // LD H, SET 3, (IX + d)
+ { &opcode_xycb_dd, 20 }, // LD L, SET 3, (IX + d)
+ { &opcode_xycb_de, 20 }, // SET 3, (IX + d)
+ { &opcode_xycb_df, 20 }, // LD A, SET 3, (IX + d)
+ { &opcode_xycb_e0, 20 }, // LD B, SET 4, (IX + d)
+ { &opcode_xycb_e1, 20 }, // LD C, SET 4, (IX + d)
+ { &opcode_xycb_e2, 20 }, // LD D, SET 4, (IX + d)
+ { &opcode_xycb_e3, 20 }, // LD E, SET 4, (IX + d)
+ { &opcode_xycb_e4, 20 }, // LD H, SET 4, (IX + d)
+ { &opcode_xycb_e5, 20 }, // LD L, SET 4, (IX + d)
+ { &opcode_xycb_e6, 20 }, // SET 4, (IX + d)
+ { &opcode_xycb_e7, 20 }, // LD A, SET 4, (IX + d)
+ { &opcode_xycb_e8, 20 }, // LD B, SET 5, (IX + d)
+ { &opcode_xycb_e9, 20 }, // LD C, SET 5, (IX + d)
+ { &opcode_xycb_ea, 20 }, // LD D, SET 5, (IX + d)
+ { &opcode_xycb_eb, 20 }, // LD E, SET 5, (IX + d)
+ { &opcode_xycb_ec, 20 }, // LD H, SET 5, (IX + d)
+ { &opcode_xycb_ed, 20 }, // LD L, SET 5, (IX + d)
+ { &opcode_xycb_ee, 20 }, // SET 5, (IX + d)
+ { &opcode_xycb_ef, 20 }, // LD A, SET 5, (IX + d)
+ { &opcode_xycb_f0, 20 }, // LD B, SET 6, (IX + d)
+ { &opcode_xycb_f1, 20 }, // LD C, SET 6, (IX + d)
+ { &opcode_xycb_f2, 20 }, // LD D, SET 6, (IX + d)
+ { &opcode_xycb_f3, 20 }, // LD E, SET 6, (IX + d)
+ { &opcode_xycb_f4, 20 }, // LD H, SET 6, (IX + d)
+ { &opcode_xycb_f5, 20 }, // LD L, SET 6, (IX + d)
+ { &opcode_xycb_f6, 20 }, // SET 6, (IX + d)
+ { &opcode_xycb_f7, 20 }, // LD A, SET 6, (IX + d)
+ { &opcode_xycb_f8, 20 }, // LD B, SET 7, (IX + d)
+ { &opcode_xycb_f9, 20 }, // LD C, SET 7, (IX + d)
+ { &opcode_xycb_fa, 20 }, // LD D, SET 7, (IX + d)
+ { &opcode_xycb_fb, 20 }, // LD E, SET 7, (IX + d)
+ { &opcode_xycb_fc, 20 }, // LD H, SET 7, (IX + d)
+ { &opcode_xycb_fd, 20 }, // LD L, SET 7, (IX + d)
+ { &opcode_xycb_fe, 20 }, // SET 7, (IX + d)
+ { &opcode_xycb_ff, 20 } // LD A, SET 7, (IX + d)
+};
+
+unsigned do_opcode_xycb( unsigned xy )
+{
+ xy = addDispl( xy, fetchByte() );
+
+ unsigned op = fetchByte();
+
+ cycles_ += OpInfoXYCB_[ op ].cycles;
+
+ OpInfoXYCB_[ op ].handler( xy );
+
+ return xy;
+}
+
+void opcode_xycb_00( unsigned xy ) // LD B, RLC (IX + d)
+{
+ B = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_01( unsigned xy ) // LD C, RLC (IX + d)
+{
+ C = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_02( unsigned xy ) // LD D, RLC (IX + d)
+{
+ D = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_03( unsigned xy ) // LD E, RLC (IX + d)
+{
+ E = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_04( unsigned xy ) // LD H, RLC (IX + d)
+{
+ H = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_05( unsigned xy ) // LD L, RLC (IX + d)
+{
+ L = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_06( unsigned xy ) // RLC (IX + d)
+{
+ writeByte( xy, rotateLeftCarry( readByte(xy) ) );
+}
+
+void opcode_xycb_07( unsigned xy ) // LD A, RLC (IX + d)
+{
+ A = rotateLeftCarry( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_08( unsigned xy ) // LD B, RRC (IX + d)
+{
+ B = rotateRightCarry( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_09( unsigned xy ) // LD C, RRC (IX + d)
+{
+ C = rotateRightCarry( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_0a( unsigned xy ) // LD D, RRC (IX + d)
+{
+ D = rotateRightCarry( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_0b( unsigned xy ) // LD E, RRC (IX + d)
+{
+ E = rotateRightCarry( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_0c( unsigned xy ) // LD H, RRC (IX + d)
+{
+ H = rotateRightCarry( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_0d( unsigned xy ) // LD L, RRC (IX + d)
+{
+ L = rotateRightCarry( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_0e( unsigned xy ) // RRC (IX + d)
+{
+ writeByte( xy, rotateRightCarry( readByte(xy) ) );
+}
+
+void opcode_xycb_0f( unsigned xy ) // LD A, RRC (IX + d)
+{
+ A = rotateRightCarry( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_10( unsigned xy ) // LD B, RL (IX + d)
+{
+ B = rotateLeft( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_11( unsigned xy ) // LD C, RL (IX + d)
+{
+ C = rotateLeft( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_12( unsigned xy ) // LD D, RL (IX + d)
+{
+ D = rotateLeft( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_13( unsigned xy ) // LD E, RL (IX + d)
+{
+ E = rotateLeft( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_14( unsigned xy ) // LD H, RL (IX + d)
+{
+ H = rotateLeft( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_15( unsigned xy ) // LD L, RL (IX + d)
+{
+ L = rotateLeft( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_16( unsigned xy ) // RL (IX + d)
+{
+ writeByte( xy, rotateLeft( readByte(xy) ) );
+}
+
+void opcode_xycb_17( unsigned xy ) // LD A, RL (IX + d)
+{
+ A = rotateLeft( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_18( unsigned xy ) // LD B, RR (IX + d)
+{
+ B = rotateRight( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_19( unsigned xy ) // LD C, RR (IX + d)
+{
+ C = rotateRight( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_1a( unsigned xy ) // LD D, RR (IX + d)
+{
+ D = rotateRight( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_1b( unsigned xy ) // LD E, RR (IX + d)
+{
+ E = rotateRight( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_1c( unsigned xy ) // LD H, RR (IX + d)
+{
+ H = rotateRight( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_1d( unsigned xy ) // LD L, RR (IX + d)
+{
+ L = rotateRight( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_1e( unsigned xy ) // RR (IX + d)
+{
+ writeByte( xy, rotateRight( readByte(xy) ) );
+}
+
+void opcode_xycb_1f( unsigned xy ) // LD A, RR (IX + d)
+{
+ A = rotateRight( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_20( unsigned xy ) // LD B, SLA (IX + d)
+{
+ B = shiftLeft( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_21( unsigned xy ) // LD C, SLA (IX + d)
+{
+ C = shiftLeft( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_22( unsigned xy ) // LD D, SLA (IX + d)
+{
+ D = shiftLeft( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_23( unsigned xy ) // LD E, SLA (IX + d)
+{
+ E = shiftLeft( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_24( unsigned xy ) // LD H, SLA (IX + d)
+{
+ H = shiftLeft( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_25( unsigned xy ) // LD L, SLA (IX + d)
+{
+ L = shiftLeft( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_26( unsigned xy ) // SLA (IX + d)
+{
+ writeByte( xy, shiftLeft( readByte(xy) ) );
+}
+
+void opcode_xycb_27( unsigned xy ) // LD A, SLA (IX + d)
+{
+ A = shiftLeft( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_28( unsigned xy ) // LD B, SRA (IX + d)
+{
+ B = shiftRightArith( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_29( unsigned xy ) // LD C, SRA (IX + d)
+{
+ C = shiftRightArith( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_2a( unsigned xy ) // LD D, SRA (IX + d)
+{
+ D = shiftRightArith( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_2b( unsigned xy ) // LD E, SRA (IX + d)
+{
+ E = shiftRightArith( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_2c( unsigned xy ) // LD H, SRA (IX + d)
+{
+ H = shiftRightArith( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_2d( unsigned xy ) // LD L, SRA (IX + d)
+{
+ L = shiftRightArith( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_2e( unsigned xy ) // SRA (IX + d)
+{
+ writeByte( xy, shiftRightArith( readByte(xy) ) );
+}
+
+void opcode_xycb_2f( unsigned xy ) // LD A, SRA (IX + d)
+{
+ A = shiftRightArith( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_30( unsigned xy ) // LD B, SLL (IX + d)
+{
+ B = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, B );
+}
+
+void opcode_xycb_31( unsigned xy ) // LD C, SLL (IX + d)
+{
+ C = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, C );
+}
+
+void opcode_xycb_32( unsigned xy ) // LD D, SLL (IX + d)
+{
+ D = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, D );
+}
+
+void opcode_xycb_33( unsigned xy ) // LD E, SLL (IX + d)
+{
+ E = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, E );
+}
+
+void opcode_xycb_34( unsigned xy ) // LD H, SLL (IX + d)
+{
+ H = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, H );
+}
+
+void opcode_xycb_35( unsigned xy ) // LD L, SLL (IX + d)
+{
+ L = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, L );
+}
+
+void opcode_xycb_36( unsigned xy ) // SLL (IX + d)
+{
+ writeByte( xy, shiftLeft( readByte(xy) ) | 0x01 );
+}
+
+void opcode_xycb_37( unsigned xy ) // LD A, SLL (IX + d)
+{
+ A = shiftLeft( readByte(xy) ) | 0x01;
+ writeByte( xy, A );
+}
+
+void opcode_xycb_38( unsigned xy ) // LD B, SRL (IX + d)
+{
+ B = shiftRightLogical( readByte(xy) );
+ writeByte( xy, B );
+}
+
+void opcode_xycb_39( unsigned xy ) // LD C, SRL (IX + d)
+{
+ C = shiftRightLogical( readByte(xy) );
+ writeByte( xy, C );
+}
+
+void opcode_xycb_3a( unsigned xy ) // LD D, SRL (IX + d)
+{
+ D = shiftRightLogical( readByte(xy) );
+ writeByte( xy, D );
+}
+
+void opcode_xycb_3b( unsigned xy ) // LD E, SRL (IX + d)
+{
+ E = shiftRightLogical( readByte(xy) );
+ writeByte( xy, E );
+}
+
+void opcode_xycb_3c( unsigned xy ) // LD H, SRL (IX + d)
+{
+ H = shiftRightLogical( readByte(xy) );
+ writeByte( xy, H );
+}
+
+void opcode_xycb_3d( unsigned xy ) // LD L, SRL (IX + d)
+{
+ L = shiftRightLogical( readByte(xy) );
+ writeByte( xy, L );
+}
+
+void opcode_xycb_3e( unsigned xy ) // SRL (IX + d)
+{
+ writeByte( xy, shiftRightLogical( readByte(xy) ) );
+}
+
+void opcode_xycb_3f( unsigned xy ) // LD A, SRL (IX + d)
+{
+ A = shiftRightLogical( readByte(xy) );
+ writeByte( xy, A );
+}
+
+void opcode_xycb_40( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_41( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_42( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_43( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_44( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_45( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_46( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_47( unsigned xy ) // BIT 0, (IX + d)
+{
+ testBit( 0, readByte( xy ) );
+}
+
+void opcode_xycb_48( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_49( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_4a( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_4b( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_4c( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_4d( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_4e( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_4f( unsigned xy ) // BIT 1, (IX + d)
+{
+ testBit( 1, readByte( xy ) );
+}
+
+void opcode_xycb_50( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_51( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_52( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_53( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_54( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_55( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_56( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_57( unsigned xy ) // BIT 2, (IX + d)
+{
+ testBit( 2, readByte( xy ) );
+}
+
+void opcode_xycb_58( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_59( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_5a( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_5b( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_5c( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_5d( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_5e( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_5f( unsigned xy ) // BIT 3, (IX + d)
+{
+ testBit( 3, readByte( xy ) );
+}
+
+void opcode_xycb_60( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_61( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_62( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_63( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_64( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_65( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_66( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_67( unsigned xy ) // BIT 4, (IX + d)
+{
+ testBit( 4, readByte( xy ) );
+}
+
+void opcode_xycb_68( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_69( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_6a( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_6b( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_6c( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_6d( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_6e( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_6f( unsigned xy ) // BIT 5, (IX + d)
+{
+ testBit( 5, readByte( xy ) );
+}
+
+void opcode_xycb_70( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_71( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_72( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_73( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_74( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_75( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_76( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_77( unsigned xy ) // BIT 6, (IX + d)
+{
+ testBit( 6, readByte( xy ) );
+}
+
+void opcode_xycb_78( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_79( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_7a( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_7b( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_7c( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_7d( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_7e( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_7f( unsigned xy ) // BIT 7, (IX + d)
+{
+ testBit( 7, readByte( xy ) );
+}
+
+void opcode_xycb_80( unsigned xy ) // LD B, RES 0, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_81( unsigned xy ) // LD C, RES 0, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_82( unsigned xy ) // LD D, RES 0, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_83( unsigned xy ) // LD E, RES 0, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_84( unsigned xy ) // LD H, RES 0, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_85( unsigned xy ) // LD L, RES 0, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_86( unsigned xy ) // RES 0, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 0) );
+}
+
+void opcode_xycb_87( unsigned xy ) // LD A, RES 0, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 0);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_88( unsigned xy ) // LD B, RES 1, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_89( unsigned xy ) // LD C, RES 1, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_8a( unsigned xy ) // LD D, RES 1, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_8b( unsigned xy ) // LD E, RES 1, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_8c( unsigned xy ) // LD H, RES 1, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_8d( unsigned xy ) // LD L, RES 1, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_8e( unsigned xy ) // RES 1, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 1) );
+}
+
+void opcode_xycb_8f( unsigned xy ) // LD A, RES 1, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 1);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_90( unsigned xy ) // LD B, RES 2, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_91( unsigned xy ) // LD C, RES 2, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_92( unsigned xy ) // LD D, RES 2, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_93( unsigned xy ) // LD E, RES 2, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_94( unsigned xy ) // LD H, RES 2, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_95( unsigned xy ) // LD L, RES 2, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_96( unsigned xy ) // RES 2, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 2) );
+}
+
+void opcode_xycb_97( unsigned xy ) // LD A, RES 2, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 2);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_98( unsigned xy ) // LD B, RES 3, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_99( unsigned xy ) // LD C, RES 3, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_9a( unsigned xy ) // LD D, RES 3, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_9b( unsigned xy ) // LD E, RES 3, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_9c( unsigned xy ) // LD H, RES 3, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_9d( unsigned xy ) // LD L, RES 3, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_9e( unsigned xy ) // RES 3, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 3) );
+}
+
+void opcode_xycb_9f( unsigned xy ) // LD A, RES 3, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 3);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_a0( unsigned xy ) // LD B, RES 4, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_a1( unsigned xy ) // LD C, RES 4, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_a2( unsigned xy ) // LD D, RES 4, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_a3( unsigned xy ) // LD E, RES 4, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_a4( unsigned xy ) // LD H, RES 4, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_a5( unsigned xy ) // LD L, RES 4, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_a6( unsigned xy ) // RES 4, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 4) );
+}
+
+void opcode_xycb_a7( unsigned xy ) // LD A, RES 4, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 4);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_a8( unsigned xy ) // LD B, RES 5, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_a9( unsigned xy ) // LD C, RES 5, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_aa( unsigned xy ) // LD D, RES 5, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_ab( unsigned xy ) // LD E, RES 5, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_ac( unsigned xy ) // LD H, RES 5, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_ad( unsigned xy ) // LD L, RES 5, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_ae( unsigned xy ) // RES 5, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 5) );
+}
+
+void opcode_xycb_af( unsigned xy ) // LD A, RES 5, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 5);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_b0( unsigned xy ) // LD B, RES 6, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_b1( unsigned xy ) // LD C, RES 6, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_b2( unsigned xy ) // LD D, RES 6, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_b3( unsigned xy ) // LD E, RES 6, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_b4( unsigned xy ) // LD H, RES 6, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_b5( unsigned xy ) // LD L, RES 6, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_b6( unsigned xy ) // RES 6, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 6) );
+}
+
+void opcode_xycb_b7( unsigned xy ) // LD A, RES 6, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 6);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_b8( unsigned xy ) // LD B, RES 7, (IX + d)
+{
+ B = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_b9( unsigned xy ) // LD C, RES 7, (IX + d)
+{
+ C = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_ba( unsigned xy ) // LD D, RES 7, (IX + d)
+{
+ D = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_bb( unsigned xy ) // LD E, RES 7, (IX + d)
+{
+ E = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_bc( unsigned xy ) // LD H, RES 7, (IX + d)
+{
+ H = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_bd( unsigned xy ) // LD L, RES 7, (IX + d)
+{
+ L = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_be( unsigned xy ) // RES 7, (IX + d)
+{
+ writeByte( xy, readByte(xy) & (unsigned char) ~(1 << 7) );
+}
+
+void opcode_xycb_bf( unsigned xy ) // LD A, RES 7, (IX + d)
+{
+ A = readByte(xy) & (unsigned char) ~(1 << 7);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_c0( unsigned xy ) // LD B, SET 0, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_c1( unsigned xy ) // LD C, SET 0, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_c2( unsigned xy ) // LD D, SET 0, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_c3( unsigned xy ) // LD E, SET 0, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_c4( unsigned xy ) // LD H, SET 0, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_c5( unsigned xy ) // LD L, SET 0, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_c6( unsigned xy ) // SET 0, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 0) );
+}
+
+void opcode_xycb_c7( unsigned xy ) // LD A, SET 0, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 0);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_c8( unsigned xy ) // LD B, SET 1, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_c9( unsigned xy ) // LD C, SET 1, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_ca( unsigned xy ) // LD D, SET 1, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_cb( unsigned xy ) // LD E, SET 1, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_cc( unsigned xy ) // LD H, SET 1, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_cd( unsigned xy ) // LD L, SET 1, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_ce( unsigned xy ) // SET 1, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 1) );
+}
+
+void opcode_xycb_cf( unsigned xy ) // LD A, SET 1, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 1);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_d0( unsigned xy ) // LD B, SET 2, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_d1( unsigned xy ) // LD C, SET 2, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_d2( unsigned xy ) // LD D, SET 2, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_d3( unsigned xy ) // LD E, SET 2, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_d4( unsigned xy ) // LD H, SET 2, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_d5( unsigned xy ) // LD L, SET 2, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_d6( unsigned xy ) // SET 2, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 2) );
+}
+
+void opcode_xycb_d7( unsigned xy ) // LD A, SET 2, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 2);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_d8( unsigned xy ) // LD B, SET 3, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_d9( unsigned xy ) // LD C, SET 3, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_da( unsigned xy ) // LD D, SET 3, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_db( unsigned xy ) // LD E, SET 3, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_dc( unsigned xy ) // LD H, SET 3, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_dd( unsigned xy ) // LD L, SET 3, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_de( unsigned xy ) // SET 3, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 3) );
+}
+
+void opcode_xycb_df( unsigned xy ) // LD A, SET 3, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 3);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_e0( unsigned xy ) // LD B, SET 4, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_e1( unsigned xy ) // LD C, SET 4, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_e2( unsigned xy ) // LD D, SET 4, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_e3( unsigned xy ) // LD E, SET 4, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_e4( unsigned xy ) // LD H, SET 4, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_e5( unsigned xy ) // LD L, SET 4, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_e6( unsigned xy ) // SET 4, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 4) );
+}
+
+void opcode_xycb_e7( unsigned xy ) // LD A, SET 4, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 4);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_e8( unsigned xy ) // LD B, SET 5, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_e9( unsigned xy ) // LD C, SET 5, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_ea( unsigned xy ) // LD D, SET 5, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_eb( unsigned xy ) // LD E, SET 5, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_ec( unsigned xy ) // LD H, SET 5, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_ed( unsigned xy ) // LD L, SET 5, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_ee( unsigned xy ) // SET 5, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 5) );
+}
+
+void opcode_xycb_ef( unsigned xy ) // LD A, SET 5, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 5);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_f0( unsigned xy ) // LD B, SET 6, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_f1( unsigned xy ) // LD C, SET 6, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_f2( unsigned xy ) // LD D, SET 6, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_f3( unsigned xy ) // LD E, SET 6, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_f4( unsigned xy ) // LD H, SET 6, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_f5( unsigned xy ) // LD L, SET 6, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_f6( unsigned xy ) // SET 6, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 6) );
+}
+
+void opcode_xycb_f7( unsigned xy ) // LD A, SET 6, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 6);
+ writeByte( xy, A );
+}
+
+void opcode_xycb_f8( unsigned xy ) // LD B, SET 7, (IX + d)
+{
+ B = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, B );
+}
+
+void opcode_xycb_f9( unsigned xy ) // LD C, SET 7, (IX + d)
+{
+ C = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, C );
+}
+
+void opcode_xycb_fa( unsigned xy ) // LD D, SET 7, (IX + d)
+{
+ D = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, D );
+}
+
+void opcode_xycb_fb( unsigned xy ) // LD E, SET 7, (IX + d)
+{
+ E = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, E );
+}
+
+void opcode_xycb_fc( unsigned xy ) // LD H, SET 7, (IX + d)
+{
+ H = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, H );
+}
+
+void opcode_xycb_fd( unsigned xy ) // LD L, SET 7, (IX + d)
+{
+ L = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, L );
+}
+
+void opcode_xycb_fe( unsigned xy ) // SET 7, (IX + d)
+{
+ writeByte( xy, readByte(xy) | (unsigned char) (1 << 7) );
+}
+
+void opcode_xycb_ff( unsigned xy ) // LD A, SET 7, (IX + d)
+{
+ A = readByte(xy) | (unsigned char) (1 << 7);
+ writeByte( xy, A );
+}
+
+OpcodeInfo OpInfo_[256] = {
+ { &opcode_00, 4 }, // NOP
+ { &opcode_01, 10 }, // LD BC,nn
+ { &opcode_02, 7 }, // LD (BC),A
+ { &opcode_03, 6 }, // INC BC
+ { &opcode_04, 4 }, // INC B
+ { &opcode_05, 4 }, // DEC B
+ { &opcode_06, 7 }, // LD B,n
+ { &opcode_07, 4 }, // RLCA
+ { &opcode_08, 4 }, // EX AF,AF'
+ { &opcode_09, 11 }, // ADD HL,BC
+ { &opcode_0a, 7 }, // LD A,(BC)
+ { &opcode_0b, 6 }, // DEC BC
+ { &opcode_0c, 4 }, // INC C
+ { &opcode_0d, 4 }, // DEC C
+ { &opcode_0e, 7 }, // LD C,n
+ { &opcode_0f, 4 }, // RRCA
+ { &opcode_10, 8 }, // DJNZ d
+ { &opcode_11, 10 }, // LD DE,nn
+ { &opcode_12, 7 }, // LD (DE),A
+ { &opcode_13, 6 }, // INC DE
+ { &opcode_14, 4 }, // INC D
+ { &opcode_15, 4 }, // DEC D
+ { &opcode_16, 7 }, // LD D,n
+ { &opcode_17, 4 }, // RLA
+ { &opcode_18, 12 }, // JR d
+ { &opcode_19, 11 }, // ADD HL,DE
+ { &opcode_1a, 7 }, // LD A,(DE)
+ { &opcode_1b, 6 }, // DEC DE
+ { &opcode_1c, 4 }, // INC E
+ { &opcode_1d, 4 }, // DEC E
+ { &opcode_1e, 7 }, // LD E,n
+ { &opcode_1f, 4 }, // RRA
+ { &opcode_20, 7 }, // JR NZ,d
+ { &opcode_21, 10 }, // LD HL,nn
+ { &opcode_22, 16 }, // LD (nn),HL
+ { &opcode_23, 6 }, // INC HL
+ { &opcode_24, 4 }, // INC H
+ { &opcode_25, 4 }, // DEC H
+ { &opcode_26, 7 }, // LD H,n
+ { &opcode_27, 4 }, // DAA
+ { &opcode_28, 7 }, // JR Z,d
+ { &opcode_29, 11 }, // ADD HL,HL
+ { &opcode_2a, 16 }, // LD HL,(nn)
+ { &opcode_2b, 6 }, // DEC HL
+ { &opcode_2c, 4 }, // INC L
+ { &opcode_2d, 4 }, // DEC L
+ { &opcode_2e, 7 }, // LD L,n
+ { &opcode_2f, 4 }, // CPL
+ { &opcode_30, 7 }, // JR NC,d
+ { &opcode_31, 10 }, // LD SP,nn
+ { &opcode_32, 13 }, // LD (nn),A
+ { &opcode_33, 6 }, // INC SP
+ { &opcode_34, 11 }, // INC (HL)
+ { &opcode_35, 11 }, // DEC (HL)
+ { &opcode_36, 10 }, // LD (HL),n
+ { &opcode_37, 4 }, // SCF
+ { &opcode_38, 7 }, // JR C,d
+ { &opcode_39, 11 }, // ADD HL,SP
+ { &opcode_3a, 13 }, // LD A,(nn)
+ { &opcode_3b, 6 }, // DEC SP
+ { &opcode_3c, 4 }, // INC A
+ { &opcode_3d, 4 }, // DEC A
+ { &opcode_3e, 7 }, // LD A,n
+ { &opcode_3f, 4 }, // CCF
+ { &opcode_40, 4 }, // LD B,B
+ { &opcode_41, 4 }, // LD B,C
+ { &opcode_42, 4 }, // LD B,D
+ { &opcode_43, 4 }, // LD B,E
+ { &opcode_44, 4 }, // LD B,H
+ { &opcode_45, 4 }, // LD B,L
+ { &opcode_46, 7 }, // LD B,(HL)
+ { &opcode_47, 4 }, // LD B,A
+ { &opcode_48, 4 }, // LD C,B
+ { &opcode_49, 4 }, // LD C,C
+ { &opcode_4a, 4 }, // LD C,D
+ { &opcode_4b, 4 }, // LD C,E
+ { &opcode_4c, 4 }, // LD C,H
+ { &opcode_4d, 4 }, // LD C,L
+ { &opcode_4e, 7 }, // LD C,(HL)
+ { &opcode_4f, 4 }, // LD C,A
+ { &opcode_50, 4 }, // LD D,B
+ { &opcode_51, 4 }, // LD D,C
+ { &opcode_52, 4 }, // LD D,D
+ { &opcode_53, 4 }, // LD D,E
+ { &opcode_54, 4 }, // LD D,H
+ { &opcode_55, 4 }, // LD D,L
+ { &opcode_56, 7 }, // LD D,(HL)
+ { &opcode_57, 4 }, // LD D,A
+ { &opcode_58, 4 }, // LD E,B
+ { &opcode_59, 4 }, // LD E,C
+ { &opcode_5a, 4 }, // LD E,D
+ { &opcode_5b, 4 }, // LD E,E
+ { &opcode_5c, 4 }, // LD E,H
+ { &opcode_5d, 4 }, // LD E,L
+ { &opcode_5e, 7 }, // LD E,(HL)
+ { &opcode_5f, 4 }, // LD E,A
+ { &opcode_60, 4 }, // LD H,B
+ { &opcode_61, 4 }, // LD H,C
+ { &opcode_62, 4 }, // LD H,D
+ { &opcode_63, 4 }, // LD H,E
+ { &opcode_64, 4 }, // LD H,H
+ { &opcode_65, 4 }, // LD H,L
+ { &opcode_66, 7 }, // LD H,(HL)
+ { &opcode_67, 4 }, // LD H,A
+ { &opcode_68, 4 }, // LD L,B
+ { &opcode_69, 4 }, // LD L,C
+ { &opcode_6a, 4 }, // LD L,D
+ { &opcode_6b, 4 }, // LD L,E
+ { &opcode_6c, 4 }, // LD L,H
+ { &opcode_6d, 4 }, // LD L,L
+ { &opcode_6e, 7 }, // LD L,(HL)
+ { &opcode_6f, 4 }, // LD L,A
+ { &opcode_70, 7 }, // LD (HL),B
+ { &opcode_71, 7 }, // LD (HL),C
+ { &opcode_72, 7 }, // LD (HL),D
+ { &opcode_73, 7 }, // LD (HL),E
+ { &opcode_74, 7 }, // LD (HL),H
+ { &opcode_75, 7 }, // LD (HL),L
+ { &opcode_76, 4 }, // HALT
+ { &opcode_77, 7 }, // LD (HL),A
+ { &opcode_78, 4 }, // LD A,B
+ { &opcode_79, 4 }, // LD A,C
+ { &opcode_7a, 4 }, // LD A,D
+ { &opcode_7b, 4 }, // LD A,E
+ { &opcode_7c, 4 }, // LD A,H
+ { &opcode_7d, 4 }, // LD A,L
+ { &opcode_7e, 7 }, // LD A,(HL)
+ { &opcode_7f, 4 }, // LD A,A
+ { &opcode_80, 4 }, // ADD A,B
+ { &opcode_81, 4 }, // ADD A,C
+ { &opcode_82, 4 }, // ADD A,D
+ { &opcode_83, 4 }, // ADD A,E
+ { &opcode_84, 4 }, // ADD A,H
+ { &opcode_85, 4 }, // ADD A,L
+ { &opcode_86, 7 }, // ADD A,(HL)
+ { &opcode_87, 4 }, // ADD A,A
+ { &opcode_88, 4 }, // ADC A,B
+ { &opcode_89, 4 }, // ADC A,C
+ { &opcode_8a, 4 }, // ADC A,D
+ { &opcode_8b, 4 }, // ADC A,E
+ { &opcode_8c, 4 }, // ADC A,H
+ { &opcode_8d, 4 }, // ADC A,L
+ { &opcode_8e, 7 }, // ADC A,(HL)
+ { &opcode_8f, 4 }, // ADC A,A
+ { &opcode_90, 4 }, // SUB B
+ { &opcode_91, 4 }, // SUB C
+ { &opcode_92, 4 }, // SUB D
+ { &opcode_93, 4 }, // SUB E
+ { &opcode_94, 4 }, // SUB H
+ { &opcode_95, 4 }, // SUB L
+ { &opcode_96, 7 }, // SUB (HL)
+ { &opcode_97, 4 }, // SUB A
+ { &opcode_98, 4 }, // SBC A,B
+ { &opcode_99, 4 }, // SBC A,C
+ { &opcode_9a, 4 }, // SBC A,D
+ { &opcode_9b, 4 }, // SBC A,E
+ { &opcode_9c, 4 }, // SBC A,H
+ { &opcode_9d, 4 }, // SBC A,L
+ { &opcode_9e, 7 }, // SBC A,(HL)
+ { &opcode_9f, 4 }, // SBC A,A
+ { &opcode_a0, 4 }, // AND B
+ { &opcode_a1, 4 }, // AND C
+ { &opcode_a2, 4 }, // AND D
+ { &opcode_a3, 4 }, // AND E
+ { &opcode_a4, 4 }, // AND H
+ { &opcode_a5, 4 }, // AND L
+ { &opcode_a6, 7 }, // AND (HL)
+ { &opcode_a7, 4 }, // AND A
+ { &opcode_a8, 4 }, // XOR B
+ { &opcode_a9, 4 }, // XOR C
+ { &opcode_aa, 4 }, // XOR D
+ { &opcode_ab, 4 }, // XOR E
+ { &opcode_ac, 4 }, // XOR H
+ { &opcode_ad, 4 }, // XOR L
+ { &opcode_ae, 7 }, // XOR (HL)
+ { &opcode_af, 4 }, // XOR A
+ { &opcode_b0, 4 }, // OR B
+ { &opcode_b1, 4 }, // OR C
+ { &opcode_b2, 4 }, // OR D
+ { &opcode_b3, 4 }, // OR E
+ { &opcode_b4, 4 }, // OR H
+ { &opcode_b5, 4 }, // OR L
+ { &opcode_b6, 7 }, // OR (HL)
+ { &opcode_b7, 4 }, // OR A
+ { &opcode_b8, 4 }, // CP B
+ { &opcode_b9, 4 }, // CP C
+ { &opcode_ba, 4 }, // CP D
+ { &opcode_bb, 4 }, // CP E
+ { &opcode_bc, 4 }, // CP H
+ { &opcode_bd, 4 }, // CP L
+ { &opcode_be, 7 }, // CP (HL)
+ { &opcode_bf, 4 }, // CP A
+ { &opcode_c0, 5 }, // RET NZ
+ { &opcode_c1, 10 }, // POP BC
+ { &opcode_c2, 10 }, // JP NZ,nn
+ { &opcode_c3, 10 }, // JP nn
+ { &opcode_c4, 10 }, // CALL NZ,nn
+ { &opcode_c5, 11 }, // PUSH BC
+ { &opcode_c6, 7 }, // ADD A,n
+ { &opcode_c7, 11 }, // RST 0
+ { &opcode_c8, 5 }, // RET Z
+ { &opcode_c9, 10 }, // RET
+ { &opcode_ca, 10 }, // JP Z,nn
+ { &opcode_cb, 0 }, // [Prefix]
+ { &opcode_cc, 10 }, // CALL Z,nn
+ { &opcode_cd, 17 }, // CALL nn
+ { &opcode_ce, 7 }, // ADC A,n
+ { &opcode_cf, 11 }, // RST 8
+ { &opcode_d0, 5 }, // RET NC
+ { &opcode_d1, 10 }, // POP DE
+ { &opcode_d2, 10 }, // JP NC,nn
+ { &opcode_d3, 11 }, // OUT (n),A
+ { &opcode_d4, 10 }, // CALL NC,nn
+ { &opcode_d5, 11 }, // PUSH DE
+ { &opcode_d6, 7 }, // SUB n
+ { &opcode_d7, 11 }, // RST 10H
+ { &opcode_d8, 5 }, // RET C
+ { &opcode_d9, 4 }, // EXX
+ { &opcode_da, 10 }, // JP C,nn
+ { &opcode_db, 11 }, // IN A,(n)
+ { &opcode_dc, 10 }, // CALL C,nn
+ { &opcode_dd, 0 }, // [IX Prefix]
+ { &opcode_de, 7 }, // SBC A,n
+ { &opcode_df, 11 }, // RST 18H
+ { &opcode_e0, 5 }, // RET PO
+ { &opcode_e1, 10 }, // POP HL
+ { &opcode_e2, 10 }, // JP PO,nn
+ { &opcode_e3, 19 }, // EX (SP),HL
+ { &opcode_e4, 10 }, // CALL PO,nn
+ { &opcode_e5, 11 }, // PUSH HL
+ { &opcode_e6, 7 }, // AND n
+ { &opcode_e7, 11 }, // RST 20H
+ { &opcode_e8, 5 }, // RET PE
+ { &opcode_e9, 4 }, // JP (HL)
+ { &opcode_ea, 10 }, // JP PE,nn
+ { &opcode_eb, 4 }, // EX DE,HL
+ { &opcode_ec, 10 }, // CALL PE,nn
+ { &opcode_ed, 0 }, // [Prefix]
+ { &opcode_ee, 7 }, // XOR n
+ { &opcode_ef, 11 }, // RST 28H
+ { &opcode_f0, 5 }, // RET P
+ { &opcode_f1, 10 }, // POP AF
+ { &opcode_f2, 10 }, // JP P,nn
+ { &opcode_f3, 4 }, // DI
+ { &opcode_f4, 10 }, // CALL P,nn
+ { &opcode_f5, 11 }, // PUSH AF
+ { &opcode_f6, 7 }, // OR n
+ { &opcode_f7, 11 }, // RST 30H
+ { &opcode_f8, 5 }, // RET M
+ { &opcode_f9, 6 }, // LD SP,HL
+ { &opcode_fa, 10 }, // JP M,nn
+ { &opcode_fb, 4 }, // EI
+ { &opcode_fc, 10 }, // CALL M,nn
+ { &opcode_fd, 0 }, // [IY Prefix]
+ { &opcode_fe, 7 }, // CP n
+ { &opcode_ff, 11 } // RST 38H
+};
+
+void opcode_00() // NOP
+{
+}
+
+void opcode_01() // LD BC,nn
+{
+ C = fetchByte();
+ B = fetchByte();
+}
+
+void opcode_02() // LD (BC),A
+{
+ writeByte( BC(), A );
+}
+
+void opcode_03() // INC BC
+{
+ if( ++C == 0 ) ++B;
+}
+
+void opcode_04() // INC B
+{
+ B = incByte( B );
+}
+
+void opcode_05() // DEC B
+{
+ B = decByte( B );
+}
+
+void opcode_06() // LD B,n
+{
+ B = fetchByte();
+}
+
+void opcode_07() // RLCA
+{
+ A = (A << 1) | (A >> 7);
+ F = F & ~(AddSub | Halfcarry | Carry);
+ if( A & 0x01 ) F |= Carry;
+}
+
+void opcode_08() // EX AF,AF'
+{
+ unsigned char x;
+
+ x = A; A = A1; A1 = x;
+ x = F; F = F1; F1 = x;
+}
+
+void opcode_09() // ADD HL,BC
+{
+ unsigned hl = HL();
+ unsigned rp = BC();
+ unsigned x = hl + rp;
+
+ F &= Sign | Zero | Parity;
+ if( x > 0xFFFF ) F |= Carry;
+ if( ((hl & 0xFFF) + (rp & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+
+ L = x & 0xFF;
+ H = (x >> 8) & 0xFF;
+}
+
+void opcode_0a() // LD A,(BC)
+{
+ A = readByte( BC() );
+}
+
+void opcode_0b() // DEC BC
+{
+ if( C-- == 0 ) --B;
+}
+
+void opcode_0c() // INC C
+{
+ C = incByte( C );
+}
+
+void opcode_0d() // DEC C
+{
+ C = decByte( C );
+}
+
+void opcode_0e() // LD C,n
+{
+ C = fetchByte();
+}
+
+void opcode_0f() // RRCA
+{
+ A = (A >> 1) | (A << 7);
+ F = F & ~(AddSub | Halfcarry | Carry);
+ if( A & 0x80 ) F |= Carry;
+}
+
+void opcode_10() // DJNZ d
+{
+ unsigned char o = fetchByte();
+
+ if( --B != 0 ) relJump( o );
+}
+
+void opcode_11() // LD DE,nn
+{
+ E = fetchByte();
+ D = fetchByte();
+}
+
+void opcode_12() // LD (DE),A
+{
+ writeByte( DE(), A );
+}
+
+void opcode_13() // INC DE
+{
+ if( ++E == 0 ) ++D;
+}
+
+void opcode_14() // INC D
+{
+ D = incByte( D );
+}
+
+void opcode_15() // DEC D
+{
+ D = decByte( D );
+}
+
+void opcode_16() // LD D,n
+{
+ D = fetchByte();
+}
+
+void opcode_17() // RLA
+{
+ unsigned char a = A;
+
+ A <<= 1;
+ if( F & Carry ) A |= 0x01;
+ F = F & ~(AddSub | Halfcarry | Carry);
+ if( a & 0x80 ) F |= Carry;
+}
+
+void opcode_18() // JR d
+{
+ relJump( fetchByte() );
+}
+
+void opcode_19() // ADD HL,DE
+{
+ unsigned hl = HL();
+ unsigned rp = DE();
+ unsigned x = hl + rp;
+
+ F &= Sign | Zero | Parity;
+ if( x > 0xFFFF ) F |= Carry;
+ if( ((hl & 0xFFF) + (rp & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+
+ L = x & 0xFF;
+ H = (x >> 8) & 0xFF;
+}
+
+void opcode_1a() // LD A,(DE)
+{
+ A = readByte( DE() );
+}
+
+void opcode_1b() // DEC DE
+{
+ if( E-- == 0 ) --D;
+}
+
+void opcode_1c() // INC E
+{
+ E = incByte( E );
+}
+
+void opcode_1d() // DEC E
+{
+ E = decByte( E );
+}
+
+void opcode_1e() // LD E,n
+{
+ E = fetchByte();
+}
+
+void opcode_1f() // RRA
+{
+ unsigned char a = A;
+
+ A >>= 1;
+ if( F & Carry ) A |= 0x80;
+ F = F & ~(AddSub | Halfcarry | Carry);
+ if( a & 0x01 ) F |= Carry;
+}
+
+void opcode_20() // JR NZ,d
+{
+ unsigned char o = fetchByte();
+
+ if( ! (F & Zero) ) relJump( o );
+}
+
+void opcode_21() // LD HL,nn
+{
+ L = fetchByte();
+ H = fetchByte();
+}
+
+void opcode_22() // LD (nn),HL
+{
+ unsigned x = fetchWord();
+
+ writeByte( x , L );
+ writeByte( x+1, H );
+}
+
+void opcode_23() // INC HL
+{
+ if( ++L == 0 ) ++H;
+}
+
+void opcode_24() // INC H
+{
+ H = incByte( H );
+}
+
+void opcode_25() // DEC H
+{
+ H = decByte( H );
+}
+
+void opcode_26() // LD H,n
+{
+ H = fetchByte();
+}
+
+/*
+ DAA is computed using the following table to get a diff value
+ that is added to or subtracted (according to the N flag) from A:
+
+ C Upper H Lower Diff
+ -+-----+-+-----+----
+ 1 * 0 0-9 60
+ 1 * 1 0-9 66
+ 1 * * A-F 66
+ 0 0-9 0 0-9 00
+ 0 0-9 1 0-9 06
+ 0 0-8 * A-F 06
+ 0 A-F 0 0-9 60
+ 0 9-F * A-F 66
+ 0 A-F 1 0-9 66
+
+ The carry and halfcarry flags are then updated using similar tables.
+
+ These tables were found by Stefano Donati of Ramsoft and are
+ published in the "Undocumented Z80 Documented" paper by Sean Young,
+ the following is an algorithmical implementation with no lookups.
+*/
+void opcode_27() // DAA
+{
+ unsigned char diff;
+ unsigned char hf = F & Halfcarry;
+ unsigned char cf = F & Carry;
+ unsigned char lower = A & 0x0F;
+
+ if( cf ) {
+ diff = (lower >= 0x0A) || hf ? 0x66 : 0x60;
+ }
+ else {
+ diff = (A >= 0x9A) ? 0x60 : 0x00;
+
+ if( hf || (lower >= 0x0A) ) diff += 0x06;
+ }
+
+ if( A >= 0x9A ) cf = Carry;
+
+ if( F & Subtraction ) {
+ A -= diff;
+ F = PSZ_[A] | Subtraction | cf;
+ if( hf && (lower <= 0x05) ) F |= Halfcarry;
+ }
+ else {
+ A += diff;
+ F = PSZ_[A] | cf;
+ if( lower >= 0x0A ) F |= Halfcarry;
+ }
+}
+
+void opcode_28() // JR Z,d
+{
+ unsigned char o = fetchByte();
+
+ if( F & Zero ) relJump( o );
+}
+
+void opcode_29() // ADD HL,HL
+{
+ unsigned hl = HL();
+ unsigned rp = hl;
+ unsigned x = hl + rp;
+
+ F &= Sign | Zero | Parity;
+ if( x > 0xFFFF ) F |= Carry;
+ if( ((hl & 0xFFF) + (rp & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+
+ L = x & 0xFF;
+ H = (x >> 8) & 0xFF;
+}
+
+void opcode_2a() // LD HL,(nn)
+{
+ unsigned x = fetchWord();
+
+ L = readByte( x );
+ H = readByte( x+1 );
+}
+
+void opcode_2b() // DEC HL
+{
+ if( L-- == 0 ) --H;
+}
+
+void opcode_2c() // INC L
+{
+ L = incByte( L );
+}
+
+void opcode_2d() // DEC L
+{
+ L = decByte( L );
+}
+
+void opcode_2e() // LD L,n
+{
+ L = fetchByte();
+}
+
+void opcode_2f() // CPL
+{
+ A ^= 0xFF;
+ F |= AddSub | Halfcarry;
+}
+
+void opcode_30() // JR NC,d
+{
+ unsigned char o = fetchByte();
+
+ if( ! (F & Carry) ) relJump( o );
+}
+
+void opcode_31() // LD SP,nn
+{
+ SP = fetchWord();
+}
+
+void opcode_32() // LD (nn),A
+{
+ writeByte( fetchWord(), A );
+}
+
+void opcode_33() // INC SP
+{
+ SP = (SP + 1) & 0xFFFF;
+}
+
+void opcode_34() // INC (HL)
+{
+ writeByte( HL(), incByte( readByte( HL() ) ) );
+}
+
+void opcode_35() // DEC (HL)
+{
+ writeByte( HL(), decByte( readByte( HL() ) ) );
+}
+
+void opcode_36() // LD (HL),n
+{
+ writeByte( HL(), fetchByte() );
+}
+
+void opcode_37() // SCF
+{
+ F = (F & (Parity | Sign | Zero)) | Carry;
+}
+
+void opcode_38() // JR C,d
+{
+ unsigned char o = fetchByte();
+
+ if( F & Carry ) relJump( o );
+}
+
+void opcode_39() // ADD HL,SP
+{
+ unsigned hl = HL();
+ unsigned rp = SP;
+ unsigned x = hl + rp;
+
+ F &= Sign | Zero | Parity;
+ if( x > 0xFFFF ) F |= Carry;
+ if( ((hl & 0xFFF) + (rp & 0xFFF)) > 0xFFF ) F |= Halfcarry;
+
+ L = x & 0xFF;
+ H = (x >> 8) & 0xFF;
+}
+
+void opcode_3a() // LD A,(nn)
+{
+ A = readByte( fetchWord() );
+}
+
+void opcode_3b() // DEC SP
+{
+ SP = (SP - 1) & 0xFFFF;
+}
+
+void opcode_3c() // INC A
+{
+ A = incByte( A );
+}
+
+void opcode_3d() // DEC A
+{
+ A = decByte( A );
+}
+
+void opcode_3e() // LD A,n
+{
+ A = fetchByte();
+}
+
+void opcode_3f() // CCF
+{
+ if( F & Carry ) {
+ F = (F & (Parity | Sign | Zero)) | Halfcarry; // Halfcarry holds previous carry
+ }
+ else {
+ F = (F & (Parity | Sign | Zero)) | Carry;
+ }
+}
+
+void opcode_40() // LD B,B
+{
+}
+
+void opcode_41() // LD B,C
+{
+ B = C;
+}
+
+void opcode_42() // LD B,D
+{
+ B = D;
+}
+
+void opcode_43() // LD B,E
+{
+ B = E;
+}
+
+void opcode_44() // LD B,H
+{
+ B = H;
+}
+
+void opcode_45() // LD B,L
+{
+ B = L;
+}
+
+void opcode_46() // LD B,(HL)
+{
+ B = readByte( HL() );
+}
+
+void opcode_47() // LD B,A
+{
+ B = A;
+}
+
+void opcode_48() // LD C,B
+{
+ C = B;
+}
+
+void opcode_49() // LD C,C
+{
+}
+
+void opcode_4a() // LD C,D
+{
+ C = D;
+}
+
+void opcode_4b() // LD C,E
+{
+ C = E;
+}
+
+void opcode_4c() // LD C,H
+{
+ C = H;
+}
+
+void opcode_4d() // LD C,L
+{
+ C = L;
+}
+
+void opcode_4e() // LD C,(HL)
+{
+ C = readByte( HL() );
+}
+
+void opcode_4f() // LD C,A
+{
+ C = A;
+}
+
+void opcode_50() // LD D,B
+{
+ D = B;
+}
+
+void opcode_51() // LD D,C
+{
+ D = C;
+}
+
+void opcode_52() // LD D,D
+{
+}
+
+void opcode_53() // LD D,E
+{
+ D = E;
+}
+
+void opcode_54() // LD D,H
+{
+ D = H;
+}
+
+void opcode_55() // LD D,L
+{
+ D = L;
+}
+
+void opcode_56() // LD D,(HL)
+{
+ D = readByte( HL() );
+}
+
+void opcode_57() // LD D,A
+{
+ D = A;
+}
+
+void opcode_58() // LD E,B
+{
+ E = B;
+}
+
+void opcode_59() // LD E,C
+{
+ E = C;
+}
+
+void opcode_5a() // LD E,D
+{
+ E = D;
+}
+
+void opcode_5b() // LD E,E
+{
+}
+
+void opcode_5c() // LD E,H
+{
+ E = H;
+}
+
+void opcode_5d() // LD E,L
+{
+ E = L;
+}
+
+void opcode_5e() // LD E,(HL)
+{
+ E = readByte( HL() );
+}
+
+void opcode_5f() // LD E,A
+{
+ E = A;
+}
+
+void opcode_60() // LD H,B
+{
+ H = B;
+}
+
+void opcode_61() // LD H,C
+{
+ H = C;
+}
+
+void opcode_62() // LD H,D
+{
+ H = D;
+}
+
+void opcode_63() // LD H,E
+{
+ H = E;
+}
+
+void opcode_64() // LD H,H
+{
+}
+
+void opcode_65() // LD H,L
+{
+ H = L;
+}
+
+void opcode_66() // LD H,(HL)
+{
+ H = readByte( HL() );
+}
+
+void opcode_67() // LD H,A
+{
+ H = A;
+}
+
+void opcode_68() // LD L,B
+{
+ L = B;
+}
+
+void opcode_69() // LD L,C
+{
+ L = C;
+}
+
+void opcode_6a() // LD L,D
+{
+ L = D;
+}
+
+void opcode_6b() // LD L,E
+{
+ L = E;
+}
+
+void opcode_6c() // LD L,H
+{
+ L = H;
+}
+
+void opcode_6d() // LD L,L
+{
+}
+
+void opcode_6e() // LD L,(HL)
+{
+ L = readByte( HL() );
+}
+
+void opcode_6f() // LD L,A
+{
+ L = A;
+}
+
+void opcode_70() // LD (HL),B
+{
+ writeByte( HL(), B );
+}
+
+void opcode_71() // LD (HL),C
+{
+ writeByte( HL(), C );
+}
+
+void opcode_72() // LD (HL),D
+{
+ writeByte( HL(), D );
+}
+
+void opcode_73() // LD (HL),E
+{
+ writeByte( HL(), E );
+}
+
+void opcode_74() // LD (HL),H
+{
+ writeByte( HL(), H );
+}
+
+void opcode_75() // LD (HL),L
+{
+ writeByte( HL(), L );
+}
+
+void opcode_76() // HALT
+{
+ iflags_ |= Halted;
+}
+
+void opcode_77() // LD (HL),A
+{
+ writeByte( HL(), A );
+}
+
+void opcode_78() // LD A,B
+{
+ A = B;
+}
+
+void opcode_79() // LD A,C
+{
+ A = C;
+}
+
+void opcode_7a() // LD A,D
+{
+ A = D;
+}
+
+void opcode_7b() // LD A,E
+{
+ A = E;
+}
+
+void opcode_7c() // LD A,H
+{
+ A = H;
+}
+
+void opcode_7d() // LD A,L
+{
+ A = L;
+}
+
+void opcode_7e() // LD A,(HL)
+{
+ A = readByte( HL() );
+}
+
+void opcode_7f() // LD A,A
+{
+}
+
+void opcode_80() // ADD A,B
+{
+ addByte( B, 0 );
+}
+
+void opcode_81() // ADD A,C
+{
+ addByte( C, 0 );
+}
+
+void opcode_82() // ADD A,D
+{
+ addByte( D, 0 );
+}
+
+void opcode_83() // ADD A,E
+{
+ addByte( E, 0 );
+}
+
+void opcode_84() // ADD A,H
+{
+ addByte( H, 0 );
+}
+
+void opcode_85() // ADD A,L
+{
+ addByte( L, 0 );
+}
+
+void opcode_86() // ADD A,(HL)
+{
+ addByte( readByte( HL() ), 0 );
+}
+
+void opcode_87() // ADD A,A
+{
+ addByte( A, 0 );
+}
+
+void opcode_88() // ADC A,B
+{
+ addByte( B, F & Carry );
+}
+
+void opcode_89() // ADC A,C
+{
+ addByte( C, F & Carry );
+}
+
+void opcode_8a() // ADC A,D
+{
+ addByte( D, F & Carry );
+}
+
+void opcode_8b() // ADC A,E
+{
+ addByte( E, F & Carry );
+}
+
+void opcode_8c() // ADC A,H
+{
+ addByte( H, F & Carry );
+}
+
+void opcode_8d() // ADC A,L
+{
+ addByte( L, F & Carry );
+}
+
+void opcode_8e() // ADC A,(HL)
+{
+ addByte( readByte( HL() ), F & Carry );
+}
+
+void opcode_8f() // ADC A,A
+{
+ addByte( A, F & Carry );
+}
+
+void opcode_90() // SUB B
+{
+ A = subByte( B, 0 );
+}
+
+void opcode_91() // SUB C
+{
+ A = subByte( C, 0 );
+}
+
+void opcode_92() // SUB D
+{
+ A = subByte( D, 0 );
+}
+
+void opcode_93() // SUB E
+{
+ A = subByte( E, 0 );
+}
+
+void opcode_94() // SUB H
+{
+ A = subByte( H, 0 );
+}
+
+void opcode_95() // SUB L
+{
+ A = subByte( L, 0 );
+}
+
+void opcode_96() // SUB (HL)
+{
+ A = subByte( readByte( HL() ), 0 );
+}
+
+void opcode_97() // SUB A
+{
+ A = subByte( A, 0 );
+}
+
+void opcode_98() // SBC A,B
+{
+ A = subByte( B, F & Carry );
+}
+
+void opcode_99() // SBC A,C
+{
+ A = subByte( C, F & Carry );
+}
+
+void opcode_9a() // SBC A,D
+{
+ A = subByte( D, F & Carry );
+}
+
+void opcode_9b() // SBC A,E
+{
+ A = subByte( E, F & Carry );
+}
+
+void opcode_9c() // SBC A,H
+{
+ A = subByte( H, F & Carry );
+}
+
+void opcode_9d() // SBC A,L
+{
+ A = subByte( L, F & Carry );
+}
+
+void opcode_9e() // SBC A,(HL)
+{
+ A = subByte( readByte( HL() ), F & Carry );
+}
+
+void opcode_9f() // SBC A,A
+{
+ A = subByte( A, F & Carry );
+}
+
+void opcode_a0() // AND B
+{
+ A &= B;
+ setFlagsPSZ();
+}
+
+void opcode_a1() // AND C
+{
+ A &= C;
+ setFlagsPSZ();
+}
+
+void opcode_a2() // AND D
+{
+ A &= D;
+ setFlagsPSZ();
+}
+
+void opcode_a3() // AND E
+{
+ A &= E;
+ setFlagsPSZ();
+}
+
+void opcode_a4() // AND H
+{
+ A &= H;
+ setFlagsPSZ();
+}
+
+void opcode_a5() // AND L
+{
+ A &= L;
+ setFlagsPSZ();
+}
+
+void opcode_a6() // AND (HL)
+{
+ A &= readByte( HL() );
+ setFlagsPSZ();
+}
+
+void opcode_a7() // AND A
+{
+ setFlagsPSZ();
+}
+
+void opcode_a8() // XOR B
+{
+ A ^= B;
+ setFlags35PSZ000();
+}
+
+void opcode_a9() // XOR C
+{
+ A ^= C;
+ setFlags35PSZ000();
+}
+
+void opcode_aa() // XOR D
+{
+ A ^= D;
+ setFlags35PSZ000();
+}
+
+void opcode_ab() // XOR E
+{
+ A ^= E;
+ setFlags35PSZ000();
+}
+
+void opcode_ac() // XOR H
+{
+ A ^= H;
+ setFlags35PSZ000();
+}
+
+void opcode_ad() // XOR L
+{
+ A ^= L;
+ setFlags35PSZ000();
+}
+
+void opcode_ae() // XOR (HL)
+{
+ A ^= readByte( HL() );
+ setFlags35PSZ000();
+}
+
+void opcode_af() // XOR A
+{
+ A = 0;
+ setFlags35PSZ000();
+}
+
+void opcode_b0() // OR B
+{
+ A |= B;
+ setFlags35PSZ000();
+}
+
+void opcode_b1() // OR C
+{
+ A |= C;
+ setFlags35PSZ000();
+}
+
+void opcode_b2() // OR D
+{
+ A |= D;
+ setFlags35PSZ000();
+}
+
+void opcode_b3() // OR E
+{
+ A |= E;
+ setFlags35PSZ000();
+}
+
+void opcode_b4() // OR H
+{
+ A |= H;
+ setFlags35PSZ000();
+}
+
+void opcode_b5() // OR L
+{
+ A |= L;
+ setFlags35PSZ000();
+}
+
+void opcode_b6() // OR (HL)
+{
+ A |= readByte( HL() );
+ setFlags35PSZ000();
+}
+
+void opcode_b7() // OR A
+{
+ setFlags35PSZ000();
+}
+
+void opcode_b8() // CP B
+{
+ cmpByte( B );
+}
+
+void opcode_b9() // CP C
+{
+ cmpByte( C );
+}
+
+void opcode_ba() // CP D
+{
+ cmpByte( D );
+}
+
+void opcode_bb() // CP E
+{
+ cmpByte( E );
+}
+
+void opcode_bc() // CP H
+{
+ cmpByte( H );
+}
+
+void opcode_bd() // CP L
+{
+ cmpByte( L );
+}
+
+void opcode_be() // CP (HL)
+{
+ cmpByte( readByte( HL() ) );
+}
+
+void opcode_bf() // CP A
+{
+ cmpByte( A );
+}
+
+void opcode_c0() // RET NZ
+{
+ if( ! (F & Zero) ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_c1() // POP BC
+{
+ C = readByte( SP++ );
+ B = readByte( SP++ );
+}
+
+void opcode_c2() // JP NZ,nn
+{
+ if( ! (F & Zero) )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_c3() // JP nn
+{
+ PC = readWord( PC );
+}
+
+void opcode_c4() // CALL NZ,nn
+{
+ if( ! (F & Zero) ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_c5() // PUSH BC
+{
+ writeByte( --SP, B );
+ writeByte( --SP, C );
+}
+
+void opcode_c6() // ADD A,n
+{
+ addByte( fetchByte(), 0 );
+}
+
+void opcode_c7() // RST 0
+{
+ callSub( 0x00 );
+}
+
+void opcode_c8() // RET Z
+{
+ if( F & Zero ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_c9() // RET
+{
+ retFromSub();
+}
+
+void opcode_ca() // JP Z,nn
+{
+ if( F & Zero )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_cb() // [Prefix]
+{
+ unsigned op = fetchByte();
+
+ cycles_ += OpInfoCB_[ op ].cycles;
+ OpInfoCB_[ op ].handler();
+}
+
+void opcode_cc() // CALL Z,nn
+{
+ if( F & Zero ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_cd() // CALL nn
+{
+ callSub( fetchWord() );
+}
+
+void opcode_ce() // ADC A,n
+{
+ addByte( fetchByte(), F & Carry );
+}
+
+void opcode_cf() // RST 8
+{
+ callSub( 0x08 );
+}
+
+void opcode_d0() // RET NC
+{
+ if( ! (F & Carry) ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_d1() // POP DE
+{
+ E = readByte( SP++ );
+ D = readByte( SP++ );
+}
+
+void opcode_d2() // JP NC,nn
+{
+ if( ! (F & Carry) )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_d3() // OUT (n),A
+{
+ writePort( fetchByte(), A );
+}
+
+void opcode_d4() // CALL NC,nn
+{
+ if( ! (F & Carry) ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_d5() // PUSH DE
+{
+ writeByte( --SP, D );
+ writeByte( --SP, E );
+}
+
+void opcode_d6() // SUB n
+{
+ A = subByte( fetchByte(), 0 );
+}
+
+void opcode_d7() // RST 10H
+{
+ callSub( 0x10 );
+}
+
+void opcode_d8() // RET C
+{
+ if( F & Carry ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_d9() // EXX
+{
+ unsigned char x;
+
+ x = B; B = B1; B1 = x;
+ x = C; C = C1; C1 = x;
+ x = D; D = D1; D1 = x;
+ x = E; E = E1; E1 = x;
+ x = H; H = H1; H1 = x;
+ x = L; L = L1; L1 = x;
+}
+
+void opcode_da() // JP C,nn
+{
+ if( F & Carry )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_db() // IN A,(n)
+{
+ A = readPort( fetchByte() );
+}
+
+void opcode_dc() // CALL C,nn
+{
+ if( F & Carry ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_dd() // [IX Prefix]
+{
+ do_opcode_xy( OpInfoDD_ );
+ IX &= 0xFFFF;
+}
+
+void opcode_de() // SBC A,n
+{
+ A = subByte( fetchByte(), F & Carry );
+}
+
+void opcode_df() // RST 18H
+{
+ callSub( 0x18 );
+}
+
+void opcode_e0() // RET PO
+{
+ if( ! (F & Parity) ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_e1() // POP HL
+{
+ L = readByte( SP++ );
+ H = readByte( SP++ );
+}
+
+void opcode_e2() // JP PO,nn
+{
+ if( ! (F & Parity) )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_e3() // EX (SP),HL
+{
+ unsigned char x;
+
+ x = readByte( SP ); writeByte( SP, L ); L = x;
+ x = readByte( SP+1 ); writeByte( SP+1, H ); H = x;
+}
+
+void opcode_e4() // CALL PO,nn
+{
+ if( ! (F & Parity) ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_e5() // PUSH HL
+{
+ writeByte( --SP, H );
+ writeByte( --SP, L );
+}
+
+void opcode_e6() // AND n
+{
+ A &= fetchByte();
+ setFlagsPSZ();
+}
+
+void opcode_e7() // RST 20H
+{
+ callSub( 0x20 );
+}
+
+void opcode_e8() // RET PE
+{
+ if( F & Parity ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_e9() // JP (HL)
+{
+ PC = HL();
+}
+
+void opcode_ea() // JP PE,nn
+{
+ if( F & Parity )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_eb() // EX DE,HL
+{
+ unsigned char x;
+
+ x = D; D = H; H = x;
+ x = E; E = L; L = x;
+}
+
+void opcode_ec() // CALL PE,nn
+{
+ if( F & Parity ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_ed() // [Prefix]
+{
+ unsigned op = fetchByte();
+
+ if( OpInfoED_[ op ].handler ) {
+ OpInfoED_[ op ].handler();
+ cycles_ += OpInfoED_[ op ].cycles;
+ }
+ else {
+ cycles_ += OpInfo_[ 0 ].cycles; // NOP
+ }
+}
+
+void opcode_ee() // XOR n
+{
+ A ^= fetchByte();
+ setFlags35PSZ000();
+}
+
+void opcode_ef() // RST 28H
+{
+ callSub( 0x28 );
+}
+
+void opcode_f0() // RET P
+{
+ if( ! (F & Sign) ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_f1() // POP AF
+{
+ F = readByte( SP++ );
+ A = readByte( SP++ );
+}
+
+void opcode_f2() // JP P,nn
+{
+ if( ! (F & Sign) )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_f3() // DI
+{
+ iflags_ &= ~(IFF1 | IFF2);
+}
+
+void opcode_f4() // CALL P,nn
+{
+ if( ! (F & Sign) ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_f5() // PUSH AF
+{
+ writeByte( --SP, A );
+ writeByte( --SP, F );
+}
+
+void opcode_f6() // OR n
+{
+ A |= fetchByte();
+ setFlags35PSZ000();
+}
+
+void opcode_f7() // RST 30H
+{
+ callSub( 0x30 );
+}
+
+void opcode_f8() // RET M
+{
+ if( F & Sign ) {
+ retFromSub();
+ cycles_ += 2;
+ }
+}
+
+void opcode_f9() // LD SP,HL
+{
+ SP = HL();
+}
+
+void opcode_fa() // JP M,nn
+{
+ if( F & Sign )
+ PC = fetchWord();
+ else
+ PC += 2;
+}
+
+void opcode_fb() // EI
+{
+ iflags_ |= IFF1 | IFF2;
+}
+
+void opcode_fc() // CALL M,nn
+{
+ if( F & Sign ) {
+ callSub( fetchWord() );
+ cycles_ += 2;
+ }
+ else {
+ PC += 2;
+ }
+}
+
+void opcode_fd() // [IY Prefix]
+{
+ do_opcode_xy( OpInfoFD_ );
+ IY &= 0xFFFF;
+}
+
+
+void opcode_fe() // CP n
+{
+ subByte( fetchByte(), 0 );
+}
+
+void opcode_ff() // RST 38H
+{
+ callSub( 0x38 );
+}
+
+
+/* Executes one instruction */
+void step(void)
+{
+ // Update memory refresh register (not strictly needed but...)
+ R = (R+1) & 0x7F;
+
+ if( iflags_ & Halted ) {
+ // CPU is halted, do a NOP instruction
+ cycles_ += OpInfo_[0].cycles; // NOP
+ }
+ else {
+ // Get the opcode to execute
+ unsigned op = fetchByte();
+
+ // Update the cycles counter with the number of cycles for this opcode
+ cycles_ += OpInfo_[ op ].cycles;
+
+ // Execute the opcode handler
+ OpInfo_[ op ].handler();
+
+ // Update registers
+ PC &= 0xFFFF; // Clip program counter
+ SP &= 0xFFFF; // Clip stack pointer
+ }
+}
+
+/*
+ Runs the CPU for the specified number of cycles.
+
+ Note: the memory refresh register is not updated!
+*/
+unsigned z80_run( unsigned runCycles )
+{
+ unsigned target_cycles = cycles_ + runCycles;
+
+ // Execute instructions until the specified number of
+ // cycles has elapsed
+ while( cycles_ < target_cycles ) {
+ if( iflags_ & Halted ) {
+ // CPU is halted, do NOPs for the rest of cycles
+ // (this may be off by a few cycles)
+ cycles_ = target_cycles;
+ }
+ else {
+ // Get the opcode to execute
+ unsigned op = fetchByte();
+
+ // Update the cycles counter with the number of cycles for this opcode
+ cycles_ += OpInfo_[ op ].cycles;
+
+ // Execute the opcode handler
+ OpInfo_[ op ].handler();
+ }
+ }
+
+ // Update registers
+ PC &= 0xFFFF; // Clip program counter
+ SP &= 0xFFFF; // Clip stack pointer
+
+ // Return the number of extra cycles executed
+ return cycles_ - target_cycles;
+}
+
+/* Interrupt */
+void z80_interrupt( unsigned char data )
+{
+ // Execute interrupt only if interrupts are enabled
+ if( iflags_ & IFF1 ) {
+ // Disable maskable interrupts and restart the CPU if halted
+ iflags_ &= ~(IFF1 | IFF2 | Halted);
+
+ switch( getInterruptMode() ) {
+ case 0:
+ OpInfo_[ data ].handler();
+ cycles_ += 11;
+ break;
+ case 1:
+ callSub( 0x38 );
+ cycles_ += 11;
+ break;
+ case 2:
+ callSub( readWord( ((unsigned)I) << 8 | (data & 0xFE) ) );
+ cycles_ += 19;
+ break;
+ }
+ }
+}
+
+/* Non-maskable interrupt */
+void nmi(void)
+{
+ // Disable maskable interrupts but preserve IFF2 (that is a copy of IFF1),
+ // also restart the CPU if halted
+ iflags_ &= ~(IFF1 | Halted);
+
+ callSub( 0x66 );
+
+ cycles_ += 11;
+}
+
+void do_opcode_xy( OpcodeInfo * info )
+{
+ unsigned op = fetchByte();
+
+ if( (op == 0xDD) || (op == 0xFD) ) {
+ // Exit now, to avoid possible infinite loops
+ PC--;
+ cycles_ += OpInfo_[ 0 ].cycles; // NOP
+ }
+ else if( op == 0xED ) {
+ // IX or IY prefix is ignored for this opcode
+ opcode_ed();
+ }
+ else {
+ // Handle IX or IY prefix if possible
+ if( info[ op ].handler ) {
+ // Extended opcode is valid
+ cycles_ += info[ op ].cycles;
+ info[ op ].handler();
+ }
+ else {
+ // Extended opcode not valid, fall back to standard opcode
+ cycles_ += OpInfo_[ op ].cycles;
+ OpInfo_[ op ].handler();
+ }
+ }
+}
+
diff --git a/apps/plugins/pacbox/z80.h b/apps/plugins/pacbox/z80.h
new file mode 100644
index 0000000..b628898
--- /dev/null
+++ b/apps/plugins/pacbox/z80.h
@@ -0,0 +1,160 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#ifndef Z80_H_
+#define Z80_H_
+
+/**
+ Environment for Z80 emulation.
+
+ This class implements all input/output functions for the Z80 emulator class,
+ that is it provides functions to access the system RAM, ROM and I/O ports.
+
+ An object of this class corresponds to a system that has no RAM, ROM or ports:
+ users of the Z80 emulator should provide the desired behaviour by writing a
+ descendant of this class.
+
+ @author Alessandro Scotti
+ @version 1.0
+*/
+
+ /** Sets the CPU cycle counter to the specified value. */
+void setCycles( unsigned value );
+
+void onReturnFromInterrupt(void);
+
+
+/**
+ Z80 software emulator.
+
+ @author Alessandro Scotti
+ @version 1.1
+*/
+ /** CPU flags */
+ enum {
+ Carry = 0x01, // C
+ AddSub = 0x02, Subtraction = AddSub, // N
+ Parity = 0x04, Overflow = Parity, // P/V, same bit used for parity and overflow
+ Flag3 = 0x08, // Aka XF, not used
+ Halfcarry = 0x10, // H
+ Flag5 = 0x20, // Aka YF, not used
+ Zero = 0x40, // Z
+ Sign = 0x80 // S
+ };
+
+ /**
+ Constructor: creates a Z80 object with the specified environment.
+ */
+// Z80( Z80Environment & );
+
+ /**
+ Copy constructor: creates a copy of the specified Z80 object.
+ */
+// Z80( const Z80 & );
+
+// /** Destructor. */
+// virtual ~Z80() {
+
+ /**
+ Resets the CPU to its initial state.
+
+ The stack pointer (SP) is set to F000h, all other registers are cleared.
+ */
+ void z80_reset(void);
+
+ /**
+ Runs the CPU for the specified number of cycles.
+
+ Note that the number of CPU cycles performed by this function may be
+ actually a little more than the value specified. If that happens then the
+ function returns the number of extra cycles executed.
+
+ @param cycles number of cycles the CPU must execute
+
+ @return the number of extra cycles executed by the last instruction
+ */
+ unsigned z80_run( unsigned cycles );
+
+ /**
+ Executes one instruction.
+ */
+ void z80_step(void);
+
+ /**
+ Invokes an interrupt.
+
+ If interrupts are enabled, the current program counter (PC) is saved on
+ the stack and assigned the specified address. When the interrupt handler
+ returns, execution resumes from the point where the interrupt occurred.
+
+ The actual interrupt address depends on the current interrupt mode and
+ on the interrupt type. For maskable interrupts, data is as follows:
+ - mode 0: data is an opcode that is executed (usually RST xxh);
+ - mode 1: data is ignored and a call is made to address 0x38;
+ - mode 2: a call is made to the 16 bit address given by (256*I + data).
+ */
+ void z80_interrupt( unsigned char data );
+
+ /** Forces a non-maskable interrupt. */
+ void z80_nmi(void);
+
+ /**
+ Copies CPU register from one object to another.
+
+ Note that the environment is not copied, only registers.
+ */
+// Z80 & operator = ( const Z80 & );
+
+ /** Returns the size of the buffer needed to take a snapshot of the CPU. */
+ unsigned getSizeOfSnapshotBuffer(void);
+
+ /**
+ Takes a snapshot of the CPU.
+
+ A snapshot saves all of the CPU registers and internals. It can be
+ restored at any time to bring the CPU back to the exact status it
+ had when the snapshot was taken.
+
+ Note: the size of the snapshot buffer must be no less than the size
+ returned by the getSizeOfSnapshotBuffer() function.
+
+ @param buffer buffer where the snapshot data is stored
+
+ @return the number of bytes written into the buffer
+ */
+ unsigned takeSnapshot( unsigned char * buffer );
+
+ /**
+ Restores a snapshot taken with takeSnapshot().
+
+ This function uses the data saved in the snapshot buffer to restore the
+ CPU status.
+
+ @param buffer buffer where the snapshot data is stored
+
+ @return the number of bytes read from the buffer
+ */
+ unsigned restoreSnapshot( unsigned char * buffer );
+
+#endif // Z80_H_
diff --git a/apps/plugins/pacbox/z80_internal.h b/apps/plugins/pacbox/z80_internal.h
new file mode 100644
index 0000000..4e45aa7
--- /dev/null
+++ b/apps/plugins/pacbox/z80_internal.h
@@ -0,0 +1,1062 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Pacbox - a Pacman Emulator for Rockbox
+ *
+ * Based on PIE - Pacman Instructional Emulator
+ *
+ * Copyright (c) 1997-2003,2004 Alessandro Scotti
+ * http://www.ascotti.org/
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#ifndef Z80_INTERNAL_H_
+#define Z80_INTERNAL_H_
+
+// Implementation of opcodes 0x00 to 0xFF
+void opcode_00(void); // NOP
+void opcode_01(void); // LD BC,nn
+void opcode_02(void); // LD (BC),A
+void opcode_03(void); // INC BC
+void opcode_04(void); // INC B
+void opcode_05(void); // DEC B
+void opcode_06(void); // LD B,n
+void opcode_07(void); // RLCA
+void opcode_08(void); // EX AF,AF'
+void opcode_09(void); // ADD HL,BC
+void opcode_0a(void); // LD A,(BC)
+void opcode_0b(void); // DEC BC
+void opcode_0c(void); // INC C
+void opcode_0d(void); // DEC C
+void opcode_0e(void); // LD C,n
+void opcode_0f(void); // RRCA
+void opcode_10(void); // DJNZ d
+void opcode_11(void); // LD DE,nn
+void opcode_12(void); // LD (DE),A
+void opcode_13(void); // INC DE
+void opcode_14(void); // INC D
+void opcode_15(void); // DEC D
+void opcode_16(void); // LD D,n
+void opcode_17(void); // RLA
+void opcode_18(void); // JR d
+void opcode_19(void); // ADD HL,DE
+void opcode_1a(void); // LD A,(DE)
+void opcode_1b(void); // DEC DE
+void opcode_1c(void); // INC E
+void opcode_1d(void); // DEC E
+void opcode_1e(void); // LD E,n
+void opcode_1f(void); // RRA
+void opcode_20(void); // JR NZ,d
+void opcode_21(void); // LD HL,nn
+void opcode_22(void); // LD (nn),HL
+void opcode_23(void); // INC HL
+void opcode_24(void); // INC H
+void opcode_25(void); // DEC H
+void opcode_26(void); // LD H,n
+void opcode_27(void); // DAA
+void opcode_28(void); // JR Z,d
+void opcode_29(void); // ADD HL,HL
+void opcode_2a(void); // LD HL,(nn)
+void opcode_2b(void); // DEC HL
+void opcode_2c(void); // INC L
+void opcode_2d(void); // DEC L
+void opcode_2e(void); // LD L,n
+void opcode_2f(void); // CPL
+void opcode_30(void); // JR NC,d
+void opcode_31(void); // LD SP,nn
+void opcode_32(void); // LD (nn),A
+void opcode_33(void); // INC SP
+void opcode_34(void); // INC (HL)
+void opcode_35(void); // DEC (HL)
+void opcode_36(void); // LD (HL),n
+void opcode_37(void); // SCF
+void opcode_38(void); // JR C,d
+void opcode_39(void); // ADD HL,SP
+void opcode_3a(void); // LD A,(nn)
+void opcode_3b(void); // DEC SP
+void opcode_3c(void); // INC A
+void opcode_3d(void); // DEC A
+void opcode_3e(void); // LD A,n
+void opcode_3f(void); // CCF
+void opcode_40(void); // LD B,B
+void opcode_41(void); // LD B,C
+void opcode_42(void); // LD B,D
+void opcode_43(void); // LD B,E
+void opcode_44(void); // LD B,H
+void opcode_45(void); // LD B,L
+void opcode_46(void); // LD B,(HL)
+void opcode_47(void); // LD B,A
+void opcode_48(void); // LD C,B
+void opcode_49(void); // LD C,C
+void opcode_4a(void); // LD C,D
+void opcode_4b(void); // LD C,E
+void opcode_4c(void); // LD C,H
+void opcode_4d(void); // LD C,L
+void opcode_4e(void); // LD C,(HL)
+void opcode_4f(void); // LD C,A
+void opcode_50(void); // LD D,B
+void opcode_51(void); // LD D,C
+void opcode_52(void); // LD D,D
+void opcode_53(void); // LD D,E
+void opcode_54(void); // LD D,H
+void opcode_55(void); // LD D,L
+void opcode_56(void); // LD D,(HL)
+void opcode_57(void); // LD D,A
+void opcode_58(void); // LD E,B
+void opcode_59(void); // LD E,C
+void opcode_5a(void); // LD E,D
+void opcode_5b(void); // LD E,E
+void opcode_5c(void); // LD E,H
+void opcode_5d(void); // LD E,L
+void opcode_5e(void); // LD E,(HL)
+void opcode_5f(void); // LD E,A
+void opcode_60(void); // LD H,B
+void opcode_61(void); // LD H,C
+void opcode_62(void); // LD H,D
+void opcode_63(void); // LD H,E
+void opcode_64(void); // LD H,H
+void opcode_65(void); // LD H,L
+void opcode_66(void); // LD H,(HL)
+void opcode_67(void); // LD H,A
+void opcode_68(void); // LD L,B
+void opcode_69(void); // LD L,C
+void opcode_6a(void); // LD L,D
+void opcode_6b(void); // LD L,E
+void opcode_6c(void); // LD L,H
+void opcode_6d(void); // LD L,L
+void opcode_6e(void); // LD L,(HL)
+void opcode_6f(void); // LD L,A
+void opcode_70(void); // LD (HL),B
+void opcode_71(void); // LD (HL),C
+void opcode_72(void); // LD (HL),D
+void opcode_73(void); // LD (HL),E
+void opcode_74(void); // LD (HL),H
+void opcode_75(void); // LD (HL),L
+void opcode_76(void); // HALT
+void opcode_77(void); // LD (HL),A
+void opcode_78(void); // LD A,B
+void opcode_79(void); // LD A,C
+void opcode_7a(void); // LD A,D
+void opcode_7b(void); // LD A,E
+void opcode_7c(void); // LD A,H
+void opcode_7d(void); // LD A,L
+void opcode_7e(void); // LD A,(HL)
+void opcode_7f(void); // LD A,A
+void opcode_80(void); // ADD A,B
+void opcode_81(void); // ADD A,C
+void opcode_82(void); // ADD A,D
+void opcode_83(void); // ADD A,E
+void opcode_84(void); // ADD A,H
+void opcode_85(void); // ADD A,L
+void opcode_86(void); // ADD A,(HL)
+void opcode_87(void); // ADD A,A
+void opcode_88(void); // ADC A,B
+void opcode_89(void); // ADC A,C
+void opcode_8a(void); // ADC A,D
+void opcode_8b(void); // ADC A,E
+void opcode_8c(void); // ADC A,H
+void opcode_8d(void); // ADC A,L
+void opcode_8e(void); // ADC A,(HL)
+void opcode_8f(void); // ADC A,A
+void opcode_90(void); // SUB B
+void opcode_91(void); // SUB C
+void opcode_92(void); // SUB D
+void opcode_93(void); // SUB E
+void opcode_94(void); // SUB H
+void opcode_95(void); // SUB L
+void opcode_96(void); // SUB (HL)
+void opcode_97(void); // SUB A
+void opcode_98(void); // SBC A,B
+void opcode_99(void); // SBC A,C
+void opcode_9a(void); // SBC A,D
+void opcode_9b(void); // SBC A,E
+void opcode_9c(void); // SBC A,H
+void opcode_9d(void); // SBC A,L
+void opcode_9e(void); // SBC A,(HL)
+void opcode_9f(void); // SBC A,A
+void opcode_a0(void); // AND B
+void opcode_a1(void); // AND C
+void opcode_a2(void); // AND D
+void opcode_a3(void); // AND E
+void opcode_a4(void); // AND H
+void opcode_a5(void); // AND L
+void opcode_a6(void); // AND (HL)
+void opcode_a7(void); // AND A
+void opcode_a8(void); // XOR B
+void opcode_a9(void); // XOR C
+void opcode_aa(void); // XOR D
+void opcode_ab(void); // XOR E
+void opcode_ac(void); // XOR H
+void opcode_ad(void); // XOR L
+void opcode_ae(void); // XOR (HL)
+void opcode_af(void); // XOR A
+void opcode_b0(void); // OR B
+void opcode_b1(void); // OR C
+void opcode_b2(void); // OR D
+void opcode_b3(void); // OR E
+void opcode_b4(void); // OR H
+void opcode_b5(void); // OR L
+void opcode_b6(void); // OR (HL)
+void opcode_b7(void); // OR A
+void opcode_b8(void); // CP B
+void opcode_b9(void); // CP C
+void opcode_ba(void); // CP D
+void opcode_bb(void); // CP E
+void opcode_bc(void); // CP H
+void opcode_bd(void); // CP L
+void opcode_be(void); // CP (HL)
+void opcode_bf(void); // CP A
+void opcode_c0(void); // RET NZ
+void opcode_c1(void); // POP BC
+void opcode_c2(void); // JP NZ,nn
+void opcode_c3(void); // JP nn
+void opcode_c4(void); // CALL NZ,nn
+void opcode_c5(void); // PUSH BC
+void opcode_c6(void); // ADD A,n
+void opcode_c7(void); // RST 0
+void opcode_c8(void); // RET Z
+void opcode_c9(void); // RET
+void opcode_ca(void); // JP Z,nn
+void opcode_cb(void); // [Prefix]
+void opcode_cc(void); // CALL Z,nn
+void opcode_cd(void); // CALL nn
+void opcode_ce(void); // ADC A,n
+void opcode_cf(void); // RST 8
+void opcode_d0(void); // RET NC
+void opcode_d1(void); // POP DE
+void opcode_d2(void); // JP NC,nn
+void opcode_d3(void); // OUT (n),A
+void opcode_d4(void); // CALL NC,nn
+void opcode_d5(void); // PUSH DE
+void opcode_d6(void); // SUB n
+void opcode_d7(void); // RST 10H
+void opcode_d8(void); // RET C
+void opcode_d9(void); // EXX
+void opcode_da(void); // JP C,nn
+void opcode_db(void); // IN A,(n)
+void opcode_dc(void); // CALL C,nn
+void opcode_dd(void); // [IX Prefix]
+void opcode_de(void); // SBC A,n
+void opcode_df(void); // RST 18H
+void opcode_e0(void); // RET PO
+void opcode_e1(void); // POP HL
+void opcode_e2(void); // JP PO,nn
+void opcode_e3(void); // EX (SP),HL
+void opcode_e4(void); // CALL PO,nn
+void opcode_e5(void); // PUSH HL
+void opcode_e6(void); // AND n
+void opcode_e7(void); // RST 20H
+void opcode_e8(void); // RET PE
+void opcode_e9(void); // JP (HL)
+void opcode_ea(void); // JP PE,nn
+void opcode_eb(void); // EX DE,HL
+void opcode_ec(void); // CALL PE,nn
+void opcode_ed(void); // [Prefix]
+void opcode_ee(void); // XOR n
+void opcode_ef(void); // RST 28H
+void opcode_f0(void); // RET P
+void opcode_f1(void); // POP AF
+void opcode_f2(void); // JP P,nn
+void opcode_f3(void); // DI
+void opcode_f4(void); // CALL P,nn
+void opcode_f5(void); // PUSH AF
+void opcode_f6(void); // OR n
+void opcode_f7(void); // RST 30H
+void opcode_f8(void); // RET M
+void opcode_f9(void); // LD SP,HL
+void opcode_fa(void); // JP M,nn
+void opcode_fb(void); // EI
+void opcode_fc(void); // CALL M,nn
+void opcode_fd(void); // [IY Prefix]
+void opcode_fe(void); // CP n
+void opcode_ff(void); // RST 38H
+
+// Handlers for the 0xCB prefix
+void opcode_cb_00(void); // RLC B
+void opcode_cb_01(void); // RLC C
+void opcode_cb_02(void); // RLC D
+void opcode_cb_03(void); // RLC E
+void opcode_cb_04(void); // RLC H
+void opcode_cb_05(void); // RLC L
+void opcode_cb_06(void); // RLC (HL)
+void opcode_cb_07(void); // RLC A
+void opcode_cb_08(void); // RRC B
+void opcode_cb_09(void); // RRC C
+void opcode_cb_0a(void); // RRC D
+void opcode_cb_0b(void); // RRC E
+void opcode_cb_0c(void); // RRC H
+void opcode_cb_0d(void); // RRC L
+void opcode_cb_0e(void); // RRC (HL)
+void opcode_cb_0f(void); // RRC A
+void opcode_cb_10(void); // RL B
+void opcode_cb_11(void); // RL C
+void opcode_cb_12(void); // RL D
+void opcode_cb_13(void); // RL E
+void opcode_cb_14(void); // RL H
+void opcode_cb_15(void); // RL L
+void opcode_cb_16(void); // RL (HL)
+void opcode_cb_17(void); // RL A
+void opcode_cb_18(void); // RR B
+void opcode_cb_19(void); // RR C
+void opcode_cb_1a(void); // RR D
+void opcode_cb_1b(void); // RR E
+void opcode_cb_1c(void); // RR H
+void opcode_cb_1d(void); // RR L
+void opcode_cb_1e(void); // RR (HL)
+void opcode_cb_1f(void); // RR A
+void opcode_cb_20(void); // SLA B
+void opcode_cb_21(void); // SLA C
+void opcode_cb_22(void); // SLA D
+void opcode_cb_23(void); // SLA E
+void opcode_cb_24(void); // SLA H
+void opcode_cb_25(void); // SLA L
+void opcode_cb_26(void); // SLA (HL)
+void opcode_cb_27(void); // SLA A
+void opcode_cb_28(void); // SRA B
+void opcode_cb_29(void); // SRA C
+void opcode_cb_2a(void); // SRA D
+void opcode_cb_2b(void); // SRA E
+void opcode_cb_2c(void); // SRA H
+void opcode_cb_2d(void); // SRA L
+void opcode_cb_2e(void); // SRA (HL)
+void opcode_cb_2f(void); // SRA A
+void opcode_cb_30(void); // SLL B [undocumented]
+void opcode_cb_31(void); // SLL C [undocumented]
+void opcode_cb_32(void); // SLL D [undocumented]
+void opcode_cb_33(void); // SLL E [undocumented]
+void opcode_cb_34(void); // SLL H [undocumented]
+void opcode_cb_35(void); // SLL L [undocumented]
+void opcode_cb_36(void); // SLL (HL) [undocumented]
+void opcode_cb_37(void); // SLL A [undocumented]
+void opcode_cb_38(void); // SRL B
+void opcode_cb_39(void); // SRL C
+void opcode_cb_3a(void); // SRL D
+void opcode_cb_3b(void); // SRL E
+void opcode_cb_3c(void); // SRL H
+void opcode_cb_3d(void); // SRL L
+void opcode_cb_3e(void); // SRL (HL)
+void opcode_cb_3f(void); // SRL A
+void opcode_cb_40(void); // BIT 0, B
+void opcode_cb_41(void); // BIT 0, C
+void opcode_cb_42(void); // BIT 0, D
+void opcode_cb_43(void); // BIT 0, E
+void opcode_cb_44(void); // BIT 0, H
+void opcode_cb_45(void); // BIT 0, L
+void opcode_cb_46(void); // BIT 0, (HL)
+void opcode_cb_47(void); // BIT 0, A
+void opcode_cb_48(void); // BIT 1, B
+void opcode_cb_49(void); // BIT 1, C
+void opcode_cb_4a(void); // BIT 1, D
+void opcode_cb_4b(void); // BIT 1, E
+void opcode_cb_4c(void); // BIT 1, H
+void opcode_cb_4d(void); // BIT 1, L
+void opcode_cb_4e(void); // BIT 1, (HL)
+void opcode_cb_4f(void); // BIT 1, A
+void opcode_cb_50(void); // BIT 2, B
+void opcode_cb_51(void); // BIT 2, C
+void opcode_cb_52(void); // BIT 2, D
+void opcode_cb_53(void); // BIT 2, E
+void opcode_cb_54(void); // BIT 2, H
+void opcode_cb_55(void); // BIT 2, L
+void opcode_cb_56(void); // BIT 2, (HL)
+void opcode_cb_57(void); // BIT 2, A
+void opcode_cb_58(void); // BIT 3, B
+void opcode_cb_59(void); // BIT 3, C
+void opcode_cb_5a(void); // BIT 3, D
+void opcode_cb_5b(void); // BIT 3, E
+void opcode_cb_5c(void); // BIT 3, H
+void opcode_cb_5d(void); // BIT 3, L
+void opcode_cb_5e(void); // BIT 3, (HL)
+void opcode_cb_5f(void); // BIT 3, A
+void opcode_cb_60(void); // BIT 4, B
+void opcode_cb_61(void); // BIT 4, C
+void opcode_cb_62(void); // BIT 4, D
+void opcode_cb_63(void); // BIT 4, E
+void opcode_cb_64(void); // BIT 4, H
+void opcode_cb_65(void); // BIT 4, L
+void opcode_cb_66(void); // BIT 4, (HL)
+void opcode_cb_67(void); // BIT 4, A
+void opcode_cb_68(void); // BIT 5, B
+void opcode_cb_69(void); // BIT 5, C
+void opcode_cb_6a(void); // BIT 5, D
+void opcode_cb_6b(void); // BIT 5, E
+void opcode_cb_6c(void); // BIT 5, H
+void opcode_cb_6d(void); // BIT 5, L
+void opcode_cb_6e(void); // BIT 5, (HL)
+void opcode_cb_6f(void); // BIT 5, A
+void opcode_cb_70(void); // BIT 6, B
+void opcode_cb_71(void); // BIT 6, C
+void opcode_cb_72(void); // BIT 6, D
+void opcode_cb_73(void); // BIT 6, E
+void opcode_cb_74(void); // BIT 6, H
+void opcode_cb_75(void); // BIT 6, L
+void opcode_cb_76(void); // BIT 6, (HL)
+void opcode_cb_77(void); // BIT 6, A
+void opcode_cb_78(void); // BIT 7, B
+void opcode_cb_79(void); // BIT 7, C
+void opcode_cb_7a(void); // BIT 7, D
+void opcode_cb_7b(void); // BIT 7, E
+void opcode_cb_7c(void); // BIT 7, H
+void opcode_cb_7d(void); // BIT 7, L
+void opcode_cb_7e(void); // BIT 7, (HL)
+void opcode_cb_7f(void); // BIT 7, A
+void opcode_cb_80(void); // RES 0, B
+void opcode_cb_81(void); // RES 0, C
+void opcode_cb_82(void); // RES 0, D
+void opcode_cb_83(void); // RES 0, E
+void opcode_cb_84(void); // RES 0, H
+void opcode_cb_85(void); // RES 0, L
+void opcode_cb_86(void); // RES 0, (HL)
+void opcode_cb_87(void); // RES 0, A
+void opcode_cb_88(void); // RES 1, B
+void opcode_cb_89(void); // RES 1, C
+void opcode_cb_8a(void); // RES 1, D
+void opcode_cb_8b(void); // RES 1, E
+void opcode_cb_8c(void); // RES 1, H
+void opcode_cb_8d(void); // RES 1, L
+void opcode_cb_8e(void); // RES 1, (HL)
+void opcode_cb_8f(void); // RES 1, A
+void opcode_cb_90(void); // RES 2, B
+void opcode_cb_91(void); // RES 2, C
+void opcode_cb_92(void); // RES 2, D
+void opcode_cb_93(void); // RES 2, E
+void opcode_cb_94(void); // RES 2, H
+void opcode_cb_95(void); // RES 2, L
+void opcode_cb_96(void); // RES 2, (HL)
+void opcode_cb_97(void); // RES 2, A
+void opcode_cb_98(void); // RES 3, B
+void opcode_cb_99(void); // RES 3, C
+void opcode_cb_9a(void); // RES 3, D
+void opcode_cb_9b(void); // RES 3, E
+void opcode_cb_9c(void); // RES 3, H
+void opcode_cb_9d(void); // RES 3, L
+void opcode_cb_9e(void); // RES 3, (HL)
+void opcode_cb_9f(void); // RES 3, A
+void opcode_cb_a0(void); // RES 4, B
+void opcode_cb_a1(void); // RES 4, C
+void opcode_cb_a2(void); // RES 4, D
+void opcode_cb_a3(void); // RES 4, E
+void opcode_cb_a4(void); // RES 4, H
+void opcode_cb_a5(void); // RES 4, L
+void opcode_cb_a6(void); // RES 4, (HL)
+void opcode_cb_a7(void); // RES 4, A
+void opcode_cb_a8(void); // RES 5, B
+void opcode_cb_a9(void); // RES 5, C
+void opcode_cb_aa(void); // RES 5, D
+void opcode_cb_ab(void); // RES 5, E
+void opcode_cb_ac(void); // RES 5, H
+void opcode_cb_ad(void); // RES 5, L
+void opcode_cb_ae(void); // RES 5, (HL)
+void opcode_cb_af(void); // RES 5, A
+void opcode_cb_b0(void); // RES 6, B
+void opcode_cb_b1(void); // RES 6, C
+void opcode_cb_b2(void); // RES 6, D
+void opcode_cb_b3(void); // RES 6, E
+void opcode_cb_b4(void); // RES 6, H
+void opcode_cb_b5(void); // RES 6, L
+void opcode_cb_b6(void); // RES 6, (HL)
+void opcode_cb_b7(void); // RES 6, A
+void opcode_cb_b8(void); // RES 7, B
+void opcode_cb_b9(void); // RES 7, C
+void opcode_cb_ba(void); // RES 7, D
+void opcode_cb_bb(void); // RES 7, E
+void opcode_cb_bc(void); // RES 7, H
+void opcode_cb_bd(void); // RES 7, L
+void opcode_cb_be(void); // RES 7, (HL)
+void opcode_cb_bf(void); // RES 7, A
+void opcode_cb_c0(void); // SET 0, B
+void opcode_cb_c1(void); // SET 0, C
+void opcode_cb_c2(void); // SET 0, D
+void opcode_cb_c3(void); // SET 0, E
+void opcode_cb_c4(void); // SET 0, H
+void opcode_cb_c5(void); // SET 0, L
+void opcode_cb_c6(void); // SET 0, (HL)
+void opcode_cb_c7(void); // SET 0, A
+void opcode_cb_c8(void); // SET 1, B
+void opcode_cb_c9(void); // SET 1, C
+void opcode_cb_ca(void); // SET 1, D
+void opcode_cb_cb(void); // SET 1, E
+void opcode_cb_cc(void); // SET 1, H
+void opcode_cb_cd(void); // SET 1, L
+void opcode_cb_ce(void); // SET 1, (HL)
+void opcode_cb_cf(void); // SET 1, A
+void opcode_cb_d0(void); // SET 2, B
+void opcode_cb_d1(void); // SET 2, C
+void opcode_cb_d2(void); // SET 2, D
+void opcode_cb_d3(void); // SET 2, E
+void opcode_cb_d4(void); // SET 2, H
+void opcode_cb_d5(void); // SET 2, L
+void opcode_cb_d6(void); // SET 2, (HL)
+void opcode_cb_d7(void); // SET 2, A
+void opcode_cb_d8(void); // SET 3, B
+void opcode_cb_d9(void); // SET 3, C
+void opcode_cb_da(void); // SET 3, D
+void opcode_cb_db(void); // SET 3, E
+void opcode_cb_dc(void); // SET 3, H
+void opcode_cb_dd(void); // SET 3, L
+void opcode_cb_de(void); // SET 3, (HL)
+void opcode_cb_df(void); // SET 3, A
+void opcode_cb_e0(void); // SET 4, B
+void opcode_cb_e1(void); // SET 4, C
+void opcode_cb_e2(void); // SET 4, D
+void opcode_cb_e3(void); // SET 4, E
+void opcode_cb_e4(void); // SET 4, H
+void opcode_cb_e5(void); // SET 4, L
+void opcode_cb_e6(void); // SET 4, (HL)
+void opcode_cb_e7(void); // SET 4, A
+void opcode_cb_e8(void); // SET 5, B
+void opcode_cb_e9(void); // SET 5, C
+void opcode_cb_ea(void); // SET 5, D
+void opcode_cb_eb(void); // SET 5, E
+void opcode_cb_ec(void); // SET 5, H
+void opcode_cb_ed(void); // SET 5, L
+void opcode_cb_ee(void); // SET 5, (HL)
+void opcode_cb_ef(void); // SET 5, A
+void opcode_cb_f0(void); // SET 6, B
+void opcode_cb_f1(void); // SET 6, C
+void opcode_cb_f2(void); // SET 6, D
+void opcode_cb_f3(void); // SET 6, E
+void opcode_cb_f4(void); // SET 6, H
+void opcode_cb_f5(void); // SET 6, L
+void opcode_cb_f6(void); // SET 6, (HL)
+void opcode_cb_f7(void); // SET 6, A
+void opcode_cb_f8(void); // SET 7, B
+void opcode_cb_f9(void); // SET 7, C
+void opcode_cb_fa(void); // SET 7, D
+void opcode_cb_fb(void); // SET 7, E
+void opcode_cb_fc(void); // SET 7, H
+void opcode_cb_fd(void); // SET 7, L
+void opcode_cb_fe(void); // SET 7, (HL)
+void opcode_cb_ff(void); // SET 7, A
+
+// Handlers for the 0xED prefix
+void opcode_ed_40(void); // IN B, (C)
+void opcode_ed_41(void); // OUT (C), B
+void opcode_ed_42(void); // SBC HL, BC
+void opcode_ed_43(void); // LD (nn), BC
+void opcode_ed_44(void); // NEG
+void opcode_ed_45(void); // RETN
+void opcode_ed_46(void); // IM 0
+void opcode_ed_47(void); // LD I, A
+void opcode_ed_48(void); // IN C, (C)
+void opcode_ed_49(void); // OUT (C), C
+void opcode_ed_4a(void); // ADC HL, BC
+void opcode_ed_4b(void); // LD BC, (nn)
+void opcode_ed_4c(void); // NEG [undocumented]
+void opcode_ed_4d(void); // RETI
+void opcode_ed_4e(void); // IM 0/1 [undocumented]
+void opcode_ed_4f(void); // LD R, A
+void opcode_ed_50(void); // IN D, (C)
+void opcode_ed_51(void); // OUT (C), D
+void opcode_ed_52(void); // SBC HL, DE
+void opcode_ed_53(void); // LD (nn), DE
+void opcode_ed_54(void); // NEG [undocumented]
+void opcode_ed_55(void); // RETN [undocumented]
+void opcode_ed_56(void); // IM 1
+void opcode_ed_57(void); // LD A, I
+void opcode_ed_58(void); // IN E, (C)
+void opcode_ed_59(void); // OUT (C), E
+void opcode_ed_5a(void); // ADC HL, DE
+void opcode_ed_5b(void); // LD DE, (nn)
+void opcode_ed_5c(void); // NEG [undocumented]
+void opcode_ed_5d(void); // RETN [undocumented]
+void opcode_ed_5e(void); // IM 2
+void opcode_ed_5f(void); // LD A, R
+void opcode_ed_60(void); // IN H, (C)
+void opcode_ed_61(void); // OUT (C), H
+void opcode_ed_62(void); // SBC HL, HL
+void opcode_ed_63(void); // LD (nn), HL
+void opcode_ed_64(void); // NEG [undocumented]
+void opcode_ed_65(void); // RETN [undocumented]
+void opcode_ed_66(void); // IM 0 [undocumented]
+void opcode_ed_67(void); // RRD
+void opcode_ed_68(void); // IN L, (C)
+void opcode_ed_69(void); // OUT (C), L
+void opcode_ed_6a(void); // ADC HL, HL
+void opcode_ed_6b(void); // LD HL, (nn)
+void opcode_ed_6c(void); // NEG [undocumented]
+void opcode_ed_6d(void); // RETN [undocumented]
+void opcode_ed_6e(void); // IM 0/1 [undocumented]
+void opcode_ed_6f(void); // RLD
+void opcode_ed_70(void); // IN (C)/IN F, (C) [undocumented]
+void opcode_ed_71(void); // OUT (C), 0 [undocumented]
+void opcode_ed_72(void); // SBC HL, SP
+void opcode_ed_73(void); // LD (nn), SP
+void opcode_ed_74(void); // NEG [undocumented]
+void opcode_ed_75(void); // RETN [undocumented]
+void opcode_ed_76(void); // IM 1 [undocumented]
+void opcode_ed_78(void); // IN A, (C)
+void opcode_ed_79(void); // OUT (C), A
+void opcode_ed_7a(void); // ADC HL, SP
+void opcode_ed_7b(void); // nLD SP, (nn)
+void opcode_ed_7c(void); // NEG [undocumented]
+void opcode_ed_7d(void); // RETN [undocumented]
+void opcode_ed_7e(void); // IM 2 [undocumented]
+void opcode_ed_a0(void); // LDI
+void opcode_ed_a1(void); // CPI
+void opcode_ed_a2(void); // INI
+void opcode_ed_a3(void); // OUTI
+void opcode_ed_a8(void); // LDD
+void opcode_ed_a9(void); // CPD
+void opcode_ed_aa(void); // IND
+void opcode_ed_ab(void); // OUTD
+void opcode_ed_b0(void); // LDIR
+void opcode_ed_b1(void); // CPIR
+void opcode_ed_b2(void); // INIR
+void opcode_ed_b3(void); // OTIR
+void opcode_ed_b8(void); // LDDR
+void opcode_ed_b9(void); // CPDR
+void opcode_ed_ba(void); // INDR
+void opcode_ed_bb(void); // OTDR
+
+// Handlers for the 0xDD prefix (IX)
+void opcode_dd_09(void); // ADD IX, BC
+void opcode_dd_19(void); // ADD IX, DE
+void opcode_dd_21(void); // LD IX, nn
+void opcode_dd_22(void); // LD (nn), IX
+void opcode_dd_23(void); // INC IX
+void opcode_dd_24(void); // INC IXH [undocumented]
+void opcode_dd_25(void); // DEC IXH [undocumented]
+void opcode_dd_26(void); // LD IXH, n [undocumented]
+void opcode_dd_29(void); // ADD IX, IX
+void opcode_dd_2a(void); // LD IX, (nn)
+void opcode_dd_2b(void); // DEC IX
+void opcode_dd_2c(void); // INC IXL [undocumented]
+void opcode_dd_2d(void); // DEC IXL [undocumented]
+void opcode_dd_2e(void); // LD IXL, n [undocumented]
+void opcode_dd_34(void); // INC (IX + d)
+void opcode_dd_35(void); // DEC (IX + d)
+void opcode_dd_36(void); // LD (IX + d), n
+void opcode_dd_39(void); // ADD IX, SP
+void opcode_dd_44(void); // LD B, IXH [undocumented]
+void opcode_dd_45(void); // LD B, IXL [undocumented]
+void opcode_dd_46(void); // LD B, (IX + d)
+void opcode_dd_4c(void); // LD C, IXH [undocumented]
+void opcode_dd_4d(void); // LD C, IXL [undocumented]
+void opcode_dd_4e(void); // LD C, (IX + d)
+void opcode_dd_54(void); // LD D, IXH [undocumented]
+void opcode_dd_55(void); // LD D, IXL [undocumented]
+void opcode_dd_56(void); // LD D, (IX + d)
+void opcode_dd_5c(void); // LD E, IXH [undocumented]
+void opcode_dd_5d(void); // LD E, IXL [undocumented]
+void opcode_dd_5e(void); // LD E, (IX + d)
+void opcode_dd_60(void); // LD IXH, B [undocumented]
+void opcode_dd_61(void); // LD IXH, C [undocumented]
+void opcode_dd_62(void); // LD IXH, D [undocumented]
+void opcode_dd_63(void); // LD IXH, E [undocumented]
+void opcode_dd_64(void); // LD IXH, IXH [undocumented]
+void opcode_dd_65(void); // LD IXH, IXL [undocumented]
+void opcode_dd_66(void); // LD H, (IX + d)
+void opcode_dd_67(void); // LD IXH, A [undocumented]
+void opcode_dd_68(void); // LD IXL, B [undocumented]
+void opcode_dd_69(void); // LD IXL, C [undocumented]
+void opcode_dd_6a(void); // LD IXL, D [undocumented]
+void opcode_dd_6b(void); // LD IXL, E [undocumented]
+void opcode_dd_6c(void); // LD IXL, IXH [undocumented]
+void opcode_dd_6d(void); // LD IXL, IXL [undocumented]
+void opcode_dd_6e(void); // LD L, (IX + d)
+void opcode_dd_6f(void); // LD IXL, A [undocumented]
+void opcode_dd_70(void); // LD (IX + d), B
+void opcode_dd_71(void); // LD (IX + d), C
+void opcode_dd_72(void); // LD (IX + d), D
+void opcode_dd_73(void); // LD (IX + d), E
+void opcode_dd_74(void); // LD (IX + d), H
+void opcode_dd_75(void); // LD (IX + d), L
+void opcode_dd_77(void); // LD (IX + d), A
+void opcode_dd_7c(void); // LD A, IXH [undocumented]
+void opcode_dd_7d(void); // LD A, IXL [undocumented]
+void opcode_dd_7e(void); // LD A, (IX + d)
+void opcode_dd_84(void); // ADD A, IXH [undocumented]
+void opcode_dd_85(void); // ADD A, IXL [undocumented]
+void opcode_dd_86(void); // ADD A, (IX + d)
+void opcode_dd_8c(void); // ADC A, IXH [undocumented]
+void opcode_dd_8d(void); // ADC A, IXL [undocumented]
+void opcode_dd_8e(void); // ADC A, (IX + d)
+void opcode_dd_94(void); // SUB IXH [undocumented]
+void opcode_dd_95(void); // SUB IXL [undocumented]
+void opcode_dd_96(void); // SUB (IX + d)
+void opcode_dd_9c(void); // SBC A, IXH [undocumented]
+void opcode_dd_9d(void); // SBC A, IXL [undocumented]
+void opcode_dd_9e(void); // SBC A, (IX + d)
+void opcode_dd_a4(void); // AND IXH [undocumented]
+void opcode_dd_a5(void); // AND IXL [undocumented]
+void opcode_dd_a6(void); // AND (IX + d)
+void opcode_dd_ac(void); // XOR IXH [undocumented]
+void opcode_dd_ad(void); // XOR IXL [undocumented]
+void opcode_dd_ae(void); // XOR (IX + d)
+void opcode_dd_b4(void); // OR IXH [undocumented]
+void opcode_dd_b5(void); // OR IXL [undocumented]
+void opcode_dd_b6(void); // OR (IX + d)
+void opcode_dd_bc(void); // CP IXH [undocumented]
+void opcode_dd_bd(void); // CP IXL [undocumented]
+void opcode_dd_be(void); // CP (IX + d)
+void opcode_dd_cb(void); //
+void opcode_dd_e1(void); // POP IX
+void opcode_dd_e3(void); // EX (SP), IX
+void opcode_dd_e5(void); // PUSH IX
+void opcode_dd_e9(void); // JP (IX)
+void opcode_dd_f9(void); // LD SP, IX
+
+// Handlers for the 0xFD prefix (IY)
+void opcode_fd_09(void); // ADD IY, BC
+void opcode_fd_19(void); // ADD IY, DE
+void opcode_fd_21(void); // LD IY, nn
+void opcode_fd_22(void); // LD (nn), IY
+void opcode_fd_23(void); // INC IY
+void opcode_fd_24(void); // INC IYH [undocumented]
+void opcode_fd_25(void); // DEC IYH [undocumented]
+void opcode_fd_26(void); // LD IYH, n [undocumented]
+void opcode_fd_29(void); // ADD IY, IY
+void opcode_fd_2a(void); // LD IY, (nn)
+void opcode_fd_2b(void); // DEC IY
+void opcode_fd_2c(void); // INC IYL [undocumented]
+void opcode_fd_2d(void); // DEC IYL [undocumented]
+void opcode_fd_2e(void); // LD IYL, n [undocumented]
+void opcode_fd_34(void); // INC (IY + d)
+void opcode_fd_35(void); // DEC (IY + d)
+void opcode_fd_36(void); // LD (IY + d), n
+void opcode_fd_39(void); // ADD IY, SP
+void opcode_fd_44(void); // LD B, IYH [undocumented]
+void opcode_fd_45(void); // LD B, IYL [undocumented]
+void opcode_fd_46(void); // LD B, (IY + d)
+void opcode_fd_4c(void); // LD C, IYH [undocumented]
+void opcode_fd_4d(void); // LD C, IYL [undocumented]
+void opcode_fd_4e(void); // LD C, (IY + d)
+void opcode_fd_54(void); // LD D, IYH [undocumented]
+void opcode_fd_55(void); // LD D, IYL [undocumented]
+void opcode_fd_56(void); // LD D, (IY + d)
+void opcode_fd_5c(void); // LD E, IYH [undocumented]
+void opcode_fd_5d(void); // LD E, IYL [undocumented]
+void opcode_fd_5e(void); // LD E, (IY + d)
+void opcode_fd_60(void); // LD IYH, B [undocumented]
+void opcode_fd_61(void); // LD IYH, C [undocumented]
+void opcode_fd_62(void); // LD IYH, D [undocumented]
+void opcode_fd_63(void); // LD IYH, E [undocumented]
+void opcode_fd_64(void); // LD IYH, IYH [undocumented]
+void opcode_fd_65(void); // LD IYH, IYL [undocumented]
+void opcode_fd_66(void); // LD H, (IY + d)
+void opcode_fd_67(void); // LD IYH, A [undocumented]
+void opcode_fd_68(void); // LD IYL, B [undocumented]
+void opcode_fd_69(void); // LD IYL, C [undocumented]
+void opcode_fd_6a(void); // LD IYL, D [undocumented]
+void opcode_fd_6b(void); // LD IYL, E [undocumented]
+void opcode_fd_6c(void); // LD IYL, IYH [undocumented]
+void opcode_fd_6d(void); // LD IYL, IYL [undocumented]
+void opcode_fd_6e(void); // LD L, (IY + d)
+void opcode_fd_6f(void); // LD IYL, A [undocumented]
+void opcode_fd_70(void); // LD (IY + d), B
+void opcode_fd_71(void); // LD (IY + d), C
+void opcode_fd_72(void); // LD (IY + d), D
+void opcode_fd_73(void); // LD (IY + d), E
+void opcode_fd_74(void); // LD (IY + d), H
+void opcode_fd_75(void); // LD (IY + d), L
+void opcode_fd_77(void); // LD (IY + d), A
+void opcode_fd_7c(void); // LD A, IYH [undocumented]
+void opcode_fd_7d(void); // LD A, IYL [undocumented]
+void opcode_fd_7e(void); // LD A, (IY + d)
+void opcode_fd_84(void); // ADD A, IYH [undocumented]
+void opcode_fd_85(void); // ADD A, IYL [undocumented]
+void opcode_fd_86(void); // ADD A, (IY + d)
+void opcode_fd_8c(void); // ADC A, IYH [undocumented]
+void opcode_fd_8d(void); // ADC A, IYL [undocumented]
+void opcode_fd_8e(void); // ADC A, (IY + d)
+void opcode_fd_94(void); // SUB IYH [undocumented]
+void opcode_fd_95(void); // SUB IYL [undocumented]
+void opcode_fd_96(void); // SUB (IY + d)
+void opcode_fd_9c(void); // SBC A, IYH [undocumented]
+void opcode_fd_9d(void); // SBC A, IYL [undocumented]
+void opcode_fd_9e(void); // SBC A, (IY + d)
+void opcode_fd_a4(void); // AND IYH [undocumented]
+void opcode_fd_a5(void); // AND IYL [undocumented]
+void opcode_fd_a6(void); // AND (IY + d)
+void opcode_fd_ac(void); // XOR IYH [undocumented]
+void opcode_fd_ad(void); // XOR IYL [undocumented]
+void opcode_fd_ae(void); // XOR (IY + d)
+void opcode_fd_b4(void); // OR IYH [undocumented]
+void opcode_fd_b5(void); // OR IYL [undocumented]
+void opcode_fd_b6(void); // OR (IY + d)
+void opcode_fd_bc(void); // CP IYH [undocumented]
+void opcode_fd_bd(void); // CP IYL [undocumented]
+void opcode_fd_be(void); // CP (IY + d)
+void opcode_fd_cb(void); //
+void opcode_fd_e1(void); // POP IY
+void opcode_fd_e3(void); // EX (SP), IY
+void opcode_fd_e5(void); // PUSH IY
+void opcode_fd_e9(void); // JP (IY)
+void opcode_fd_f9(void); // LD SP, IY
+
+// Handlers for 0xDDCB and 0xFDCB prefixes
+void opcode_xycb_00( unsigned ); // LD B, RLC (IX + d) [undocumented]
+void opcode_xycb_01( unsigned ); // LD C, RLC (IX + d) [undocumented]
+void opcode_xycb_02( unsigned ); // LD D, RLC (IX + d) [undocumented]
+void opcode_xycb_03( unsigned ); // LD E, RLC (IX + d) [undocumented]
+void opcode_xycb_04( unsigned ); // LD H, RLC (IX + d) [undocumented]
+void opcode_xycb_05( unsigned ); // LD L, RLC (IX + d) [undocumented]
+void opcode_xycb_06( unsigned ); // RLC (IX + d)
+void opcode_xycb_07( unsigned ); // LD A, RLC (IX + d) [undocumented]
+void opcode_xycb_08( unsigned ); // LD B, RRC (IX + d) [undocumented]
+void opcode_xycb_09( unsigned ); // LD C, RRC (IX + d) [undocumented]
+void opcode_xycb_0a( unsigned ); // LD D, RRC (IX + d) [undocumented]
+void opcode_xycb_0b( unsigned ); // LD E, RRC (IX + d) [undocumented]
+void opcode_xycb_0c( unsigned ); // LD H, RRC (IX + d) [undocumented]
+void opcode_xycb_0d( unsigned ); // LD L, RRC (IX + d) [undocumented]
+void opcode_xycb_0e( unsigned ); // RRC (IX + d)
+void opcode_xycb_0f( unsigned ); // LD A, RRC (IX + d) [undocumented]
+void opcode_xycb_10( unsigned ); // LD B, RL (IX + d) [undocumented]
+void opcode_xycb_11( unsigned ); // LD C, RL (IX + d) [undocumented]
+void opcode_xycb_12( unsigned ); // LD D, RL (IX + d) [undocumented]
+void opcode_xycb_13( unsigned ); // LD E, RL (IX + d) [undocumented]
+void opcode_xycb_14( unsigned ); // LD H, RL (IX + d) [undocumented]
+void opcode_xycb_15( unsigned ); // LD L, RL (IX + d) [undocumented]
+void opcode_xycb_16( unsigned ); // RL (IX + d)
+void opcode_xycb_17( unsigned ); // LD A, RL (IX + d) [undocumented]
+void opcode_xycb_18( unsigned ); // LD B, RR (IX + d) [undocumented]
+void opcode_xycb_19( unsigned ); // LD C, RR (IX + d) [undocumented]
+void opcode_xycb_1a( unsigned ); // LD D, RR (IX + d) [undocumented]
+void opcode_xycb_1b( unsigned ); // LD E, RR (IX + d) [undocumented]
+void opcode_xycb_1c( unsigned ); // LD H, RR (IX + d) [undocumented]
+void opcode_xycb_1d( unsigned ); // LD L, RR (IX + d) [undocumented]
+void opcode_xycb_1e( unsigned ); // RR (IX + d)
+void opcode_xycb_1f( unsigned ); // LD A, RR (IX + d) [undocumented]
+void opcode_xycb_20( unsigned ); // LD B, SLA (IX + d) [undocumented]
+void opcode_xycb_21( unsigned ); // LD C, SLA (IX + d) [undocumented]
+void opcode_xycb_22( unsigned ); // LD D, SLA (IX + d) [undocumented]
+void opcode_xycb_23( unsigned ); // LD E, SLA (IX + d) [undocumented]
+void opcode_xycb_24( unsigned ); // LD H, SLA (IX + d) [undocumented]
+void opcode_xycb_25( unsigned ); // LD L, SLA (IX + d) [undocumented]
+void opcode_xycb_26( unsigned ); // SLA (IX + d)
+void opcode_xycb_27( unsigned ); // LD A, SLA (IX + d) [undocumented]
+void opcode_xycb_28( unsigned ); // LD B, SRA (IX + d) [undocumented]
+void opcode_xycb_29( unsigned ); // LD C, SRA (IX + d) [undocumented]
+void opcode_xycb_2a( unsigned ); // LD D, SRA (IX + d) [undocumented]
+void opcode_xycb_2b( unsigned ); // LD E, SRA (IX + d) [undocumented]
+void opcode_xycb_2c( unsigned ); // LD H, SRA (IX + d) [undocumented]
+void opcode_xycb_2d( unsigned ); // LD L, SRA (IX + d) [undocumented]
+void opcode_xycb_2e( unsigned ); // SRA (IX + d)
+void opcode_xycb_2f( unsigned ); // LD A, SRA (IX + d) [undocumented]
+void opcode_xycb_30( unsigned ); // LD B, SLL (IX + d) [undocumented]
+void opcode_xycb_31( unsigned ); // LD C, SLL (IX + d) [undocumented]
+void opcode_xycb_32( unsigned ); // LD D, SLL (IX + d) [undocumented]
+void opcode_xycb_33( unsigned ); // LD E, SLL (IX + d) [undocumented]
+void opcode_xycb_34( unsigned ); // LD H, SLL (IX + d) [undocumented]
+void opcode_xycb_35( unsigned ); // LD L, SLL (IX + d) [undocumented]
+void opcode_xycb_36( unsigned ); // SLL (IX + d) [undocumented]
+void opcode_xycb_37( unsigned ); // LD A, SLL (IX + d) [undocumented]
+void opcode_xycb_38( unsigned ); // LD B, SRL (IX + d) [undocumented]
+void opcode_xycb_39( unsigned ); // LD C, SRL (IX + d) [undocumented]
+void opcode_xycb_3a( unsigned ); // LD D, SRL (IX + d) [undocumented]
+void opcode_xycb_3b( unsigned ); // LD E, SRL (IX + d) [undocumented]
+void opcode_xycb_3c( unsigned ); // LD H, SRL (IX + d) [undocumented]
+void opcode_xycb_3d( unsigned ); // LD L, SRL (IX + d) [undocumented]
+void opcode_xycb_3e( unsigned ); // SRL (IX + d)
+void opcode_xycb_3f( unsigned ); // LD A, SRL (IX + d) [undocumented]
+void opcode_xycb_40( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_41( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_42( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_43( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_44( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_45( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_46( unsigned ); // BIT 0, (IX + d)
+void opcode_xycb_47( unsigned ); // BIT 0, (IX + d) [undocumented]
+void opcode_xycb_48( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_49( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_4a( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_4b( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_4c( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_4d( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_4e( unsigned ); // BIT 1, (IX + d)
+void opcode_xycb_4f( unsigned ); // BIT 1, (IX + d) [undocumented]
+void opcode_xycb_50( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_51( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_52( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_53( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_54( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_55( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_56( unsigned ); // BIT 2, (IX + d)
+void opcode_xycb_57( unsigned ); // BIT 2, (IX + d) [undocumented]
+void opcode_xycb_58( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_59( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_5a( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_5b( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_5c( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_5d( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_5e( unsigned ); // BIT 3, (IX + d)
+void opcode_xycb_5f( unsigned ); // BIT 3, (IX + d) [undocumented]
+void opcode_xycb_60( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_61( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_62( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_63( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_64( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_65( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_66( unsigned ); // BIT 4, (IX + d)
+void opcode_xycb_67( unsigned ); // BIT 4, (IX + d) [undocumented]
+void opcode_xycb_68( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_69( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_6a( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_6b( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_6c( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_6d( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_6e( unsigned ); // BIT 5, (IX + d)
+void opcode_xycb_6f( unsigned ); // BIT 5, (IX + d) [undocumented]
+void opcode_xycb_70( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_71( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_72( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_73( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_74( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_75( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_76( unsigned ); // BIT 6, (IX + d)
+void opcode_xycb_77( unsigned ); // BIT 6, (IX + d) [undocumented]
+void opcode_xycb_78( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_79( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_7a( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_7b( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_7c( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_7d( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_7e( unsigned ); // BIT 7, (IX + d)
+void opcode_xycb_7f( unsigned ); // BIT 7, (IX + d) [undocumented]
+void opcode_xycb_80( unsigned ); // LD B, RES 0, (IX + d) [undocumented]
+void opcode_xycb_81( unsigned ); // LD C, RES 0, (IX + d) [undocumented]
+void opcode_xycb_82( unsigned ); // LD D, RES 0, (IX + d) [undocumented]
+void opcode_xycb_83( unsigned ); // LD E, RES 0, (IX + d) [undocumented]
+void opcode_xycb_84( unsigned ); // LD H, RES 0, (IX + d) [undocumented]
+void opcode_xycb_85( unsigned ); // LD L, RES 0, (IX + d) [undocumented]
+void opcode_xycb_86( unsigned ); // RES 0, (IX + d)
+void opcode_xycb_87( unsigned ); // LD A, RES 0, (IX + d) [undocumented]
+void opcode_xycb_88( unsigned ); // LD B, RES 1, (IX + d) [undocumented]
+void opcode_xycb_89( unsigned ); // LD C, RES 1, (IX + d) [undocumented]
+void opcode_xycb_8a( unsigned ); // LD D, RES 1, (IX + d) [undocumented]
+void opcode_xycb_8b( unsigned ); // LD E, RES 1, (IX + d) [undocumented]
+void opcode_xycb_8c( unsigned ); // LD H, RES 1, (IX + d) [undocumented]
+void opcode_xycb_8d( unsigned ); // LD L, RES 1, (IX + d) [undocumented]
+void opcode_xycb_8e( unsigned ); // RES 1, (IX + d)
+void opcode_xycb_8f( unsigned ); // LD A, RES 1, (IX + d) [undocumented]
+void opcode_xycb_90( unsigned ); // LD B, RES 2, (IX + d) [undocumented]
+void opcode_xycb_91( unsigned ); // LD C, RES 2, (IX + d) [undocumented]
+void opcode_xycb_92( unsigned ); // LD D, RES 2, (IX + d) [undocumented]
+void opcode_xycb_93( unsigned ); // LD E, RES 2, (IX + d) [undocumented]
+void opcode_xycb_94( unsigned ); // LD H, RES 2, (IX + d) [undocumented]
+void opcode_xycb_95( unsigned ); // LD L, RES 2, (IX + d) [undocumented]
+void opcode_xycb_96( unsigned ); // RES 2, (IX + d)
+void opcode_xycb_97( unsigned ); // LD A, RES 2, (IX + d) [undocumented]
+void opcode_xycb_98( unsigned ); // LD B, RES 3, (IX + d) [undocumented]
+void opcode_xycb_99( unsigned ); // LD C, RES 3, (IX + d) [undocumented]
+void opcode_xycb_9a( unsigned ); // LD D, RES 3, (IX + d) [undocumented]
+void opcode_xycb_9b( unsigned ); // LD E, RES 3, (IX + d) [undocumented]
+void opcode_xycb_9c( unsigned ); // LD H, RES 3, (IX + d) [undocumented]
+void opcode_xycb_9d( unsigned ); // LD L, RES 3, (IX + d) [undocumented]
+void opcode_xycb_9e( unsigned ); // RES 3, (IX + d)
+void opcode_xycb_9f( unsigned ); // LD A, RES 3, (IX + d) [undocumented]
+void opcode_xycb_a0( unsigned ); // LD B, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a1( unsigned ); // LD C, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a2( unsigned ); // LD D, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a3( unsigned ); // LD E, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a4( unsigned ); // LD H, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a5( unsigned ); // LD L, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a6( unsigned ); // RES 4, (IX + d)
+void opcode_xycb_a7( unsigned ); // LD A, RES 4, (IX + d) [undocumented]
+void opcode_xycb_a8( unsigned ); // LD B, RES 5, (IX + d) [undocumented]
+void opcode_xycb_a9( unsigned ); // LD C, RES 5, (IX + d) [undocumented]
+void opcode_xycb_aa( unsigned ); // LD D, RES 5, (IX + d) [undocumented]
+void opcode_xycb_ab( unsigned ); // LD E, RES 5, (IX + d) [undocumented]
+void opcode_xycb_ac( unsigned ); // LD H, RES 5, (IX + d) [undocumented]
+void opcode_xycb_ad( unsigned ); // LD L, RES 5, (IX + d) [undocumented]
+void opcode_xycb_ae( unsigned ); // RES 5, (IX + d)
+void opcode_xycb_af( unsigned ); // LD A, RES 5, (IX + d) [undocumented]
+void opcode_xycb_b0( unsigned ); // LD B, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b1( unsigned ); // LD C, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b2( unsigned ); // LD D, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b3( unsigned ); // LD E, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b4( unsigned ); // LD H, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b5( unsigned ); // LD L, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b6( unsigned ); // RES 6, (IX + d)
+void opcode_xycb_b7( unsigned ); // LD A, RES 6, (IX + d) [undocumented]
+void opcode_xycb_b8( unsigned ); // LD B, RES 7, (IX + d) [undocumented]
+void opcode_xycb_b9( unsigned ); // LD C, RES 7, (IX + d) [undocumented]
+void opcode_xycb_ba( unsigned ); // LD D, RES 7, (IX + d) [undocumented]
+void opcode_xycb_bb( unsigned ); // LD E, RES 7, (IX + d) [undocumented]
+void opcode_xycb_bc( unsigned ); // LD H, RES 7, (IX + d) [undocumented]
+void opcode_xycb_bd( unsigned ); // LD L, RES 7, (IX + d) [undocumented]
+void opcode_xycb_be( unsigned ); // RES 7, (IX + d)
+void opcode_xycb_bf( unsigned ); // LD A, RES 7, (IX + d) [undocumented]
+void opcode_xycb_c0( unsigned ); // LD B, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c1( unsigned ); // LD C, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c2( unsigned ); // LD D, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c3( unsigned ); // LD E, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c4( unsigned ); // LD H, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c5( unsigned ); // LD L, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c6( unsigned ); // SET 0, (IX + d)
+void opcode_xycb_c7( unsigned ); // LD A, SET 0, (IX + d) [undocumented]
+void opcode_xycb_c8( unsigned ); // LD B, SET 1, (IX + d) [undocumented]
+void opcode_xycb_c9( unsigned ); // LD C, SET 1, (IX + d) [undocumented]
+void opcode_xycb_ca( unsigned ); // LD D, SET 1, (IX + d) [undocumented]
+void opcode_xycb_cb( unsigned ); // LD E, SET 1, (IX + d) [undocumented]
+void opcode_xycb_cc( unsigned ); // LD H, SET 1, (IX + d) [undocumented]
+void opcode_xycb_cd( unsigned ); // LD L, SET 1, (IX + d) [undocumented]
+void opcode_xycb_ce( unsigned ); // SET 1, (IX + d)
+void opcode_xycb_cf( unsigned ); // LD A, SET 1, (IX + d) [undocumented]
+void opcode_xycb_d0( unsigned ); // LD B, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d1( unsigned ); // LD C, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d2( unsigned ); // LD D, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d3( unsigned ); // LD E, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d4( unsigned ); // LD H, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d5( unsigned ); // LD L, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d6( unsigned ); // SET 2, (IX + d)
+void opcode_xycb_d7( unsigned ); // LD A, SET 2, (IX + d) [undocumented]
+void opcode_xycb_d8( unsigned ); // LD B, SET 3, (IX + d) [undocumented]
+void opcode_xycb_d9( unsigned ); // LD C, SET 3, (IX + d) [undocumented]
+void opcode_xycb_da( unsigned ); // LD D, SET 3, (IX + d) [undocumented]
+void opcode_xycb_db( unsigned ); // LD E, SET 3, (IX + d) [undocumented]
+void opcode_xycb_dc( unsigned ); // LD H, SET 3, (IX + d) [undocumented]
+void opcode_xycb_dd( unsigned ); // LD L, SET 3, (IX + d) [undocumented]
+void opcode_xycb_de( unsigned ); // SET 3, (IX + d)
+void opcode_xycb_df( unsigned ); // LD A, SET 3, (IX + d) [undocumented]
+void opcode_xycb_e0( unsigned ); // LD B, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e1( unsigned ); // LD C, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e2( unsigned ); // LD D, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e3( unsigned ); // LD E, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e4( unsigned ); // LD H, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e5( unsigned ); // LD L, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e6( unsigned ); // SET 4, (IX + d)
+void opcode_xycb_e7( unsigned ); // LD A, SET 4, (IX + d) [undocumented]
+void opcode_xycb_e8( unsigned ); // LD B, SET 5, (IX + d) [undocumented]
+void opcode_xycb_e9( unsigned ); // LD C, SET 5, (IX + d) [undocumented]
+void opcode_xycb_ea( unsigned ); // LD D, SET 5, (IX + d) [undocumented]
+void opcode_xycb_eb( unsigned ); // LD E, SET 5, (IX + d) [undocumented]
+void opcode_xycb_ec( unsigned ); // LD H, SET 5, (IX + d) [undocumented]
+void opcode_xycb_ed( unsigned ); // LD L, SET 5, (IX + d) [undocumented]
+void opcode_xycb_ee( unsigned ); // SET 5, (IX + d)
+void opcode_xycb_ef( unsigned ); // LD A, SET 5, (IX + d) [undocumented]
+void opcode_xycb_f0( unsigned ); // LD B, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f1( unsigned ); // LD C, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f2( unsigned ); // LD D, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f3( unsigned ); // LD E, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f4( unsigned ); // LD H, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f5( unsigned ); // LD L, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f6( unsigned ); // SET 6, (IX + d)
+void opcode_xycb_f7( unsigned ); // LD A, SET 6, (IX + d) [undocumented]
+void opcode_xycb_f8( unsigned ); // LD B, SET 7, (IX + d) [undocumented]
+void opcode_xycb_f9( unsigned ); // LD C, SET 7, (IX + d) [undocumented]
+void opcode_xycb_fa( unsigned ); // LD D, SET 7, (IX + d) [undocumented]
+void opcode_xycb_fb( unsigned ); // LD E, SET 7, (IX + d) [undocumented]
+void opcode_xycb_fc( unsigned ); // LD H, SET 7, (IX + d) [undocumented]
+void opcode_xycb_fd( unsigned ); // LD L, SET 7, (IX + d) [undocumented]
+void opcode_xycb_fe( unsigned ); // SET 7, (IX + d)
+void opcode_xycb_ff( unsigned ); // LD A, SET 7, (IX + d) [undocumented]
+
+// Trivia: there are 1018 opcode_xxx() functions in this class,
+// for a total of 1274 emulated opcodes. Fortunately, most of them
+// were automatically generated by custom made programs and scripts.
+
+#endif