1 /** Z80: portable Z80 emulator *******************************/
2 /**                                                         **/
3 /**                          Codes.h                        **/
4 /**                                                         **/
5 /** This file contains implementation for the main table of **/
6 /** Z80 commands. It is included from Z80.c.                **/
7 /**                                                         **/
8 /** Copyright (C) Marat Fayzullin 1994-2002                 **/
9 /**     You are not allowed to distribute this software     **/
10 /**     commercially. Please, notify me, if you make any    **/
11 /**     changes to this file.                               **/
12 /*************************************************************/
13 
14 case JR_NZ:   if(AF_L&Z_FLAG) PC_W++; else { T_STATES-=5;M_JR; } break;
15 case JR_NC:   if(AF_L&C_FLAG) PC_W++; else { T_STATES-=5;M_JR; } break;
16 case JR_Z:    if(AF_L&Z_FLAG) { T_STATES-=5;M_JR; } else PC_W++; break;
17 case JR_C:    if(AF_L&C_FLAG) { T_STATES-=5;M_JR; } else PC_W++; break;
18 
19 case JP_NZ:   if(AF_L&Z_FLAG) PC_W+=2; else { M_JP; } break;
20 case JP_NC:   if(AF_L&C_FLAG) PC_W+=2; else { M_JP; } break;
21 case JP_PO:   if(AF_L&P_FLAG) PC_W+=2; else { M_JP; } break;
22 case JP_P:    if(AF_L&S_FLAG) PC_W+=2; else { M_JP; } break;
23 case JP_Z:    if(AF_L&Z_FLAG) { M_JP; } else PC_W+=2; break;
24 case JP_C:    if(AF_L&C_FLAG) { M_JP; } else PC_W+=2; break;
25 case JP_PE:   if(AF_L&P_FLAG) { M_JP; } else PC_W+=2; break;
26 case JP_M:    if(AF_L&S_FLAG) { M_JP; } else PC_W+=2; break;
27 
28 case RET_NZ:  if(!(AF_L&Z_FLAG)) { T_STATES-=6;M_RET; } break;
29 case RET_NC:  if(!(AF_L&C_FLAG)) { T_STATES-=6;M_RET; } break;
30 case RET_PO:  if(!(AF_L&P_FLAG)) { T_STATES-=6;M_RET; } break;
31 case RET_P:   if(!(AF_L&S_FLAG)) { T_STATES-=6;M_RET; } break;
32 case RET_Z:   if(AF_L&Z_FLAG)    { T_STATES-=6;M_RET; } break;
33 case RET_C:   if(AF_L&C_FLAG)    { T_STATES-=6;M_RET; } break;
34 case RET_PE:  if(AF_L&P_FLAG)    { T_STATES-=6;M_RET; } break;
35 case RET_M:   if(AF_L&S_FLAG)    { T_STATES-=6;M_RET; } break;
36 
37 case CALL_NZ: if(AF_L&Z_FLAG) PC_W+=2; else { T_STATES-=7;M_CALL; } break;
38 case CALL_NC: if(AF_L&C_FLAG) PC_W+=2; else { T_STATES-=7;M_CALL; } break;
39 case CALL_PO: if(AF_L&P_FLAG) PC_W+=2; else { T_STATES-=7;M_CALL; } break;
40 case CALL_P:  if(AF_L&S_FLAG) PC_W+=2; else { T_STATES-=7;M_CALL; } break;
41 case CALL_Z:  if(AF_L&Z_FLAG) { T_STATES-=7;M_CALL; } else PC_W+=2; break;
42 case CALL_C:  if(AF_L&C_FLAG) { T_STATES-=7;M_CALL; } else PC_W+=2; break;
43 case CALL_PE: if(AF_L&P_FLAG) { T_STATES-=7;M_CALL; } else PC_W+=2; break;
44 case CALL_M:  if(AF_L&S_FLAG) { T_STATES-=7;M_CALL; } else PC_W+=2; break;
45 
46 case ADD_BYTE: I=RdZ80(PC_W++);M_ADD(I);break;
47 case SUB_BYTE: I=RdZ80(PC_W++);M_SUB(I);break;
48 case AND_BYTE: I=RdZ80(PC_W++);M_AND(I);break;
49 case OR_BYTE:  I=RdZ80(PC_W++);M_IOR(I);break;
50 case ADC_BYTE: I=RdZ80(PC_W++);M_ADC(I);break;
51 case SBC_BYTE: I=RdZ80(PC_W++);M_SBC(I);break;
52 case XOR_BYTE: I=RdZ80(PC_W++);M_XOR(I);break;
53 case CP_BYTE:  I=RdZ80(PC_W++);M_CMP(I);break;
54 
55 case LD_BC_WORD: M_LDWORD(BC);break;
56 case LD_DE_WORD: M_LDWORD(DE);break;
57 case LD_HL_WORD: M_LDWORD(HL);break;
58 case LD_SP_WORD: M_LDWORD(SP);break;
59 
60 case LD_PC_HL: PC_W=HL_W;break;
61 case LD_SP_HL: SP_W=HL_W;break;
62 case LD_A_xBC: AF_H=RdZ80(BC_W);break;
63 case LD_A_xDE: AF_H=RdZ80(DE_W);break;
64 
65 case ADD_HL_BC:  M_ADDW(HL,BC);break;
66 case ADD_HL_DE:  M_ADDW(HL,DE);break;
67 case ADD_HL_HL:  M_ADDW(HL,HL);break;
68 case ADD_HL_SP:  M_ADDW(HL,SP);break;
69 
70 case DEC_B:    M_DEC(BC_H);break;
71 case DEC_C:    M_DEC(BC_L);break;
72 case DEC_D:    M_DEC(DE_H);break;
73 case DEC_E:    M_DEC(DE_L);break;
74 case DEC_H:    M_DEC(HL_H);break;
75 case DEC_L:    M_DEC(HL_L);break;
76 case DEC_A:    M_DEC(AF_H);break;
77 case DEC_xHL:  I=RdZ80(HL_W);M_DEC(I);WrZ80(HL_W,I);break;
78 
79 case INC_B:    M_INC(BC_H);break;
80 case INC_C:    M_INC(BC_L);break;
81 case INC_D:    M_INC(DE_H);break;
82 case INC_E:    M_INC(DE_L);break;
83 case INC_H:    M_INC(HL_H);break;
84 case INC_L:    M_INC(HL_L);break;
85 case INC_A:    M_INC(AF_H);break;
86 case INC_xHL:  I=RdZ80(HL_W);M_INC(I);WrZ80(HL_W,I);break;
87 
88 case RLCA:
89   I=AF_H&0x80? C_FLAG:0;
90   AF_H=(AF_H<<1)|I;
91   AF_L=(AF_L&~(C_FLAG|N_FLAG|H_FLAG))|I;
92   break;
93 case RLA:
94   I=AF_H&0x80? C_FLAG:0;
95   AF_H=(AF_H<<1)|(AF_L&C_FLAG);
96   AF_L=(AF_L&~(C_FLAG|N_FLAG|H_FLAG))|I;
97   break;
98 case RRCA:
99   I=AF_H&0x01;
100   AF_H=(AF_H>>1)|(I? 0x80:0);
101   AF_L=(AF_L&~(C_FLAG|N_FLAG|H_FLAG))|I;
102   break;
103 case RRA:
104   I=AF_H&0x01;
105   AF_H=(AF_H>>1)|(AF_L&C_FLAG? 0x80:0);
106   AF_L=(AF_L&~(C_FLAG|N_FLAG|H_FLAG))|I;
107   break;
108 
109 case RST00:    M_RST(0x0000);break;
110 case RST08:    M_RST(0x0008);break;
111 case RST10:    M_RST(0x0010);break;
112 case RST18:    M_RST(0x0018);break;
113 case RST20:    M_RST(0x0020);break;
114 case RST28:    M_RST(0x0028);break;
115 case RST30:    M_RST(0x0030);break;
116 case RST38:    M_RST(0x0038);break;
117 
118 case PUSH_BC:  M_PUSH(BC);break;
119 case PUSH_DE:  M_PUSH(DE);break;
120 case PUSH_HL:  M_PUSH(HL);break;
121 case PUSH_AF:  M_PUSH(AF);break;
122 
123 case POP_BC:   M_POP(BC);break;
124 case POP_DE:   M_POP(DE);break;
125 case POP_HL:   M_POP(HL);break;
126 case POP_AF:   M_POP(AF);break;
127 
128 case DJNZ: if(--BC_H) { T_STATES-=5;M_JR; } else PC_W++;break;
129 case JP:   M_JP;break;
130 case JR:   M_JR;break;
131 case CALL: M_CALL;break;
132 case RET:  M_RET;break;
133 case SCF:  S(C_FLAG);R(N_FLAG|H_FLAG);break;
134 case CPL:  AF_H=~AF_H;S(N_FLAG|H_FLAG);break;
135 case OUTA: I=RdZ80(PC_W++);OutZ80((AF_W & 0xff00) | (I & 0x00ff), AF_H);break;
136 case INA:  I=RdZ80(PC_W++);AF_H=InZ80((AF_W & 0xff00) | (I & 0x00ff));break;
137 
138 case DI:
139   IF_W &= ~(IFF_1 | IFF_2 | IFF_3);
140   break;
141 
142 case EI:
143   IF_W |=  (IFF_1 | IFF_2 | IFF_3);
144   break;
145 
146 case CCF:
147   AF_L^=C_FLAG;R(N_FLAG|H_FLAG);
148   AF_L|=AF_L&C_FLAG? 0:H_FLAG;
149   break;
150 
151 case EXX:
152   WZ_W=BC_W;BC_W=BC_P;BC_P=WZ_W;
153   WZ_W=DE_W;DE_W=DE_P;DE_P=WZ_W;
154   WZ_W=HL_W;HL_W=HL_P;HL_P=WZ_W;
155   break;
156 
157 case EX_DE_HL: WZ_W=DE_W;DE_W=HL_W;HL_W=WZ_W;break;
158 case EX_AF_AF: WZ_W=AF_W;AF_W=AF_P;AF_P=WZ_W;break;
159 
160 case LD_xBC_A: WrZ80(BC_W,AF_H);break;
161 case LD_xDE_A: WrZ80(DE_W,AF_H);break;
162 
163 case LD_xHL_BYTE: WrZ80(HL_W,RdZ80(PC_W++));break;
164 
165 case LD_xWORD_HL:
166   WZ_L=RdZ80(PC_W++);
167   WZ_H=RdZ80(PC_W++);
168   WrZ80(WZ_W++,HL_L);
169   WrZ80(WZ_W,HL_H);
170   break;
171 
172 case LD_HL_xWORD:
173   WZ_L=RdZ80(PC_W++);
174   WZ_H=RdZ80(PC_W++);
175   HL_L=RdZ80(WZ_W++);
176   HL_H=RdZ80(WZ_W);
177   break;
178 
179 case LD_A_xWORD:
180   WZ_L=RdZ80(PC_W++);
181   WZ_H=RdZ80(PC_W++);
182   AF_H=RdZ80(WZ_W);
183   break;
184 
185 case LD_xWORD_A:
186   WZ_L=RdZ80(PC_W++);
187   WZ_H=RdZ80(PC_W++);
188   WrZ80(WZ_W,AF_H);
189   break;
190 
191 case EX_HL_xSP:
192   WZ_L=RdZ80(SP_W);WrZ80(SP_W++,HL_L);
193   WZ_H=RdZ80(SP_W);WrZ80(SP_W--,HL_H);
194   HL_W=WZ_W;
195   break;
196