1/*****************************************************************************\
2 Snes9x - Portable Super Nintendo Entertainment System (TM) emulator.
3 This file is licensed under the Snes9x License.
4 For further information, consult the LICENSE file in the root directory.
5\*****************************************************************************/
6
7#include "snes9x.h"
8#include "memmap.h"
9#include "apu/apu.h"
10
11// for "Magic WDM" features
12#ifdef DEBUGGER
13#include "snapshot.h"
14#include "display.h"
15#include "debug.h"
16#include "missing.h"
17#endif
18
19#ifdef SA1_OPCODES
20#define AddCycles(n) { SA1.Cycles += (n); }
21#else
22#define AddCycles(n) { CPU.Cycles += (n); while (CPU.Cycles >= CPU.NextEvent) S9xDoHEventProcessing(); }
23#endif
24
25#include "cpuaddr.h"
26#include "cpuops.h"
27#include "cpumacro.h"
28
29
30/* ADC ********************************************************************* */
31
32static void Op69M1 (void)
33{
34 ADC(Immediate8(READ));
35}
36
37static void Op69M0 (void)
38{
39 ADC(Immediate16(READ));
40}
41
42static void Op69Slow (void)
43{
44 if (CheckMemory())
45 ADC(Immediate8Slow(READ));
46 else
47 ADC(Immediate16Slow(READ));
48}
49
50rOP8 (65M1, Direct, WRAP_BANK, ADC)
51rOP16(65M0, Direct, WRAP_BANK, ADC)
52rOPM (65Slow, DirectSlow, WRAP_BANK, ADC)
53
54rOP8 (75E1, DirectIndexedXE1, WRAP_BANK, ADC)
55rOP8 (75E0M1, DirectIndexedXE0, WRAP_BANK, ADC)
56rOP16(75E0M0, DirectIndexedXE0, WRAP_BANK, ADC)
57rOPM (75Slow, DirectIndexedXSlow, WRAP_BANK, ADC)
58
59rOP8 (72E1, DirectIndirectE1, WRAP_NONE, ADC)
60rOP8 (72E0M1, DirectIndirectE0, WRAP_NONE, ADC)
61rOP16(72E0M0, DirectIndirectE0, WRAP_NONE, ADC)
62rOPM (72Slow, DirectIndirectSlow, WRAP_NONE, ADC)
63
64rOP8 (61E1, DirectIndexedIndirectE1, WRAP_NONE, ADC)
65rOP8 (61E0M1, DirectIndexedIndirectE0, WRAP_NONE, ADC)
66rOP16(61E0M0, DirectIndexedIndirectE0, WRAP_NONE, ADC)
67rOPM (61Slow, DirectIndexedIndirectSlow, WRAP_NONE, ADC)
68
69rOP8 (71E1, DirectIndirectIndexedE1, WRAP_NONE, ADC)
70rOP8 (71E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, ADC)
71rOP16(71E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, ADC)
72rOP8 (71E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, ADC)
73rOP16(71E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, ADC)
74rOPM (71Slow, DirectIndirectIndexedSlow, WRAP_NONE, ADC)
75
76rOP8 (67M1, DirectIndirectLong, WRAP_NONE, ADC)
77rOP16(67M0, DirectIndirectLong, WRAP_NONE, ADC)
78rOPM (67Slow, DirectIndirectLongSlow, WRAP_NONE, ADC)
79
80rOP8 (77M1, DirectIndirectIndexedLong, WRAP_NONE, ADC)
81rOP16(77M0, DirectIndirectIndexedLong, WRAP_NONE, ADC)
82rOPM (77Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, ADC)
83
84rOP8 (6DM1, Absolute, WRAP_NONE, ADC)
85rOP16(6DM0, Absolute, WRAP_NONE, ADC)
86rOPM (6DSlow, AbsoluteSlow, WRAP_NONE, ADC)
87
88rOP8 (7DM1X1, AbsoluteIndexedXX1, WRAP_NONE, ADC)
89rOP16(7DM0X1, AbsoluteIndexedXX1, WRAP_NONE, ADC)
90rOP8 (7DM1X0, AbsoluteIndexedXX0, WRAP_NONE, ADC)
91rOP16(7DM0X0, AbsoluteIndexedXX0, WRAP_NONE, ADC)
92rOPM (7DSlow, AbsoluteIndexedXSlow, WRAP_NONE, ADC)
93
94rOP8 (79M1X1, AbsoluteIndexedYX1, WRAP_NONE, ADC)
95rOP16(79M0X1, AbsoluteIndexedYX1, WRAP_NONE, ADC)
96rOP8 (79M1X0, AbsoluteIndexedYX0, WRAP_NONE, ADC)
97rOP16(79M0X0, AbsoluteIndexedYX0, WRAP_NONE, ADC)
98rOPM (79Slow, AbsoluteIndexedYSlow, WRAP_NONE, ADC)
99
100rOP8 (6FM1, AbsoluteLong, WRAP_NONE, ADC)
101rOP16(6FM0, AbsoluteLong, WRAP_NONE, ADC)
102rOPM (6FSlow, AbsoluteLongSlow, WRAP_NONE, ADC)
103
104rOP8 (7FM1, AbsoluteLongIndexedX, WRAP_NONE, ADC)
105rOP16(7FM0, AbsoluteLongIndexedX, WRAP_NONE, ADC)
106rOPM (7FSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, ADC)
107
108rOP8 (63M1, StackRelative, WRAP_NONE, ADC)
109rOP16(63M0, StackRelative, WRAP_NONE, ADC)
110rOPM (63Slow, StackRelativeSlow, WRAP_NONE, ADC)
111
112rOP8 (73M1, StackRelativeIndirectIndexed, WRAP_NONE, ADC)
113rOP16(73M0, StackRelativeIndirectIndexed, WRAP_NONE, ADC)
114rOPM (73Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, ADC)
115
116/* AND ********************************************************************* */
117
118static void Op29M1 (void)
119{
120 Registers.AL &= Immediate8(READ);
121 SetZN(Registers.AL);
122}
123
124static void Op29M0 (void)
125{
126 Registers.A.W &= Immediate16(READ);
127 SetZN(Registers.A.W);
128}
129
130static void Op29Slow (void)
131{
132 if (CheckMemory())
133 {
134 Registers.AL &= Immediate8Slow(READ);
135 SetZN(Registers.AL);
136 }
137 else
138 {
139 Registers.A.W &= Immediate16Slow(READ);
140 SetZN(Registers.A.W);
141 }
142}
143
144rOP8 (25M1, Direct, WRAP_BANK, AND)
145rOP16(25M0, Direct, WRAP_BANK, AND)
146rOPM (25Slow, DirectSlow, WRAP_BANK, AND)
147
148rOP8 (35E1, DirectIndexedXE1, WRAP_BANK, AND)
149rOP8 (35E0M1, DirectIndexedXE0, WRAP_BANK, AND)
150rOP16(35E0M0, DirectIndexedXE0, WRAP_BANK, AND)
151rOPM (35Slow, DirectIndexedXSlow, WRAP_BANK, AND)
152
153rOP8 (32E1, DirectIndirectE1, WRAP_NONE, AND)
154rOP8 (32E0M1, DirectIndirectE0, WRAP_NONE, AND)
155rOP16(32E0M0, DirectIndirectE0, WRAP_NONE, AND)
156rOPM (32Slow, DirectIndirectSlow, WRAP_NONE, AND)
157
158rOP8 (21E1, DirectIndexedIndirectE1, WRAP_NONE, AND)
159rOP8 (21E0M1, DirectIndexedIndirectE0, WRAP_NONE, AND)
160rOP16(21E0M0, DirectIndexedIndirectE0, WRAP_NONE, AND)
161rOPM (21Slow, DirectIndexedIndirectSlow, WRAP_NONE, AND)
162
163rOP8 (31E1, DirectIndirectIndexedE1, WRAP_NONE, AND)
164rOP8 (31E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, AND)
165rOP16(31E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, AND)
166rOP8 (31E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, AND)
167rOP16(31E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, AND)
168rOPM (31Slow, DirectIndirectIndexedSlow, WRAP_NONE, AND)
169
170rOP8 (27M1, DirectIndirectLong, WRAP_NONE, AND)
171rOP16(27M0, DirectIndirectLong, WRAP_NONE, AND)
172rOPM (27Slow, DirectIndirectLongSlow, WRAP_NONE, AND)
173
174rOP8 (37M1, DirectIndirectIndexedLong, WRAP_NONE, AND)
175rOP16(37M0, DirectIndirectIndexedLong, WRAP_NONE, AND)
176rOPM (37Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, AND)
177
178rOP8 (2DM1, Absolute, WRAP_NONE, AND)
179rOP16(2DM0, Absolute, WRAP_NONE, AND)
180rOPM (2DSlow, AbsoluteSlow, WRAP_NONE, AND)
181
182rOP8 (3DM1X1, AbsoluteIndexedXX1, WRAP_NONE, AND)
183rOP16(3DM0X1, AbsoluteIndexedXX1, WRAP_NONE, AND)
184rOP8 (3DM1X0, AbsoluteIndexedXX0, WRAP_NONE, AND)
185rOP16(3DM0X0, AbsoluteIndexedXX0, WRAP_NONE, AND)
186rOPM (3DSlow, AbsoluteIndexedXSlow, WRAP_NONE, AND)
187
188rOP8 (39M1X1, AbsoluteIndexedYX1, WRAP_NONE, AND)
189rOP16(39M0X1, AbsoluteIndexedYX1, WRAP_NONE, AND)
190rOP8 (39M1X0, AbsoluteIndexedYX0, WRAP_NONE, AND)
191rOP16(39M0X0, AbsoluteIndexedYX0, WRAP_NONE, AND)
192rOPM (39Slow, AbsoluteIndexedYSlow, WRAP_NONE, AND)
193
194rOP8 (2FM1, AbsoluteLong, WRAP_NONE, AND)
195rOP16(2FM0, AbsoluteLong, WRAP_NONE, AND)
196rOPM (2FSlow, AbsoluteLongSlow, WRAP_NONE, AND)
197
198rOP8 (3FM1, AbsoluteLongIndexedX, WRAP_NONE, AND)
199rOP16(3FM0, AbsoluteLongIndexedX, WRAP_NONE, AND)
200rOPM (3FSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, AND)
201
202rOP8 (23M1, StackRelative, WRAP_NONE, AND)
203rOP16(23M0, StackRelative, WRAP_NONE, AND)
204rOPM (23Slow, StackRelativeSlow, WRAP_NONE, AND)
205
206rOP8 (33M1, StackRelativeIndirectIndexed, WRAP_NONE, AND)
207rOP16(33M0, StackRelativeIndirectIndexed, WRAP_NONE, AND)
208rOPM (33Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, AND)
209
210/* ASL ********************************************************************* */
211
212static void Op0AM1 (void)
213{
214 AddCycles(ONE_CYCLE);
215 ICPU._Carry = (Registers.AL & 0x80) != 0;
216 Registers.AL <<= 1;
217 SetZN(Registers.AL);
218}
219
220static void Op0AM0 (void)
221{
222 AddCycles(ONE_CYCLE);
223 ICPU._Carry = (Registers.AH & 0x80) != 0;
224 Registers.A.W <<= 1;
225 SetZN(Registers.A.W);
226}
227
228static void Op0ASlow (void)
229{
230 AddCycles(ONE_CYCLE);
231
232 if (CheckMemory())
233 {
234 ICPU._Carry = (Registers.AL & 0x80) != 0;
235 Registers.AL <<= 1;
236 SetZN(Registers.AL);
237 }
238 else
239 {
240 ICPU._Carry = (Registers.AH & 0x80) != 0;
241 Registers.A.W <<= 1;
242 SetZN(Registers.A.W);
243 }
244}
245
246mOP8 (06M1, Direct, WRAP_BANK, ASL)
247mOP16(06M0, Direct, WRAP_BANK, ASL)
248mOPM (06Slow, DirectSlow, WRAP_BANK, ASL)
249
250mOP8 (16E1, DirectIndexedXE1, WRAP_BANK, ASL)
251mOP8 (16E0M1, DirectIndexedXE0, WRAP_BANK, ASL)
252mOP16(16E0M0, DirectIndexedXE0, WRAP_BANK, ASL)
253mOPM (16Slow, DirectIndexedXSlow, WRAP_BANK, ASL)
254
255mOP8 (0EM1, Absolute, WRAP_NONE, ASL)
256mOP16(0EM0, Absolute, WRAP_NONE, ASL)
257mOPM (0ESlow, AbsoluteSlow, WRAP_NONE, ASL)
258
259mOP8 (1EM1X1, AbsoluteIndexedXX1, WRAP_NONE, ASL)
260mOP16(1EM0X1, AbsoluteIndexedXX1, WRAP_NONE, ASL)
261mOP8 (1EM1X0, AbsoluteIndexedXX0, WRAP_NONE, ASL)
262mOP16(1EM0X0, AbsoluteIndexedXX0, WRAP_NONE, ASL)
263mOPM (1ESlow, AbsoluteIndexedXSlow, WRAP_NONE, ASL)
264
265/* BIT ********************************************************************* */
266
267static void Op89M1 (void)
268{
269 ICPU._Zero = Registers.AL & Immediate8(READ);
270}
271
272static void Op89M0 (void)
273{
274 ICPU._Zero = (Registers.A.W & Immediate16(READ)) != 0;
275}
276
277static void Op89Slow (void)
278{
279 if (CheckMemory())
280 ICPU._Zero = Registers.AL & Immediate8Slow(READ);
281 else
282 ICPU._Zero = (Registers.A.W & Immediate16Slow(READ)) != 0;
283}
284
285rOP8 (24M1, Direct, WRAP_BANK, BIT)
286rOP16(24M0, Direct, WRAP_BANK, BIT)
287rOPM (24Slow, DirectSlow, WRAP_BANK, BIT)
288
289rOP8 (34E1, DirectIndexedXE1, WRAP_BANK, BIT)
290rOP8 (34E0M1, DirectIndexedXE0, WRAP_BANK, BIT)
291rOP16(34E0M0, DirectIndexedXE0, WRAP_BANK, BIT)
292rOPM (34Slow, DirectIndexedXSlow, WRAP_BANK, BIT)
293
294rOP8 (2CM1, Absolute, WRAP_NONE, BIT)
295rOP16(2CM0, Absolute, WRAP_NONE, BIT)
296rOPM (2CSlow, AbsoluteSlow, WRAP_NONE, BIT)
297
298rOP8 (3CM1X1, AbsoluteIndexedXX1, WRAP_NONE, BIT)
299rOP16(3CM0X1, AbsoluteIndexedXX1, WRAP_NONE, BIT)
300rOP8 (3CM1X0, AbsoluteIndexedXX0, WRAP_NONE, BIT)
301rOP16(3CM0X0, AbsoluteIndexedXX0, WRAP_NONE, BIT)
302rOPM (3CSlow, AbsoluteIndexedXSlow, WRAP_NONE, BIT)
303
304/* CMP ********************************************************************* */
305
306static void OpC9M1 (void)
307{
308 int16 Int16 = (int16) Registers.AL - (int16) Immediate8(READ);
309 ICPU._Carry = Int16 >= 0;
310 SetZN((uint8) Int16);
311}
312
313static void OpC9M0 (void)
314{
315 int32 Int32 = (int32) Registers.A.W - (int32) Immediate16(READ);
316 ICPU._Carry = Int32 >= 0;
317 SetZN((uint16) Int32);
318}
319
320static void OpC9Slow (void)
321{
322 if (CheckMemory())
323 {
324 int16 Int16 = (int16) Registers.AL - (int16) Immediate8Slow(READ);
325 ICPU._Carry = Int16 >= 0;
326 SetZN((uint8) Int16);
327 }
328 else
329 {
330 int32 Int32 = (int32) Registers.A.W - (int32) Immediate16Slow(READ);
331 ICPU._Carry = Int32 >= 0;
332 SetZN((uint16) Int32);
333 }
334}
335
336rOP8 (C5M1, Direct, WRAP_BANK, CMP)
337rOP16(C5M0, Direct, WRAP_BANK, CMP)
338rOPM (C5Slow, DirectSlow, WRAP_BANK, CMP)
339
340rOP8 (D5E1, DirectIndexedXE1, WRAP_BANK, CMP)
341rOP8 (D5E0M1, DirectIndexedXE0, WRAP_BANK, CMP)
342rOP16(D5E0M0, DirectIndexedXE0, WRAP_BANK, CMP)
343rOPM (D5Slow, DirectIndexedXSlow, WRAP_BANK, CMP)
344
345rOP8 (D2E1, DirectIndirectE1, WRAP_NONE, CMP)
346rOP8 (D2E0M1, DirectIndirectE0, WRAP_NONE, CMP)
347rOP16(D2E0M0, DirectIndirectE0, WRAP_NONE, CMP)
348rOPM (D2Slow, DirectIndirectSlow, WRAP_NONE, CMP)
349
350rOP8 (C1E1, DirectIndexedIndirectE1, WRAP_NONE, CMP)
351rOP8 (C1E0M1, DirectIndexedIndirectE0, WRAP_NONE, CMP)
352rOP16(C1E0M0, DirectIndexedIndirectE0, WRAP_NONE, CMP)
353rOPM (C1Slow, DirectIndexedIndirectSlow, WRAP_NONE, CMP)
354
355rOP8 (D1E1, DirectIndirectIndexedE1, WRAP_NONE, CMP)
356rOP8 (D1E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, CMP)
357rOP16(D1E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, CMP)
358rOP8 (D1E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, CMP)
359rOP16(D1E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, CMP)
360rOPM (D1Slow, DirectIndirectIndexedSlow, WRAP_NONE, CMP)
361
362rOP8 (C7M1, DirectIndirectLong, WRAP_NONE, CMP)
363rOP16(C7M0, DirectIndirectLong, WRAP_NONE, CMP)
364rOPM (C7Slow, DirectIndirectLongSlow, WRAP_NONE, CMP)
365
366rOP8 (D7M1, DirectIndirectIndexedLong, WRAP_NONE, CMP)
367rOP16(D7M0, DirectIndirectIndexedLong, WRAP_NONE, CMP)
368rOPM (D7Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, CMP)
369
370rOP8 (CDM1, Absolute, WRAP_NONE, CMP)
371rOP16(CDM0, Absolute, WRAP_NONE, CMP)
372rOPM (CDSlow, AbsoluteSlow, WRAP_NONE, CMP)
373
374rOP8 (DDM1X1, AbsoluteIndexedXX1, WRAP_NONE, CMP)
375rOP16(DDM0X1, AbsoluteIndexedXX1, WRAP_NONE, CMP)
376rOP8 (DDM1X0, AbsoluteIndexedXX0, WRAP_NONE, CMP)
377rOP16(DDM0X0, AbsoluteIndexedXX0, WRAP_NONE, CMP)
378rOPM (DDSlow, AbsoluteIndexedXSlow, WRAP_NONE, CMP)
379
380rOP8 (D9M1X1, AbsoluteIndexedYX1, WRAP_NONE, CMP)
381rOP16(D9M0X1, AbsoluteIndexedYX1, WRAP_NONE, CMP)
382rOP8 (D9M1X0, AbsoluteIndexedYX0, WRAP_NONE, CMP)
383rOP16(D9M0X0, AbsoluteIndexedYX0, WRAP_NONE, CMP)
384rOPM (D9Slow, AbsoluteIndexedYSlow, WRAP_NONE, CMP)
385
386rOP8 (CFM1, AbsoluteLong, WRAP_NONE, CMP)
387rOP16(CFM0, AbsoluteLong, WRAP_NONE, CMP)
388rOPM (CFSlow, AbsoluteLongSlow, WRAP_NONE, CMP)
389
390rOP8 (DFM1, AbsoluteLongIndexedX, WRAP_NONE, CMP)
391rOP16(DFM0, AbsoluteLongIndexedX, WRAP_NONE, CMP)
392rOPM (DFSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, CMP)
393
394rOP8 (C3M1, StackRelative, WRAP_NONE, CMP)
395rOP16(C3M0, StackRelative, WRAP_NONE, CMP)
396rOPM (C3Slow, StackRelativeSlow, WRAP_NONE, CMP)
397
398rOP8 (D3M1, StackRelativeIndirectIndexed, WRAP_NONE, CMP)
399rOP16(D3M0, StackRelativeIndirectIndexed, WRAP_NONE, CMP)
400rOPM (D3Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, CMP)
401
402/* CPX ********************************************************************* */
403
404static void OpE0X1 (void)
405{
406 int16 Int16 = (int16) Registers.XL - (int16) Immediate8(READ);
407 ICPU._Carry = Int16 >= 0;
408 SetZN((uint8) Int16);
409}
410
411static void OpE0X0 (void)
412{
413 int32 Int32 = (int32) Registers.X.W - (int32) Immediate16(READ);
414 ICPU._Carry = Int32 >= 0;
415 SetZN((uint16) Int32);
416}
417
418static void OpE0Slow (void)
419{
420 if (CheckIndex())
421 {
422 int16 Int16 = (int16) Registers.XL - (int16) Immediate8Slow(READ);
423 ICPU._Carry = Int16 >= 0;
424 SetZN((uint8) Int16);
425 }
426 else
427 {
428 int32 Int32 = (int32) Registers.X.W - (int32) Immediate16Slow(READ);
429 ICPU._Carry = Int32 >= 0;
430 SetZN((uint16) Int32);
431 }
432}
433
434rOP8 (E4X1, Direct, WRAP_BANK, CPX)
435rOP16(E4X0, Direct, WRAP_BANK, CPX)
436rOPX (E4Slow, DirectSlow, WRAP_BANK, CPX)
437
438rOP8 (ECX1, Absolute, WRAP_NONE, CPX)
439rOP16(ECX0, Absolute, WRAP_NONE, CPX)
440rOPX (ECSlow, AbsoluteSlow, WRAP_NONE, CPX)
441
442/* CPY ********************************************************************* */
443
444static void OpC0X1 (void)
445{
446 int16 Int16 = (int16) Registers.YL - (int16) Immediate8(READ);
447 ICPU._Carry = Int16 >= 0;
448 SetZN((uint8) Int16);
449}
450
451static void OpC0X0 (void)
452{
453 int32 Int32 = (int32) Registers.Y.W - (int32) Immediate16(READ);
454 ICPU._Carry = Int32 >= 0;
455 SetZN((uint16) Int32);
456}
457
458static void OpC0Slow (void)
459{
460 if (CheckIndex())
461 {
462 int16 Int16 = (int16) Registers.YL - (int16) Immediate8Slow(READ);
463 ICPU._Carry = Int16 >= 0;
464 SetZN((uint8) Int16);
465 }
466 else
467 {
468 int32 Int32 = (int32) Registers.Y.W - (int32) Immediate16Slow(READ);
469 ICPU._Carry = Int32 >= 0;
470 SetZN((uint16) Int32);
471 }
472}
473
474rOP8 (C4X1, Direct, WRAP_BANK, CPY)
475rOP16(C4X0, Direct, WRAP_BANK, CPY)
476rOPX (C4Slow, DirectSlow, WRAP_BANK, CPY)
477
478rOP8 (CCX1, Absolute, WRAP_NONE, CPY)
479rOP16(CCX0, Absolute, WRAP_NONE, CPY)
480rOPX (CCSlow, AbsoluteSlow, WRAP_NONE, CPY)
481
482/* DEC ********************************************************************* */
483
484static void Op3AM1 (void)
485{
486 AddCycles(ONE_CYCLE);
487 Registers.AL--;
488 SetZN(Registers.AL);
489}
490
491static void Op3AM0 (void)
492{
493 AddCycles(ONE_CYCLE);
494 Registers.A.W--;
495 SetZN(Registers.A.W);
496}
497
498static void Op3ASlow (void)
499{
500 AddCycles(ONE_CYCLE);
501
502 if (CheckMemory())
503 {
504 Registers.AL--;
505 SetZN(Registers.AL);
506 }
507 else
508 {
509 Registers.A.W--;
510 SetZN(Registers.A.W);
511 }
512}
513
514mOP8 (C6M1, Direct, WRAP_BANK, DEC)
515mOP16(C6M0, Direct, WRAP_BANK, DEC)
516mOPM (C6Slow, DirectSlow, WRAP_BANK, DEC)
517
518mOP8 (D6E1, DirectIndexedXE1, WRAP_BANK, DEC)
519mOP8 (D6E0M1, DirectIndexedXE0, WRAP_BANK, DEC)
520mOP16(D6E0M0, DirectIndexedXE0, WRAP_BANK, DEC)
521mOPM (D6Slow, DirectIndexedXSlow, WRAP_BANK, DEC)
522
523mOP8 (CEM1, Absolute, WRAP_NONE, DEC)
524mOP16(CEM0, Absolute, WRAP_NONE, DEC)
525mOPM (CESlow, AbsoluteSlow, WRAP_NONE, DEC)
526
527mOP8 (DEM1X1, AbsoluteIndexedXX1, WRAP_NONE, DEC)
528mOP16(DEM0X1, AbsoluteIndexedXX1, WRAP_NONE, DEC)
529mOP8 (DEM1X0, AbsoluteIndexedXX0, WRAP_NONE, DEC)
530mOP16(DEM0X0, AbsoluteIndexedXX0, WRAP_NONE, DEC)
531mOPM (DESlow, AbsoluteIndexedXSlow, WRAP_NONE, DEC)
532
533/* EOR ********************************************************************* */
534
535static void Op49M1 (void)
536{
537 Registers.AL ^= Immediate8(READ);
538 SetZN(Registers.AL);
539}
540
541static void Op49M0 (void)
542{
543 Registers.A.W ^= Immediate16(READ);
544 SetZN(Registers.A.W);
545}
546
547static void Op49Slow (void)
548{
549 if (CheckMemory())
550 {
551 Registers.AL ^= Immediate8Slow(READ);
552 SetZN(Registers.AL);
553 }
554 else
555 {
556 Registers.A.W ^= Immediate16Slow(READ);
557 SetZN(Registers.A.W);
558 }
559}
560
561rOP8 (45M1, Direct, WRAP_BANK, EOR)
562rOP16(45M0, Direct, WRAP_BANK, EOR)
563rOPM (45Slow, DirectSlow, WRAP_BANK, EOR)
564
565rOP8 (55E1, DirectIndexedXE1, WRAP_BANK, EOR)
566rOP8 (55E0M1, DirectIndexedXE0, WRAP_BANK, EOR)
567rOP16(55E0M0, DirectIndexedXE0, WRAP_BANK, EOR)
568rOPM (55Slow, DirectIndexedXSlow, WRAP_BANK, EOR)
569
570rOP8 (52E1, DirectIndirectE1, WRAP_NONE, EOR)
571rOP8 (52E0M1, DirectIndirectE0, WRAP_NONE, EOR)
572rOP16(52E0M0, DirectIndirectE0, WRAP_NONE, EOR)
573rOPM (52Slow, DirectIndirectSlow, WRAP_NONE, EOR)
574
575rOP8 (41E1, DirectIndexedIndirectE1, WRAP_NONE, EOR)
576rOP8 (41E0M1, DirectIndexedIndirectE0, WRAP_NONE, EOR)
577rOP16(41E0M0, DirectIndexedIndirectE0, WRAP_NONE, EOR)
578rOPM (41Slow, DirectIndexedIndirectSlow, WRAP_NONE, EOR)
579
580rOP8 (51E1, DirectIndirectIndexedE1, WRAP_NONE, EOR)
581rOP8 (51E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, EOR)
582rOP16(51E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, EOR)
583rOP8 (51E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, EOR)
584rOP16(51E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, EOR)
585rOPM (51Slow, DirectIndirectIndexedSlow, WRAP_NONE, EOR)
586
587rOP8 (47M1, DirectIndirectLong, WRAP_NONE, EOR)
588rOP16(47M0, DirectIndirectLong, WRAP_NONE, EOR)
589rOPM (47Slow, DirectIndirectLongSlow, WRAP_NONE, EOR)
590
591rOP8 (57M1, DirectIndirectIndexedLong, WRAP_NONE, EOR)
592rOP16(57M0, DirectIndirectIndexedLong, WRAP_NONE, EOR)
593rOPM (57Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, EOR)
594
595rOP8 (4DM1, Absolute, WRAP_NONE, EOR)
596rOP16(4DM0, Absolute, WRAP_NONE, EOR)
597rOPM (4DSlow, AbsoluteSlow, WRAP_NONE, EOR)
598
599rOP8 (5DM1X1, AbsoluteIndexedXX1, WRAP_NONE, EOR)
600rOP16(5DM0X1, AbsoluteIndexedXX1, WRAP_NONE, EOR)
601rOP8 (5DM1X0, AbsoluteIndexedXX0, WRAP_NONE, EOR)
602rOP16(5DM0X0, AbsoluteIndexedXX0, WRAP_NONE, EOR)
603rOPM (5DSlow, AbsoluteIndexedXSlow, WRAP_NONE, EOR)
604
605rOP8 (59M1X1, AbsoluteIndexedYX1, WRAP_NONE, EOR)
606rOP16(59M0X1, AbsoluteIndexedYX1, WRAP_NONE, EOR)
607rOP8 (59M1X0, AbsoluteIndexedYX0, WRAP_NONE, EOR)
608rOP16(59M0X0, AbsoluteIndexedYX0, WRAP_NONE, EOR)
609rOPM (59Slow, AbsoluteIndexedYSlow, WRAP_NONE, EOR)
610
611rOP8 (4FM1, AbsoluteLong, WRAP_NONE, EOR)
612rOP16(4FM0, AbsoluteLong, WRAP_NONE, EOR)
613rOPM (4FSlow, AbsoluteLongSlow, WRAP_NONE, EOR)
614
615rOP8 (5FM1, AbsoluteLongIndexedX, WRAP_NONE, EOR)
616rOP16(5FM0, AbsoluteLongIndexedX, WRAP_NONE, EOR)
617rOPM (5FSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, EOR)
618
619rOP8 (43M1, StackRelative, WRAP_NONE, EOR)
620rOP16(43M0, StackRelative, WRAP_NONE, EOR)
621rOPM (43Slow, StackRelativeSlow, WRAP_NONE, EOR)
622
623rOP8 (53M1, StackRelativeIndirectIndexed, WRAP_NONE, EOR)
624rOP16(53M0, StackRelativeIndirectIndexed, WRAP_NONE, EOR)
625rOPM (53Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, EOR)
626
627/* INC ********************************************************************* */
628
629static void Op1AM1 (void)
630{
631 AddCycles(ONE_CYCLE);
632 Registers.AL++;
633 SetZN(Registers.AL);
634}
635
636static void Op1AM0 (void)
637{
638 AddCycles(ONE_CYCLE);
639 Registers.A.W++;
640 SetZN(Registers.A.W);
641}
642
643static void Op1ASlow (void)
644{
645 AddCycles(ONE_CYCLE);
646
647 if (CheckMemory())
648 {
649 Registers.AL++;
650 SetZN(Registers.AL);
651 }
652 else
653 {
654 Registers.A.W++;
655 SetZN(Registers.A.W);
656 }
657}
658
659mOP8 (E6M1, Direct, WRAP_BANK, INC)
660mOP16(E6M0, Direct, WRAP_BANK, INC)
661mOPM (E6Slow, DirectSlow, WRAP_BANK, INC)
662
663mOP8 (F6E1, DirectIndexedXE1, WRAP_BANK, INC)
664mOP8 (F6E0M1, DirectIndexedXE0, WRAP_BANK, INC)
665mOP16(F6E0M0, DirectIndexedXE0, WRAP_BANK, INC)
666mOPM (F6Slow, DirectIndexedXSlow, WRAP_BANK, INC)
667
668mOP8 (EEM1, Absolute, WRAP_NONE, INC)
669mOP16(EEM0, Absolute, WRAP_NONE, INC)
670mOPM (EESlow, AbsoluteSlow, WRAP_NONE, INC)
671
672mOP8 (FEM1X1, AbsoluteIndexedXX1, WRAP_NONE, INC)
673mOP16(FEM0X1, AbsoluteIndexedXX1, WRAP_NONE, INC)
674mOP8 (FEM1X0, AbsoluteIndexedXX0, WRAP_NONE, INC)
675mOP16(FEM0X0, AbsoluteIndexedXX0, WRAP_NONE, INC)
676mOPM (FESlow, AbsoluteIndexedXSlow, WRAP_NONE, INC)
677
678/* LDA ********************************************************************* */
679
680static void OpA9M1 (void)
681{
682 Registers.AL = Immediate8(READ);
683 SetZN(Registers.AL);
684}
685
686static void OpA9M0 (void)
687{
688 Registers.A.W = Immediate16(READ);
689 SetZN(Registers.A.W);
690}
691
692static void OpA9Slow (void)
693{
694 if (CheckMemory())
695 {
696 Registers.AL = Immediate8Slow(READ);
697 SetZN(Registers.AL);
698 }
699 else
700 {
701 Registers.A.W = Immediate16Slow(READ);
702 SetZN(Registers.A.W);
703 }
704}
705
706rOP8 (A5M1, Direct, WRAP_BANK, LDA)
707rOP16(A5M0, Direct, WRAP_BANK, LDA)
708rOPM (A5Slow, DirectSlow, WRAP_BANK, LDA)
709
710rOP8 (B5E1, DirectIndexedXE1, WRAP_BANK, LDA)
711rOP8 (B5E0M1, DirectIndexedXE0, WRAP_BANK, LDA)
712rOP16(B5E0M0, DirectIndexedXE0, WRAP_BANK, LDA)
713rOPM (B5Slow, DirectIndexedXSlow, WRAP_BANK, LDA)
714
715rOP8 (B2E1, DirectIndirectE1, WRAP_NONE, LDA)
716rOP8 (B2E0M1, DirectIndirectE0, WRAP_NONE, LDA)
717rOP16(B2E0M0, DirectIndirectE0, WRAP_NONE, LDA)
718rOPM (B2Slow, DirectIndirectSlow, WRAP_NONE, LDA)
719
720rOP8 (A1E1, DirectIndexedIndirectE1, WRAP_NONE, LDA)
721rOP8 (A1E0M1, DirectIndexedIndirectE0, WRAP_NONE, LDA)
722rOP16(A1E0M0, DirectIndexedIndirectE0, WRAP_NONE, LDA)
723rOPM (A1Slow, DirectIndexedIndirectSlow, WRAP_NONE, LDA)
724
725rOP8 (B1E1, DirectIndirectIndexedE1, WRAP_NONE, LDA)
726rOP8 (B1E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, LDA)
727rOP16(B1E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, LDA)
728rOP8 (B1E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, LDA)
729rOP16(B1E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, LDA)
730rOPM (B1Slow, DirectIndirectIndexedSlow, WRAP_NONE, LDA)
731
732rOP8 (A7M1, DirectIndirectLong, WRAP_NONE, LDA)
733rOP16(A7M0, DirectIndirectLong, WRAP_NONE, LDA)
734rOPM (A7Slow, DirectIndirectLongSlow, WRAP_NONE, LDA)
735
736rOP8 (B7M1, DirectIndirectIndexedLong, WRAP_NONE, LDA)
737rOP16(B7M0, DirectIndirectIndexedLong, WRAP_NONE, LDA)
738rOPM (B7Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, LDA)
739
740rOP8 (ADM1, Absolute, WRAP_NONE, LDA)
741rOP16(ADM0, Absolute, WRAP_NONE, LDA)
742rOPM (ADSlow, AbsoluteSlow, WRAP_NONE, LDA)
743
744rOP8 (BDM1X1, AbsoluteIndexedXX1, WRAP_NONE, LDA)
745rOP16(BDM0X1, AbsoluteIndexedXX1, WRAP_NONE, LDA)
746rOP8 (BDM1X0, AbsoluteIndexedXX0, WRAP_NONE, LDA)
747rOP16(BDM0X0, AbsoluteIndexedXX0, WRAP_NONE, LDA)
748rOPM (BDSlow, AbsoluteIndexedXSlow, WRAP_NONE, LDA)
749
750rOP8 (B9M1X1, AbsoluteIndexedYX1, WRAP_NONE, LDA)
751rOP16(B9M0X1, AbsoluteIndexedYX1, WRAP_NONE, LDA)
752rOP8 (B9M1X0, AbsoluteIndexedYX0, WRAP_NONE, LDA)
753rOP16(B9M0X0, AbsoluteIndexedYX0, WRAP_NONE, LDA)
754rOPM (B9Slow, AbsoluteIndexedYSlow, WRAP_NONE, LDA)
755
756rOP8 (AFM1, AbsoluteLong, WRAP_NONE, LDA)
757rOP16(AFM0, AbsoluteLong, WRAP_NONE, LDA)
758rOPM (AFSlow, AbsoluteLongSlow, WRAP_NONE, LDA)
759
760rOP8 (BFM1, AbsoluteLongIndexedX, WRAP_NONE, LDA)
761rOP16(BFM0, AbsoluteLongIndexedX, WRAP_NONE, LDA)
762rOPM (BFSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, LDA)
763
764rOP8 (A3M1, StackRelative, WRAP_NONE, LDA)
765rOP16(A3M0, StackRelative, WRAP_NONE, LDA)
766rOPM (A3Slow, StackRelativeSlow, WRAP_NONE, LDA)
767
768rOP8 (B3M1, StackRelativeIndirectIndexed, WRAP_NONE, LDA)
769rOP16(B3M0, StackRelativeIndirectIndexed, WRAP_NONE, LDA)
770rOPM (B3Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, LDA)
771
772/* LDX ********************************************************************* */
773
774static void OpA2X1 (void)
775{
776 Registers.XL = Immediate8(READ);
777 SetZN(Registers.XL);
778}
779
780static void OpA2X0 (void)
781{
782 Registers.X.W = Immediate16(READ);
783 SetZN(Registers.X.W);
784}
785
786static void OpA2Slow (void)
787{
788 if (CheckIndex())
789 {
790 Registers.XL = Immediate8Slow(READ);
791 SetZN(Registers.XL);
792 }
793 else
794 {
795 Registers.X.W = Immediate16Slow(READ);
796 SetZN(Registers.X.W);
797 }
798}
799
800rOP8 (A6X1, Direct, WRAP_BANK, LDX)
801rOP16(A6X0, Direct, WRAP_BANK, LDX)
802rOPX (A6Slow, DirectSlow, WRAP_BANK, LDX)
803
804rOP8 (B6E1, DirectIndexedYE1, WRAP_BANK, LDX)
805rOP8 (B6E0X1, DirectIndexedYE0, WRAP_BANK, LDX)
806rOP16(B6E0X0, DirectIndexedYE0, WRAP_BANK, LDX)
807rOPX (B6Slow, DirectIndexedYSlow, WRAP_BANK, LDX)
808
809rOP8 (AEX1, Absolute, WRAP_BANK, LDX)
810rOP16(AEX0, Absolute, WRAP_BANK, LDX)
811rOPX (AESlow, AbsoluteSlow, WRAP_BANK, LDX)
812
813rOP8 (BEX1, AbsoluteIndexedYX1, WRAP_BANK, LDX)
814rOP16(BEX0, AbsoluteIndexedYX0, WRAP_BANK, LDX)
815rOPX (BESlow, AbsoluteIndexedYSlow, WRAP_BANK, LDX)
816
817/* LDY ********************************************************************* */
818
819static void OpA0X1 (void)
820{
821 Registers.YL = Immediate8(READ);
822 SetZN(Registers.YL);
823}
824
825static void OpA0X0 (void)
826{
827 Registers.Y.W = Immediate16(READ);
828 SetZN(Registers.Y.W);
829}
830
831static void OpA0Slow (void)
832{
833 if (CheckIndex())
834 {
835 Registers.YL = Immediate8Slow(READ);
836 SetZN(Registers.YL);
837 }
838 else
839 {
840 Registers.Y.W = Immediate16Slow(READ);
841 SetZN(Registers.Y.W);
842 }
843}
844
845rOP8 (A4X1, Direct, WRAP_BANK, LDY)
846rOP16(A4X0, Direct, WRAP_BANK, LDY)
847rOPX (A4Slow, DirectSlow, WRAP_BANK, LDY)
848
849rOP8 (B4E1, DirectIndexedXE1, WRAP_BANK, LDY)
850rOP8 (B4E0X1, DirectIndexedXE0, WRAP_BANK, LDY)
851rOP16(B4E0X0, DirectIndexedXE0, WRAP_BANK, LDY)
852rOPX (B4Slow, DirectIndexedXSlow, WRAP_BANK, LDY)
853
854rOP8 (ACX1, Absolute, WRAP_BANK, LDY)
855rOP16(ACX0, Absolute, WRAP_BANK, LDY)
856rOPX (ACSlow, AbsoluteSlow, WRAP_BANK, LDY)
857
858rOP8 (BCX1, AbsoluteIndexedXX1, WRAP_BANK, LDY)
859rOP16(BCX0, AbsoluteIndexedXX0, WRAP_BANK, LDY)
860rOPX (BCSlow, AbsoluteIndexedXSlow, WRAP_BANK, LDY)
861
862/* LSR ********************************************************************* */
863
864static void Op4AM1 (void)
865{
866 AddCycles(ONE_CYCLE);
867 ICPU._Carry = Registers.AL & 1;
868 Registers.AL >>= 1;
869 SetZN(Registers.AL);
870}
871
872static void Op4AM0 (void)
873{
874 AddCycles(ONE_CYCLE);
875 ICPU._Carry = Registers.A.W & 1;
876 Registers.A.W >>= 1;
877 SetZN(Registers.A.W);
878}
879
880static void Op4ASlow (void)
881{
882 AddCycles(ONE_CYCLE);
883
884 if (CheckMemory())
885 {
886 ICPU._Carry = Registers.AL & 1;
887 Registers.AL >>= 1;
888 SetZN(Registers.AL);
889 }
890 else
891 {
892 ICPU._Carry = Registers.A.W & 1;
893 Registers.A.W >>= 1;
894 SetZN(Registers.A.W);
895 }
896}
897
898mOP8 (46M1, Direct, WRAP_BANK, LSR)
899mOP16(46M0, Direct, WRAP_BANK, LSR)
900mOPM (46Slow, DirectSlow, WRAP_BANK, LSR)
901
902mOP8 (56E1, DirectIndexedXE1, WRAP_BANK, LSR)
903mOP8 (56E0M1, DirectIndexedXE0, WRAP_BANK, LSR)
904mOP16(56E0M0, DirectIndexedXE0, WRAP_BANK, LSR)
905mOPM (56Slow, DirectIndexedXSlow, WRAP_BANK, LSR)
906
907mOP8 (4EM1, Absolute, WRAP_NONE, LSR)
908mOP16(4EM0, Absolute, WRAP_NONE, LSR)
909mOPM (4ESlow, AbsoluteSlow, WRAP_NONE, LSR)
910
911mOP8 (5EM1X1, AbsoluteIndexedXX1, WRAP_NONE, LSR)
912mOP16(5EM0X1, AbsoluteIndexedXX1, WRAP_NONE, LSR)
913mOP8 (5EM1X0, AbsoluteIndexedXX0, WRAP_NONE, LSR)
914mOP16(5EM0X0, AbsoluteIndexedXX0, WRAP_NONE, LSR)
915mOPM (5ESlow, AbsoluteIndexedXSlow, WRAP_NONE, LSR)
916
917/* ORA ********************************************************************* */
918
919static void Op09M1 (void)
920{
921 Registers.AL |= Immediate8(READ);
922 SetZN(Registers.AL);
923}
924
925static void Op09M0 (void)
926{
927 Registers.A.W |= Immediate16(READ);
928 SetZN(Registers.A.W);
929}
930
931static void Op09Slow (void)
932{
933 if (CheckMemory())
934 {
935 Registers.AL |= Immediate8Slow(READ);
936 SetZN(Registers.AL);
937 }
938 else
939 {
940 Registers.A.W |= Immediate16Slow(READ);
941 SetZN(Registers.A.W);
942 }
943}
944
945rOP8 (05M1, Direct, WRAP_BANK, ORA)
946rOP16(05M0, Direct, WRAP_BANK, ORA)
947rOPM (05Slow, DirectSlow, WRAP_BANK, ORA)
948
949rOP8 (15E1, DirectIndexedXE1, WRAP_BANK, ORA)
950rOP8 (15E0M1, DirectIndexedXE0, WRAP_BANK, ORA)
951rOP16(15E0M0, DirectIndexedXE0, WRAP_BANK, ORA)
952rOPM (15Slow, DirectIndexedXSlow, WRAP_BANK, ORA)
953
954rOP8 (12E1, DirectIndirectE1, WRAP_NONE, ORA)
955rOP8 (12E0M1, DirectIndirectE0, WRAP_NONE, ORA)
956rOP16(12E0M0, DirectIndirectE0, WRAP_NONE, ORA)
957rOPM (12Slow, DirectIndirectSlow, WRAP_NONE, ORA)
958
959rOP8 (01E1, DirectIndexedIndirectE1, WRAP_NONE, ORA)
960rOP8 (01E0M1, DirectIndexedIndirectE0, WRAP_NONE, ORA)
961rOP16(01E0M0, DirectIndexedIndirectE0, WRAP_NONE, ORA)
962rOPM (01Slow, DirectIndexedIndirectSlow, WRAP_NONE, ORA)
963
964rOP8 (11E1, DirectIndirectIndexedE1, WRAP_NONE, ORA)
965rOP8 (11E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, ORA)
966rOP16(11E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, ORA)
967rOP8 (11E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, ORA)
968rOP16(11E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, ORA)
969rOPM (11Slow, DirectIndirectIndexedSlow, WRAP_NONE, ORA)
970
971rOP8 (07M1, DirectIndirectLong, WRAP_NONE, ORA)
972rOP16(07M0, DirectIndirectLong, WRAP_NONE, ORA)
973rOPM (07Slow, DirectIndirectLongSlow, WRAP_NONE, ORA)
974
975rOP8 (17M1, DirectIndirectIndexedLong, WRAP_NONE, ORA)
976rOP16(17M0, DirectIndirectIndexedLong, WRAP_NONE, ORA)
977rOPM (17Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, ORA)
978
979rOP8 (0DM1, Absolute, WRAP_NONE, ORA)
980rOP16(0DM0, Absolute, WRAP_NONE, ORA)
981rOPM (0DSlow, AbsoluteSlow, WRAP_NONE, ORA)
982
983rOP8 (1DM1X1, AbsoluteIndexedXX1, WRAP_NONE, ORA)
984rOP16(1DM0X1, AbsoluteIndexedXX1, WRAP_NONE, ORA)
985rOP8 (1DM1X0, AbsoluteIndexedXX0, WRAP_NONE, ORA)
986rOP16(1DM0X0, AbsoluteIndexedXX0, WRAP_NONE, ORA)
987rOPM (1DSlow, AbsoluteIndexedXSlow, WRAP_NONE, ORA)
988
989rOP8 (19M1X1, AbsoluteIndexedYX1, WRAP_NONE, ORA)
990rOP16(19M0X1, AbsoluteIndexedYX1, WRAP_NONE, ORA)
991rOP8 (19M1X0, AbsoluteIndexedYX0, WRAP_NONE, ORA)
992rOP16(19M0X0, AbsoluteIndexedYX0, WRAP_NONE, ORA)
993rOPM (19Slow, AbsoluteIndexedYSlow, WRAP_NONE, ORA)
994
995rOP8 (0FM1, AbsoluteLong, WRAP_NONE, ORA)
996rOP16(0FM0, AbsoluteLong, WRAP_NONE, ORA)
997rOPM (0FSlow, AbsoluteLongSlow, WRAP_NONE, ORA)
998
999rOP8 (1FM1, AbsoluteLongIndexedX, WRAP_NONE, ORA)
1000rOP16(1FM0, AbsoluteLongIndexedX, WRAP_NONE, ORA)
1001rOPM (1FSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, ORA)
1002
1003rOP8 (03M1, StackRelative, WRAP_NONE, ORA)
1004rOP16(03M0, StackRelative, WRAP_NONE, ORA)
1005rOPM (03Slow, StackRelativeSlow, WRAP_NONE, ORA)
1006
1007rOP8 (13M1, StackRelativeIndirectIndexed, WRAP_NONE, ORA)
1008rOP16(13M0, StackRelativeIndirectIndexed, WRAP_NONE, ORA)
1009rOPM (13Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, ORA)
1010
1011/* ROL ********************************************************************* */
1012
1013static void Op2AM1 (void)
1014{
1015 AddCycles(ONE_CYCLE);
1016 uint16 w = (((uint16) Registers.AL) << 1) | CheckCarry();
1017 ICPU._Carry = w >= 0x100;
1018 Registers.AL = (uint8) w;
1019 SetZN(Registers.AL);
1020}
1021
1022static void Op2AM0 (void)
1023{
1024 AddCycles(ONE_CYCLE);
1025 uint32 w = (((uint32) Registers.A.W) << 1) | CheckCarry();
1026 ICPU._Carry = w >= 0x10000;
1027 Registers.A.W = (uint16) w;
1028 SetZN(Registers.A.W);
1029}
1030
1031static void Op2ASlow (void)
1032{
1033 AddCycles(ONE_CYCLE);
1034
1035 if (CheckMemory())
1036 {
1037 uint16 w = (((uint16) Registers.AL) << 1) | CheckCarry();
1038 ICPU._Carry = w >= 0x100;
1039 Registers.AL = (uint8) w;
1040 SetZN(Registers.AL);
1041 }
1042 else
1043 {
1044 uint32 w = (((uint32) Registers.A.W) << 1) | CheckCarry();
1045 ICPU._Carry = w >= 0x10000;
1046 Registers.A.W = (uint16) w;
1047 SetZN(Registers.A.W);
1048 }
1049}
1050
1051mOP8 (26M1, Direct, WRAP_BANK, ROL)
1052mOP16(26M0, Direct, WRAP_BANK, ROL)
1053mOPM (26Slow, DirectSlow, WRAP_BANK, ROL)
1054
1055mOP8 (36E1, DirectIndexedXE1, WRAP_BANK, ROL)
1056mOP8 (36E0M1, DirectIndexedXE0, WRAP_BANK, ROL)
1057mOP16(36E0M0, DirectIndexedXE0, WRAP_BANK, ROL)
1058mOPM (36Slow, DirectIndexedXSlow, WRAP_BANK, ROL)
1059
1060mOP8 (2EM1, Absolute, WRAP_NONE, ROL)
1061mOP16(2EM0, Absolute, WRAP_NONE, ROL)
1062mOPM (2ESlow, AbsoluteSlow, WRAP_NONE, ROL)
1063
1064mOP8 (3EM1X1, AbsoluteIndexedXX1, WRAP_NONE, ROL)
1065mOP16(3EM0X1, AbsoluteIndexedXX1, WRAP_NONE, ROL)
1066mOP8 (3EM1X0, AbsoluteIndexedXX0, WRAP_NONE, ROL)
1067mOP16(3EM0X0, AbsoluteIndexedXX0, WRAP_NONE, ROL)
1068mOPM (3ESlow, AbsoluteIndexedXSlow, WRAP_NONE, ROL)
1069
1070/* ROR ********************************************************************* */
1071
1072static void Op6AM1 (void)
1073{
1074 AddCycles(ONE_CYCLE);
1075 uint16 w = ((uint16) Registers.AL) | (((uint16) CheckCarry()) << 8);
1076 ICPU._Carry = w & 1;
1077 w >>= 1;
1078 Registers.AL = (uint8) w;
1079 SetZN(Registers.AL);
1080}
1081
1082static void Op6AM0 (void)
1083{
1084 AddCycles(ONE_CYCLE);
1085 uint32 w = ((uint32) Registers.A.W) | (((uint32) CheckCarry()) << 16);
1086 ICPU._Carry = w & 1;
1087 w >>= 1;
1088 Registers.A.W = (uint16) w;
1089 SetZN(Registers.A.W);
1090}
1091
1092static void Op6ASlow (void)
1093{
1094 AddCycles(ONE_CYCLE);
1095
1096 if (CheckMemory())
1097 {
1098 uint16 w = ((uint16) Registers.AL) | (((uint16) CheckCarry()) << 8);
1099 ICPU._Carry = w & 1;
1100 w >>= 1;
1101 Registers.AL = (uint8) w;
1102 SetZN(Registers.AL);
1103 }
1104 else
1105 {
1106 uint32 w = ((uint32) Registers.A.W) | (((uint32) CheckCarry()) << 16);
1107 ICPU._Carry = w & 1;
1108 w >>= 1;
1109 Registers.A.W = (uint16) w;
1110 SetZN(Registers.A.W);
1111 }
1112}
1113
1114mOP8 (66M1, Direct, WRAP_BANK, ROR)
1115mOP16(66M0, Direct, WRAP_BANK, ROR)
1116mOPM (66Slow, DirectSlow, WRAP_BANK, ROR)
1117
1118mOP8 (76E1, DirectIndexedXE1, WRAP_BANK, ROR)
1119mOP8 (76E0M1, DirectIndexedXE0, WRAP_BANK, ROR)
1120mOP16(76E0M0, DirectIndexedXE0, WRAP_BANK, ROR)
1121mOPM (76Slow, DirectIndexedXSlow, WRAP_BANK, ROR)
1122
1123mOP8 (6EM1, Absolute, WRAP_NONE, ROR)
1124mOP16(6EM0, Absolute, WRAP_NONE, ROR)
1125mOPM (6ESlow, AbsoluteSlow, WRAP_NONE, ROR)
1126
1127mOP8 (7EM1X1, AbsoluteIndexedXX1, WRAP_NONE, ROR)
1128mOP16(7EM0X1, AbsoluteIndexedXX1, WRAP_NONE, ROR)
1129mOP8 (7EM1X0, AbsoluteIndexedXX0, WRAP_NONE, ROR)
1130mOP16(7EM0X0, AbsoluteIndexedXX0, WRAP_NONE, ROR)
1131mOPM (7ESlow, AbsoluteIndexedXSlow, WRAP_NONE, ROR)
1132
1133/* SBC ********************************************************************* */
1134
1135static void OpE9M1 (void)
1136{
1137 SBC(Immediate8(READ));
1138}
1139
1140static void OpE9M0 (void)
1141{
1142 SBC(Immediate16(READ));
1143}
1144
1145static void OpE9Slow (void)
1146{
1147 if (CheckMemory())
1148 SBC(Immediate8Slow(READ));
1149 else
1150 SBC(Immediate16Slow(READ));
1151}
1152
1153rOP8 (E5M1, Direct, WRAP_BANK, SBC)
1154rOP16(E5M0, Direct, WRAP_BANK, SBC)
1155rOPM (E5Slow, DirectSlow, WRAP_BANK, SBC)
1156
1157rOP8 (F5E1, DirectIndexedXE1, WRAP_BANK, SBC)
1158rOP8 (F5E0M1, DirectIndexedXE0, WRAP_BANK, SBC)
1159rOP16(F5E0M0, DirectIndexedXE0, WRAP_BANK, SBC)
1160rOPM (F5Slow, DirectIndexedXSlow, WRAP_BANK, SBC)
1161
1162rOP8 (F2E1, DirectIndirectE1, WRAP_NONE, SBC)
1163rOP8 (F2E0M1, DirectIndirectE0, WRAP_NONE, SBC)
1164rOP16(F2E0M0, DirectIndirectE0, WRAP_NONE, SBC)
1165rOPM (F2Slow, DirectIndirectSlow, WRAP_NONE, SBC)
1166
1167rOP8 (E1E1, DirectIndexedIndirectE1, WRAP_NONE, SBC)
1168rOP8 (E1E0M1, DirectIndexedIndirectE0, WRAP_NONE, SBC)
1169rOP16(E1E0M0, DirectIndexedIndirectE0, WRAP_NONE, SBC)
1170rOPM (E1Slow, DirectIndexedIndirectSlow, WRAP_NONE, SBC)
1171
1172rOP8 (F1E1, DirectIndirectIndexedE1, WRAP_NONE, SBC)
1173rOP8 (F1E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, SBC)
1174rOP16(F1E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, SBC)
1175rOP8 (F1E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, SBC)
1176rOP16(F1E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, SBC)
1177rOPM (F1Slow, DirectIndirectIndexedSlow, WRAP_NONE, SBC)
1178
1179rOP8 (E7M1, DirectIndirectLong, WRAP_NONE, SBC)
1180rOP16(E7M0, DirectIndirectLong, WRAP_NONE, SBC)
1181rOPM (E7Slow, DirectIndirectLongSlow, WRAP_NONE, SBC)
1182
1183rOP8 (F7M1, DirectIndirectIndexedLong, WRAP_NONE, SBC)
1184rOP16(F7M0, DirectIndirectIndexedLong, WRAP_NONE, SBC)
1185rOPM (F7Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, SBC)
1186
1187rOP8 (EDM1, Absolute, WRAP_NONE, SBC)
1188rOP16(EDM0, Absolute, WRAP_NONE, SBC)
1189rOPM (EDSlow, AbsoluteSlow, WRAP_NONE, SBC)
1190
1191rOP8 (FDM1X1, AbsoluteIndexedXX1, WRAP_NONE, SBC)
1192rOP16(FDM0X1, AbsoluteIndexedXX1, WRAP_NONE, SBC)
1193rOP8 (FDM1X0, AbsoluteIndexedXX0, WRAP_NONE, SBC)
1194rOP16(FDM0X0, AbsoluteIndexedXX0, WRAP_NONE, SBC)
1195rOPM (FDSlow, AbsoluteIndexedXSlow, WRAP_NONE, SBC)
1196
1197rOP8 (F9M1X1, AbsoluteIndexedYX1, WRAP_NONE, SBC)
1198rOP16(F9M0X1, AbsoluteIndexedYX1, WRAP_NONE, SBC)
1199rOP8 (F9M1X0, AbsoluteIndexedYX0, WRAP_NONE, SBC)
1200rOP16(F9M0X0, AbsoluteIndexedYX0, WRAP_NONE, SBC)
1201rOPM (F9Slow, AbsoluteIndexedYSlow, WRAP_NONE, SBC)
1202
1203rOP8 (EFM1, AbsoluteLong, WRAP_NONE, SBC)
1204rOP16(EFM0, AbsoluteLong, WRAP_NONE, SBC)
1205rOPM (EFSlow, AbsoluteLongSlow, WRAP_NONE, SBC)
1206
1207rOP8 (FFM1, AbsoluteLongIndexedX, WRAP_NONE, SBC)
1208rOP16(FFM0, AbsoluteLongIndexedX, WRAP_NONE, SBC)
1209rOPM (FFSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, SBC)
1210
1211rOP8 (E3M1, StackRelative, WRAP_NONE, SBC)
1212rOP16(E3M0, StackRelative, WRAP_NONE, SBC)
1213rOPM (E3Slow, StackRelativeSlow, WRAP_NONE, SBC)
1214
1215rOP8 (F3M1, StackRelativeIndirectIndexed, WRAP_NONE, SBC)
1216rOP16(F3M0, StackRelativeIndirectIndexed, WRAP_NONE, SBC)
1217rOPM (F3Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, SBC)
1218
1219/* STA ********************************************************************* */
1220
1221wOP8 (85M1, Direct, WRAP_BANK, STA)
1222wOP16(85M0, Direct, WRAP_BANK, STA)
1223wOPM (85Slow, DirectSlow, WRAP_BANK, STA)
1224
1225wOP8 (95E1, DirectIndexedXE1, WRAP_BANK, STA)
1226wOP8 (95E0M1, DirectIndexedXE0, WRAP_BANK, STA)
1227wOP16(95E0M0, DirectIndexedXE0, WRAP_BANK, STA)
1228wOPM (95Slow, DirectIndexedXSlow, WRAP_BANK, STA)
1229
1230wOP8 (92E1, DirectIndirectE1, WRAP_NONE, STA)
1231wOP8 (92E0M1, DirectIndirectE0, WRAP_NONE, STA)
1232wOP16(92E0M0, DirectIndirectE0, WRAP_NONE, STA)
1233wOPM (92Slow, DirectIndirectSlow, WRAP_NONE, STA)
1234
1235wOP8 (81E1, DirectIndexedIndirectE1, WRAP_NONE, STA)
1236wOP8 (81E0M1, DirectIndexedIndirectE0, WRAP_NONE, STA)
1237wOP16(81E0M0, DirectIndexedIndirectE0, WRAP_NONE, STA)
1238wOPM (81Slow, DirectIndexedIndirectSlow, WRAP_NONE, STA)
1239
1240wOP8 (91E1, DirectIndirectIndexedE1, WRAP_NONE, STA)
1241wOP8 (91E0M1X1, DirectIndirectIndexedE0X1, WRAP_NONE, STA)
1242wOP16(91E0M0X1, DirectIndirectIndexedE0X1, WRAP_NONE, STA)
1243wOP8 (91E0M1X0, DirectIndirectIndexedE0X0, WRAP_NONE, STA)
1244wOP16(91E0M0X0, DirectIndirectIndexedE0X0, WRAP_NONE, STA)
1245wOPM (91Slow, DirectIndirectIndexedSlow, WRAP_NONE, STA)
1246
1247wOP8 (87M1, DirectIndirectLong, WRAP_NONE, STA)
1248wOP16(87M0, DirectIndirectLong, WRAP_NONE, STA)
1249wOPM (87Slow, DirectIndirectLongSlow, WRAP_NONE, STA)
1250
1251wOP8 (97M1, DirectIndirectIndexedLong, WRAP_NONE, STA)
1252wOP16(97M0, DirectIndirectIndexedLong, WRAP_NONE, STA)
1253wOPM (97Slow, DirectIndirectIndexedLongSlow, WRAP_NONE, STA)
1254
1255wOP8 (8DM1, Absolute, WRAP_NONE, STA)
1256wOP16(8DM0, Absolute, WRAP_NONE, STA)
1257wOPM (8DSlow, AbsoluteSlow, WRAP_NONE, STA)
1258
1259wOP8 (9DM1X1, AbsoluteIndexedXX1, WRAP_NONE, STA)
1260wOP16(9DM0X1, AbsoluteIndexedXX1, WRAP_NONE, STA)
1261wOP8 (9DM1X0, AbsoluteIndexedXX0, WRAP_NONE, STA)
1262wOP16(9DM0X0, AbsoluteIndexedXX0, WRAP_NONE, STA)
1263wOPM (9DSlow, AbsoluteIndexedXSlow, WRAP_NONE, STA)
1264
1265wOP8 (99M1X1, AbsoluteIndexedYX1, WRAP_NONE, STA)
1266wOP16(99M0X1, AbsoluteIndexedYX1, WRAP_NONE, STA)
1267wOP8 (99M1X0, AbsoluteIndexedYX0, WRAP_NONE, STA)
1268wOP16(99M0X0, AbsoluteIndexedYX0, WRAP_NONE, STA)
1269wOPM (99Slow, AbsoluteIndexedYSlow, WRAP_NONE, STA)
1270
1271wOP8 (8FM1, AbsoluteLong, WRAP_NONE, STA)
1272wOP16(8FM0, AbsoluteLong, WRAP_NONE, STA)
1273wOPM (8FSlow, AbsoluteLongSlow, WRAP_NONE, STA)
1274
1275wOP8 (9FM1, AbsoluteLongIndexedX, WRAP_NONE, STA)
1276wOP16(9FM0, AbsoluteLongIndexedX, WRAP_NONE, STA)
1277wOPM (9FSlow, AbsoluteLongIndexedXSlow, WRAP_NONE, STA)
1278
1279wOP8 (83M1, StackRelative, WRAP_NONE, STA)
1280wOP16(83M0, StackRelative, WRAP_NONE, STA)
1281wOPM (83Slow, StackRelativeSlow, WRAP_NONE, STA)
1282
1283wOP8 (93M1, StackRelativeIndirectIndexed, WRAP_NONE, STA)
1284wOP16(93M0, StackRelativeIndirectIndexed, WRAP_NONE, STA)
1285wOPM (93Slow, StackRelativeIndirectIndexedSlow, WRAP_NONE, STA)
1286
1287/* STX ********************************************************************* */
1288
1289wOP8 (86X1, Direct, WRAP_BANK, STX)
1290wOP16(86X0, Direct, WRAP_BANK, STX)
1291wOPX (86Slow, DirectSlow, WRAP_BANK, STX)
1292
1293wOP8 (96E1, DirectIndexedYE1, WRAP_BANK, STX)
1294wOP8 (96E0X1, DirectIndexedYE0, WRAP_BANK, STX)
1295wOP16(96E0X0, DirectIndexedYE0, WRAP_BANK, STX)
1296wOPX (96Slow, DirectIndexedYSlow, WRAP_BANK, STX)
1297
1298wOP8 (8EX1, Absolute, WRAP_BANK, STX)
1299wOP16(8EX0, Absolute, WRAP_BANK, STX)
1300wOPX (8ESlow, AbsoluteSlow, WRAP_BANK, STX)
1301
1302/* STY ********************************************************************* */
1303
1304wOP8 (84X1, Direct, WRAP_BANK, STY)
1305wOP16(84X0, Direct, WRAP_BANK, STY)
1306wOPX (84Slow, DirectSlow, WRAP_BANK, STY)
1307
1308wOP8 (94E1, DirectIndexedXE1, WRAP_BANK, STY)
1309wOP8 (94E0X1, DirectIndexedXE0, WRAP_BANK, STY)
1310wOP16(94E0X0, DirectIndexedXE0, WRAP_BANK, STY)
1311wOPX (94Slow, DirectIndexedXSlow, WRAP_BANK, STY)
1312
1313wOP8 (8CX1, Absolute, WRAP_BANK, STY)
1314wOP16(8CX0, Absolute, WRAP_BANK, STY)
1315wOPX (8CSlow, AbsoluteSlow, WRAP_BANK, STY)
1316
1317/* STZ ********************************************************************* */
1318
1319wOP8 (64M1, Direct, WRAP_BANK, STZ)
1320wOP16(64M0, Direct, WRAP_BANK, STZ)
1321wOPM (64Slow, DirectSlow, WRAP_BANK, STZ)
1322
1323wOP8 (74E1, DirectIndexedXE1, WRAP_BANK, STZ)
1324wOP8 (74E0M1, DirectIndexedXE0, WRAP_BANK, STZ)
1325wOP16(74E0M0, DirectIndexedXE0, WRAP_BANK, STZ)
1326wOPM (74Slow, DirectIndexedXSlow, WRAP_BANK, STZ)
1327
1328wOP8 (9CM1, Absolute, WRAP_NONE, STZ)
1329wOP16(9CM0, Absolute, WRAP_NONE, STZ)
1330wOPM (9CSlow, AbsoluteSlow, WRAP_NONE, STZ)
1331
1332wOP8 (9EM1X1, AbsoluteIndexedXX1, WRAP_NONE, STZ)
1333wOP16(9EM0X1, AbsoluteIndexedXX1, WRAP_NONE, STZ)
1334wOP8 (9EM1X0, AbsoluteIndexedXX0, WRAP_NONE, STZ)
1335wOP16(9EM0X0, AbsoluteIndexedXX0, WRAP_NONE, STZ)
1336wOPM (9ESlow, AbsoluteIndexedXSlow, WRAP_NONE, STZ)
1337
1338/* TRB ********************************************************************* */
1339
1340mOP8 (14M1, Direct, WRAP_BANK, TRB)
1341mOP16(14M0, Direct, WRAP_BANK, TRB)
1342mOPM (14Slow, DirectSlow, WRAP_BANK, TRB)
1343
1344mOP8 (1CM1, Absolute, WRAP_BANK, TRB)
1345mOP16(1CM0, Absolute, WRAP_BANK, TRB)
1346mOPM (1CSlow, AbsoluteSlow, WRAP_BANK, TRB)
1347
1348/* TSB ********************************************************************* */
1349
1350mOP8 (04M1, Direct, WRAP_BANK, TSB)
1351mOP16(04M0, Direct, WRAP_BANK, TSB)
1352mOPM (04Slow, DirectSlow, WRAP_BANK, TSB)
1353
1354mOP8 (0CM1, Absolute, WRAP_BANK, TSB)
1355mOP16(0CM0, Absolute, WRAP_BANK, TSB)
1356mOPM (0CSlow, AbsoluteSlow, WRAP_BANK, TSB)
1357
1358/* Branch Instructions ***************************************************** */
1359
1360// BCC
1361bOP(90E0, Relative, !CheckCarry(), 0, 0)
1362bOP(90E1, Relative, !CheckCarry(), 0, 1)
1363bOP(90Slow, RelativeSlow, !CheckCarry(), 0, CheckEmulation())
1364
1365// BCS
1366bOP(B0E0, Relative, CheckCarry(), 0, 0)
1367bOP(B0E1, Relative, CheckCarry(), 0, 1)
1368bOP(B0Slow, RelativeSlow, CheckCarry(), 0, CheckEmulation())
1369
1370// BEQ
1371bOP(F0E0, Relative, CheckZero(), 2, 0)
1372bOP(F0E1, Relative, CheckZero(), 2, 1)
1373bOP(F0Slow, RelativeSlow, CheckZero(), 2, CheckEmulation())
1374
1375// BMI
1376bOP(30E0, Relative, CheckNegative(), 1, 0)
1377bOP(30E1, Relative, CheckNegative(), 1, 1)
1378bOP(30Slow, RelativeSlow, CheckNegative(), 1, CheckEmulation())
1379
1380// BNE
1381bOP(D0E0, Relative, !CheckZero(), 1, 0)
1382bOP(D0E1, Relative, !CheckZero(), 1, 1)
1383bOP(D0Slow, RelativeSlow, !CheckZero(), 1, CheckEmulation())
1384
1385// BPL
1386bOP(10E0, Relative, !CheckNegative(), 1, 0)
1387bOP(10E1, Relative, !CheckNegative(), 1, 1)
1388bOP(10Slow, RelativeSlow, !CheckNegative(), 1, CheckEmulation())
1389
1390// BRA
1391bOP(80E0, Relative, 1, X, 0)
1392bOP(80E1, Relative, 1, X, 1)
1393bOP(80Slow, RelativeSlow, 1, X, CheckEmulation())
1394
1395// BVC
1396bOP(50E0, Relative, !CheckOverflow(), 0, 0)
1397bOP(50E1, Relative, !CheckOverflow(), 0, 1)
1398bOP(50Slow, RelativeSlow, !CheckOverflow(), 0, CheckEmulation())
1399
1400// BVS
1401bOP(70E0, Relative, CheckOverflow(), 0, 0)
1402bOP(70E1, Relative, CheckOverflow(), 0, 1)
1403bOP(70Slow, RelativeSlow, CheckOverflow(), 0, CheckEmulation())
1404
1405// BRL
1406static void Op82 (void)
1407{
1408 S9xSetPCBase(ICPU.ShiftedPB + RelativeLong(JUMP));
1409}
1410
1411static void Op82Slow (void)
1412{
1413 S9xSetPCBase(ICPU.ShiftedPB + RelativeLongSlow(JUMP));
1414}
1415
1416/* Flag Instructions ******************************************************* */
1417
1418// CLC
1419static void Op18 (void)
1420{
1421 ClearCarry();
1422 AddCycles(ONE_CYCLE);
1423}
1424
1425// SEC
1426static void Op38 (void)
1427{
1428 SetCarry();
1429 AddCycles(ONE_CYCLE);
1430}
1431
1432// CLD
1433static void OpD8 (void)
1434{
1435 ClearDecimal();
1436 AddCycles(ONE_CYCLE);
1437}
1438
1439// SED
1440static void OpF8 (void)
1441{
1442 SetDecimal();
1443 AddCycles(ONE_CYCLE);
1444#ifdef DEBUGGER
1445 missing.decimal_mode = 1;
1446#endif
1447}
1448
1449// CLI
1450static void Op58 (void)
1451{
1452 AddCycles(ONE_CYCLE);
1453
1454#ifndef SA1_OPCODES
1455 Timings.IRQFlagChanging |= IRQ_CLEAR_FLAG;
1456#else
1457 ClearIRQ();
1458#endif
1459}
1460
1461// SEI
1462static void Op78 (void)
1463{
1464 AddCycles(ONE_CYCLE);
1465
1466#ifndef SA1_OPCODES
1467 Timings.IRQFlagChanging |= IRQ_SET_FLAG;
1468#else
1469 SetIRQ();
1470#endif
1471}
1472
1473// CLV
1474static void OpB8 (void)
1475{
1476 ClearOverflow();
1477 AddCycles(ONE_CYCLE);
1478}
1479
1480/* DEX/DEY ***************************************************************** */
1481
1482static void OpCAX1 (void)
1483{
1484 AddCycles(ONE_CYCLE);
1485 Registers.XL--;
1486 SetZN(Registers.XL);
1487}
1488
1489static void OpCAX0 (void)
1490{
1491 AddCycles(ONE_CYCLE);
1492 Registers.X.W--;
1493 SetZN(Registers.X.W);
1494}
1495
1496static void OpCASlow (void)
1497{
1498 AddCycles(ONE_CYCLE);
1499
1500 if (CheckIndex())
1501 {
1502 Registers.XL--;
1503 SetZN(Registers.XL);
1504 }
1505 else
1506 {
1507 Registers.X.W--;
1508 SetZN(Registers.X.W);
1509 }
1510}
1511
1512static void Op88X1 (void)
1513{
1514 AddCycles(ONE_CYCLE);
1515 Registers.YL--;
1516 SetZN(Registers.YL);
1517}
1518
1519static void Op88X0 (void)
1520{
1521 AddCycles(ONE_CYCLE);
1522 Registers.Y.W--;
1523 SetZN(Registers.Y.W);
1524}
1525
1526static void Op88Slow (void)
1527{
1528 AddCycles(ONE_CYCLE);
1529
1530 if (CheckIndex())
1531 {
1532 Registers.YL--;
1533 SetZN(Registers.YL);
1534 }
1535 else
1536 {
1537 Registers.Y.W--;
1538 SetZN(Registers.Y.W);
1539 }
1540}
1541
1542/* INX/INY ***************************************************************** */
1543
1544static void OpE8X1 (void)
1545{
1546 AddCycles(ONE_CYCLE);
1547 Registers.XL++;
1548 SetZN(Registers.XL);
1549}
1550
1551static void OpE8X0 (void)
1552{
1553 AddCycles(ONE_CYCLE);
1554 Registers.X.W++;
1555 SetZN(Registers.X.W);
1556}
1557
1558static void OpE8Slow (void)
1559{
1560 AddCycles(ONE_CYCLE);
1561
1562 if (CheckIndex())
1563 {
1564 Registers.XL++;
1565 SetZN(Registers.XL);
1566 }
1567 else
1568 {
1569 Registers.X.W++;
1570 SetZN(Registers.X.W);
1571 }
1572}
1573
1574static void OpC8X1 (void)
1575{
1576 AddCycles(ONE_CYCLE);
1577 Registers.YL++;
1578 SetZN(Registers.YL);
1579}
1580
1581static void OpC8X0 (void)
1582{
1583 AddCycles(ONE_CYCLE);
1584 Registers.Y.W++;
1585 SetZN(Registers.Y.W);
1586}
1587
1588static void OpC8Slow (void)
1589{
1590 AddCycles(ONE_CYCLE);
1591
1592 if (CheckIndex())
1593 {
1594 Registers.YL++;
1595 SetZN(Registers.YL);
1596 }
1597 else
1598 {
1599 Registers.Y.W++;
1600 SetZN(Registers.Y.W);
1601 }
1602}
1603
1604/* NOP ********************************************************************* */
1605
1606static void OpEA (void)
1607{
1608 AddCycles(ONE_CYCLE);
1609}
1610
1611/* PUSH Instructions ******************************************************* */
1612
1613#define PushW(w) \
1614 S9xSetWord(w, Registers.S.W - 1, WRAP_BANK, WRITE_10); \
1615 Registers.S.W -= 2;
1616
1617#define PushWE(w) \
1618 Registers.SL--; \
1619 S9xSetWord(w, Registers.S.W, WRAP_PAGE, WRITE_10); \
1620 Registers.SL--;
1621
1622#define PushB(b) \
1623 S9xSetByte(b, Registers.S.W--);
1624
1625#define PushBE(b) \
1626 S9xSetByte(b, Registers.S.W); \
1627 Registers.SL--;
1628
1629// PEA
1630static void OpF4E0 (void)
1631{
1632 uint16 val = (uint16) Absolute(NONE);
1633 PushW(val);
1634 OpenBus = val & 0xff;
1635}
1636
1637static void OpF4E1 (void)
1638{
1639 // Note: PEA is a new instruction,
1640 // and so doesn't respect the emu-mode stack bounds.
1641 uint16 val = (uint16) Absolute(NONE);
1642 PushW(val);
1643 OpenBus = val & 0xff;
1644 Registers.SH = 1;
1645}
1646
1647static void OpF4Slow (void)
1648{
1649 uint16 val = (uint16) AbsoluteSlow(NONE);
1650 PushW(val);
1651 OpenBus = val & 0xff;
1652 if (CheckEmulation())
1653 Registers.SH = 1;
1654}
1655
1656// PEI
1657static void OpD4E0 (void)
1658{
1659 uint16 val = (uint16) DirectIndirectE0(NONE);
1660 PushW(val);
1661 OpenBus = val & 0xff;
1662}
1663
1664static void OpD4E1 (void)
1665{
1666 // Note: PEI is a new instruction,
1667 // and so doesn't respect the emu-mode stack bounds.
1668 uint16 val = (uint16) DirectIndirectE1(NONE);
1669 PushW(val);
1670 OpenBus = val & 0xff;
1671 Registers.SH = 1;
1672}
1673
1674static void OpD4Slow (void)
1675{
1676 uint16 val = (uint16) DirectIndirectSlow(NONE);
1677 PushW(val);
1678 OpenBus = val & 0xff;
1679 if (CheckEmulation())
1680 Registers.SH = 1;
1681}
1682
1683// PER
1684static void Op62E0 (void)
1685{
1686 uint16 val = (uint16) RelativeLong(NONE);
1687 PushW(val);
1688 OpenBus = val & 0xff;
1689}
1690
1691static void Op62E1 (void)
1692{
1693 // Note: PER is a new instruction,
1694 // and so doesn't respect the emu-mode stack bounds.
1695 uint16 val = (uint16) RelativeLong(NONE);
1696 PushW(val);
1697 OpenBus = val & 0xff;
1698 Registers.SH = 1;
1699}
1700
1701static void Op62Slow (void)
1702{
1703 uint16 val = (uint16) RelativeLongSlow(NONE);
1704 PushW(val);
1705 OpenBus = val & 0xff;
1706 if (CheckEmulation())
1707 Registers.SH = 1;
1708}
1709
1710// PHA
1711static void Op48E1 (void)
1712{
1713 AddCycles(ONE_CYCLE);
1714 PushBE(Registers.AL);
1715 OpenBus = Registers.AL;
1716}
1717
1718static void Op48E0M1 (void)
1719{
1720 AddCycles(ONE_CYCLE);
1721 PushB(Registers.AL);
1722 OpenBus = Registers.AL;
1723}
1724
1725static void Op48E0M0 (void)
1726{
1727 AddCycles(ONE_CYCLE);
1728 PushW(Registers.A.W);
1729 OpenBus = Registers.AL;
1730}
1731
1732static void Op48Slow (void)
1733{
1734 AddCycles(ONE_CYCLE);
1735
1736 if (CheckEmulation())
1737 {
1738 PushBE(Registers.AL);
1739 }
1740 else
1741 if (CheckMemory())
1742 {
1743 PushB(Registers.AL);
1744 }
1745 else
1746 {
1747 PushW(Registers.A.W);
1748 }
1749
1750 OpenBus = Registers.AL;
1751}
1752
1753// PHB
1754static void Op8BE1 (void)
1755{
1756 AddCycles(ONE_CYCLE);
1757 PushBE(Registers.DB);
1758 OpenBus = Registers.DB;
1759}
1760
1761static void Op8BE0 (void)
1762{
1763 AddCycles(ONE_CYCLE);
1764 PushB(Registers.DB);
1765 OpenBus = Registers.DB;
1766}
1767
1768static void Op8BSlow (void)
1769{
1770 AddCycles(ONE_CYCLE);
1771
1772 if (CheckEmulation())
1773 {
1774 PushBE(Registers.DB);
1775 }
1776 else
1777 {
1778 PushB(Registers.DB);
1779 }
1780
1781 OpenBus = Registers.DB;
1782}
1783
1784// PHD
1785static void Op0BE0 (void)
1786{
1787 AddCycles(ONE_CYCLE);
1788 PushW(Registers.D.W);
1789 OpenBus = Registers.DL;
1790}
1791
1792static void Op0BE1 (void)
1793{
1794 // Note: PHD is a new instruction,
1795 // and so doesn't respect the emu-mode stack bounds.
1796 AddCycles(ONE_CYCLE);
1797 PushW(Registers.D.W);
1798 OpenBus = Registers.DL;
1799 Registers.SH = 1;
1800}
1801
1802static void Op0BSlow (void)
1803{
1804 AddCycles(ONE_CYCLE);
1805 PushW(Registers.D.W);
1806 OpenBus = Registers.DL;
1807 if (CheckEmulation())
1808 Registers.SH = 1;
1809}
1810
1811// PHK
1812static void Op4BE1 (void)
1813{
1814 AddCycles(ONE_CYCLE);
1815 PushBE(Registers.PB);
1816 OpenBus = Registers.PB;
1817}
1818
1819static void Op4BE0 (void)
1820{
1821 AddCycles(ONE_CYCLE);
1822 PushB(Registers.PB);
1823 OpenBus = Registers.PB;
1824}
1825
1826static void Op4BSlow (void)
1827{
1828 AddCycles(ONE_CYCLE);
1829
1830 if (CheckEmulation())
1831 {
1832 PushBE(Registers.PB);
1833 }
1834 else
1835 {
1836 PushB(Registers.PB);
1837 }
1838
1839 OpenBus = Registers.PB;
1840}
1841
1842// PHP
1843static void Op08E0 (void)
1844{
1845 S9xPackStatus();
1846 AddCycles(ONE_CYCLE);
1847 PushB(Registers.PL);
1848 OpenBus = Registers.PL;
1849}
1850
1851static void Op08E1 (void)
1852{
1853 S9xPackStatus();
1854 AddCycles(ONE_CYCLE);
1855 PushBE(Registers.PL);
1856 OpenBus = Registers.PL;
1857}
1858
1859static void Op08Slow (void)
1860{
1861 S9xPackStatus();
1862 AddCycles(ONE_CYCLE);
1863
1864 if (CheckEmulation())
1865 {
1866 PushBE(Registers.PL);
1867 }
1868 else
1869 {
1870 PushB(Registers.PL);
1871 }
1872
1873 OpenBus = Registers.PL;
1874}
1875
1876// PHX
1877static void OpDAE1 (void)
1878{
1879 AddCycles(ONE_CYCLE);
1880 PushBE(Registers.XL);
1881 OpenBus = Registers.XL;
1882}
1883
1884static void OpDAE0X1 (void)
1885{
1886 AddCycles(ONE_CYCLE);
1887 PushB(Registers.XL);
1888 OpenBus = Registers.XL;
1889}
1890
1891static void OpDAE0X0 (void)
1892{
1893 AddCycles(ONE_CYCLE);
1894 PushW(Registers.X.W);
1895 OpenBus = Registers.XL;
1896}
1897
1898static void OpDASlow (void)
1899{
1900 AddCycles(ONE_CYCLE);
1901
1902 if (CheckEmulation())
1903 {
1904 PushBE(Registers.XL);
1905 }
1906 else
1907 if (CheckIndex())
1908 {
1909 PushB(Registers.XL);
1910 }
1911 else
1912 {
1913 PushW(Registers.X.W);
1914 }
1915
1916 OpenBus = Registers.XL;
1917}
1918
1919// PHY
1920static void Op5AE1 (void)
1921{
1922 AddCycles(ONE_CYCLE);
1923 PushBE(Registers.YL);
1924 OpenBus = Registers.YL;
1925}
1926
1927static void Op5AE0X1 (void)
1928{
1929 AddCycles(ONE_CYCLE);
1930 PushB(Registers.YL);
1931 OpenBus = Registers.YL;
1932}
1933
1934static void Op5AE0X0 (void)
1935{
1936 AddCycles(ONE_CYCLE);
1937 PushW(Registers.Y.W);
1938 OpenBus = Registers.YL;
1939}
1940
1941static void Op5ASlow (void)
1942{
1943 AddCycles(ONE_CYCLE);
1944
1945 if (CheckEmulation())
1946 {
1947 PushBE(Registers.YL);
1948 }
1949 else
1950 if (CheckIndex())
1951 {
1952 PushB(Registers.YL);
1953 }
1954 else
1955 {
1956 PushW(Registers.Y.W);
1957 }
1958
1959 OpenBus = Registers.YL;
1960}
1961
1962/* PULL Instructions ******************************************************* */
1963
1964#define PullW(w) \
1965 w = S9xGetWord(Registers.S.W + 1, WRAP_BANK); \
1966 Registers.S.W += 2;
1967
1968#define PullWE(w) \
1969 Registers.SL++; \
1970 w = S9xGetWord(Registers.S.W, WRAP_PAGE); \
1971 Registers.SL++;
1972
1973#define PullB(b) \
1974 b = S9xGetByte(++Registers.S.W);
1975
1976#define PullBE(b) \
1977 Registers.SL++; \
1978 b = S9xGetByte(Registers.S.W);
1979
1980// PLA
1981static void Op68E1 (void)
1982{
1983 AddCycles(TWO_CYCLES);
1984 PullBE(Registers.AL);
1985 SetZN(Registers.AL);
1986 OpenBus = Registers.AL;
1987}
1988
1989static void Op68E0M1 (void)
1990{
1991 AddCycles(TWO_CYCLES);
1992 PullB(Registers.AL);
1993 SetZN(Registers.AL);
1994 OpenBus = Registers.AL;
1995}
1996
1997static void Op68E0M0 (void)
1998{
1999 AddCycles(TWO_CYCLES);
2000 PullW(Registers.A.W);
2001 SetZN(Registers.A.W);
2002 OpenBus = Registers.AH;
2003}
2004
2005static void Op68Slow (void)
2006{
2007 AddCycles(TWO_CYCLES);
2008
2009 if (CheckEmulation())
2010 {
2011 PullBE(Registers.AL);
2012 SetZN(Registers.AL);
2013 OpenBus = Registers.AL;
2014 }
2015 else
2016 if (CheckMemory())
2017 {
2018 PullB(Registers.AL);
2019 SetZN(Registers.AL);
2020 OpenBus = Registers.AL;
2021 }
2022 else
2023 {
2024 PullW(Registers.A.W);
2025 SetZN(Registers.A.W);
2026 OpenBus = Registers.AH;
2027 }
2028}
2029
2030// PLB
2031static void OpABE1 (void)
2032{
2033 AddCycles(TWO_CYCLES);
2034 PullBE(Registers.DB);
2035 SetZN(Registers.DB);
2036 ICPU.ShiftedDB = Registers.DB << 16;
2037 OpenBus = Registers.DB;
2038}
2039
2040static void OpABE0 (void)
2041{
2042 AddCycles(TWO_CYCLES);
2043 PullB(Registers.DB);
2044 SetZN(Registers.DB);
2045 ICPU.ShiftedDB = Registers.DB << 16;
2046 OpenBus = Registers.DB;
2047}
2048
2049static void OpABSlow (void)
2050{
2051 AddCycles(TWO_CYCLES);
2052
2053 if (CheckEmulation())
2054 {
2055 PullBE(Registers.DB);
2056 }
2057 else
2058 {
2059 PullB(Registers.DB);
2060 }
2061
2062 SetZN(Registers.DB);
2063 ICPU.ShiftedDB = Registers.DB << 16;
2064 OpenBus = Registers.DB;
2065}
2066
2067// PLD
2068static void Op2BE0 (void)
2069{
2070 AddCycles(TWO_CYCLES);
2071 PullW(Registers.D.W);
2072 SetZN(Registers.D.W);
2073 OpenBus = Registers.DH;
2074}
2075
2076static void Op2BE1 (void)
2077{
2078 // Note: PLD is a new instruction,
2079 // and so doesn't respect the emu-mode stack bounds.
2080 AddCycles(TWO_CYCLES);
2081 PullW(Registers.D.W);
2082 SetZN(Registers.D.W);
2083 OpenBus = Registers.DH;
2084 Registers.SH = 1;
2085}
2086
2087static void Op2BSlow (void)
2088{
2089 AddCycles(TWO_CYCLES);
2090 PullW(Registers.D.W);
2091 SetZN(Registers.D.W);
2092 OpenBus = Registers.DH;
2093 if (CheckEmulation())
2094 Registers.SH = 1;
2095}
2096
2097// PLP
2098static void Op28E1 (void)
2099{
2100 AddCycles(TWO_CYCLES);
2101 PullBE(Registers.PL);
2102 OpenBus = Registers.PL;
2103 SetFlags(MemoryFlag | IndexFlag);
2104 S9xUnpackStatus();
2105 S9xFixCycles();
2106 CHECK_FOR_IRQ();
2107}
2108
2109static void Op28E0 (void)
2110{
2111 AddCycles(TWO_CYCLES);
2112 PullB(Registers.PL);
2113 OpenBus = Registers.PL;
2114 S9xUnpackStatus();
2115
2116 if (CheckIndex())
2117 {
2118 Registers.XH = 0;
2119 Registers.YH = 0;
2120 }
2121
2122 S9xFixCycles();
2123 CHECK_FOR_IRQ();
2124}
2125
2126static void Op28Slow (void)
2127{
2128 AddCycles(TWO_CYCLES);
2129
2130 if (CheckEmulation())
2131 {
2132 PullBE(Registers.PL);
2133 OpenBus = Registers.PL;
2134 SetFlags(MemoryFlag | IndexFlag);
2135 }
2136 else
2137 {
2138 PullB(Registers.PL);
2139 OpenBus = Registers.PL;
2140 }
2141
2142 S9xUnpackStatus();
2143
2144 if (CheckIndex())
2145 {
2146 Registers.XH = 0;
2147 Registers.YH = 0;
2148 }
2149
2150 S9xFixCycles();
2151 CHECK_FOR_IRQ();
2152}
2153
2154// PLX
2155static void OpFAE1 (void)
2156{
2157 AddCycles(TWO_CYCLES);
2158 PullBE(Registers.XL);
2159 SetZN(Registers.XL);
2160 OpenBus = Registers.XL;
2161}
2162
2163static void OpFAE0X1 (void)
2164{
2165 AddCycles(TWO_CYCLES);
2166 PullB(Registers.XL);
2167 SetZN(Registers.XL);
2168 OpenBus = Registers.XL;
2169}
2170
2171static void OpFAE0X0 (void)
2172{
2173 AddCycles(TWO_CYCLES);
2174 PullW(Registers.X.W);
2175 SetZN(Registers.X.W);
2176 OpenBus = Registers.XH;
2177}
2178
2179static void OpFASlow (void)
2180{
2181 AddCycles(TWO_CYCLES);
2182
2183 if (CheckEmulation())
2184 {
2185 PullBE(Registers.XL);
2186 SetZN(Registers.XL);
2187 OpenBus = Registers.XL;
2188 }
2189 else
2190 if (CheckIndex())
2191 {
2192 PullB(Registers.XL);
2193 SetZN(Registers.XL);
2194 OpenBus = Registers.XL;
2195 }
2196 else
2197 {
2198 PullW(Registers.X.W);
2199 SetZN(Registers.X.W);
2200 OpenBus = Registers.XH;
2201 }
2202}
2203
2204// PLY
2205static void Op7AE1 (void)
2206{
2207 AddCycles(TWO_CYCLES);
2208 PullBE(Registers.YL);
2209 SetZN(Registers.YL);
2210 OpenBus = Registers.YL;
2211}
2212
2213static void Op7AE0X1 (void)
2214{
2215 AddCycles(TWO_CYCLES);
2216 PullB(Registers.YL);
2217 SetZN(Registers.YL);
2218 OpenBus = Registers.YL;
2219}
2220
2221static void Op7AE0X0 (void)
2222{
2223 AddCycles(TWO_CYCLES);
2224 PullW(Registers.Y.W);
2225 SetZN(Registers.Y.W);
2226 OpenBus = Registers.YH;
2227}
2228
2229static void Op7ASlow (void)
2230{
2231 AddCycles(TWO_CYCLES);
2232
2233 if (CheckEmulation())
2234 {
2235 PullBE(Registers.YL);
2236 SetZN(Registers.YL);
2237 OpenBus = Registers.YL;
2238 }
2239 else
2240 if (CheckIndex())
2241 {
2242 PullB(Registers.YL);
2243 SetZN(Registers.YL);
2244 OpenBus = Registers.YL;
2245 }
2246 else
2247 {
2248 PullW(Registers.Y.W);
2249 SetZN(Registers.Y.W);
2250 OpenBus = Registers.YH;
2251 }
2252}
2253
2254/* Transfer Instructions *************************************************** */
2255
2256// TAX
2257static void OpAAX1 (void)
2258{
2259 AddCycles(ONE_CYCLE);
2260 Registers.XL = Registers.AL;
2261 SetZN(Registers.XL);
2262}
2263
2264static void OpAAX0 (void)
2265{
2266 AddCycles(ONE_CYCLE);
2267 Registers.X.W = Registers.A.W;
2268 SetZN(Registers.X.W);
2269}
2270
2271static void OpAASlow (void)
2272{
2273 AddCycles(ONE_CYCLE);
2274
2275 if (CheckIndex())
2276 {
2277 Registers.XL = Registers.AL;
2278 SetZN(Registers.XL);
2279 }
2280 else
2281 {
2282 Registers.X.W = Registers.A.W;
2283 SetZN(Registers.X.W);
2284 }
2285}
2286
2287// TAY
2288static void OpA8X1 (void)
2289{
2290 AddCycles(ONE_CYCLE);
2291 Registers.YL = Registers.AL;
2292 SetZN(Registers.YL);
2293}
2294
2295static void OpA8X0 (void)
2296{
2297 AddCycles(ONE_CYCLE);
2298 Registers.Y.W = Registers.A.W;
2299 SetZN(Registers.Y.W);
2300}
2301
2302static void OpA8Slow (void)
2303{
2304 AddCycles(ONE_CYCLE);
2305
2306 if (CheckIndex())
2307 {
2308 Registers.YL = Registers.AL;
2309 SetZN(Registers.YL);
2310 }
2311 else
2312 {
2313 Registers.Y.W = Registers.A.W;
2314 SetZN(Registers.Y.W);
2315 }
2316}
2317
2318// TCD
2319static void Op5B (void)
2320{
2321 AddCycles(ONE_CYCLE);
2322 Registers.D.W = Registers.A.W;
2323 SetZN(Registers.D.W);
2324}
2325
2326// TCS
2327static void Op1B (void)
2328{
2329 AddCycles(ONE_CYCLE);
2330 Registers.S.W = Registers.A.W;
2331 if (CheckEmulation())
2332 Registers.SH = 1;
2333}
2334
2335// TDC
2336static void Op7B (void)
2337{
2338 AddCycles(ONE_CYCLE);
2339 Registers.A.W = Registers.D.W;
2340 SetZN(Registers.A.W);
2341}
2342
2343// TSC
2344static void Op3B (void)
2345{
2346 AddCycles(ONE_CYCLE);
2347 Registers.A.W = Registers.S.W;
2348 SetZN(Registers.A.W);
2349}
2350
2351// TSX
2352static void OpBAX1 (void)
2353{
2354 AddCycles(ONE_CYCLE);
2355 Registers.XL = Registers.SL;
2356 SetZN(Registers.XL);
2357}
2358
2359static void OpBAX0 (void)
2360{
2361 AddCycles(ONE_CYCLE);
2362 Registers.X.W = Registers.S.W;
2363 SetZN(Registers.X.W);
2364}
2365
2366static void OpBASlow (void)
2367{
2368 AddCycles(ONE_CYCLE);
2369
2370 if (CheckIndex())
2371 {
2372 Registers.XL = Registers.SL;
2373 SetZN(Registers.XL);
2374 }
2375 else
2376 {
2377 Registers.X.W = Registers.S.W;
2378 SetZN(Registers.X.W);
2379 }
2380}
2381
2382// TXA
2383static void Op8AM1 (void)
2384{
2385 AddCycles(ONE_CYCLE);
2386 Registers.AL = Registers.XL;
2387 SetZN(Registers.AL);
2388}
2389
2390static void Op8AM0 (void)
2391{
2392 AddCycles(ONE_CYCLE);
2393 Registers.A.W = Registers.X.W;
2394 SetZN(Registers.A.W);
2395}
2396
2397static void Op8ASlow (void)
2398{
2399 AddCycles(ONE_CYCLE);
2400
2401 if (CheckMemory())
2402 {
2403 Registers.AL = Registers.XL;
2404 SetZN(Registers.AL);
2405 }
2406 else
2407 {
2408 Registers.A.W = Registers.X.W;
2409 SetZN(Registers.A.W);
2410 }
2411}
2412
2413// TXS
2414static void Op9A (void)
2415{
2416 AddCycles(ONE_CYCLE);
2417 Registers.S.W = Registers.X.W;
2418 if (CheckEmulation())
2419 Registers.SH = 1;
2420}
2421
2422// TXY
2423static void Op9BX1 (void)
2424{
2425 AddCycles(ONE_CYCLE);
2426 Registers.YL = Registers.XL;
2427 SetZN(Registers.YL);
2428}
2429
2430static void Op9BX0 (void)
2431{
2432 AddCycles(ONE_CYCLE);
2433 Registers.Y.W = Registers.X.W;
2434 SetZN(Registers.Y.W);
2435}
2436
2437static void Op9BSlow (void)
2438{
2439 AddCycles(ONE_CYCLE);
2440
2441 if (CheckIndex())
2442 {
2443 Registers.YL = Registers.XL;
2444 SetZN(Registers.YL);
2445 }
2446 else
2447 {
2448 Registers.Y.W = Registers.X.W;
2449 SetZN(Registers.Y.W);
2450 }
2451}
2452
2453// TYA
2454static void Op98M1 (void)
2455{
2456 AddCycles(ONE_CYCLE);
2457 Registers.AL = Registers.YL;
2458 SetZN(Registers.AL);
2459}
2460
2461static void Op98M0 (void)
2462{
2463 AddCycles(ONE_CYCLE);
2464 Registers.A.W = Registers.Y.W;
2465 SetZN(Registers.A.W);
2466}
2467
2468static void Op98Slow (void)
2469{
2470 AddCycles(ONE_CYCLE);
2471
2472 if (CheckMemory())
2473 {
2474 Registers.AL = Registers.YL;
2475 SetZN(Registers.AL);
2476 }
2477 else
2478 {
2479 Registers.A.W = Registers.Y.W;
2480 SetZN(Registers.A.W);
2481 }
2482}
2483
2484// TYX
2485static void OpBBX1 (void)
2486{
2487 AddCycles(ONE_CYCLE);
2488 Registers.XL = Registers.YL;
2489 SetZN(Registers.XL);
2490}
2491
2492static void OpBBX0 (void)
2493{
2494 AddCycles(ONE_CYCLE);
2495 Registers.X.W = Registers.Y.W;
2496 SetZN(Registers.X.W);
2497}
2498
2499static void OpBBSlow (void)
2500{
2501 AddCycles(ONE_CYCLE);
2502
2503 if (CheckIndex())
2504 {
2505 Registers.XL = Registers.YL;
2506 SetZN(Registers.XL);
2507 }
2508 else
2509 {
2510 Registers.X.W = Registers.Y.W;
2511 SetZN(Registers.X.W);
2512 }
2513}
2514
2515/* XCE ********************************************************************* */
2516
2517static void OpFB (void)
2518{
2519 AddCycles(ONE_CYCLE);
2520
2521 uint8 A1 = ICPU._Carry;
2522 uint8 A2 = Registers.PH;
2523
2524 ICPU._Carry = A2 & 1;
2525 Registers.PH = A1;
2526
2527 if (CheckEmulation())
2528 {
2529 SetFlags(MemoryFlag | IndexFlag);
2530 Registers.SH = 1;
2531 #ifdef DEBUGGER
2532 missing.emulate6502 = 1;
2533 #endif
2534 }
2535
2536 if (CheckIndex())
2537 {
2538 Registers.XH = 0;
2539 Registers.YH = 0;
2540 }
2541
2542 S9xFixCycles();
2543}
2544
2545/* BRK ********************************************************************* */
2546
2547static void Op00 (void)
2548{
2549#ifdef DEBUGGER
2550 if (CPU.Flags & TRACE_FLAG)
2551 S9xTraceMessage("*** BRK");
2552#endif
2553
2554 AddCycles(CPU.MemSpeed);
2555
2556 uint16 addr;
2557
2558 if (!CheckEmulation())
2559 {
2560 PushB(Registers.PB);
2561 PushW(Registers.PCw + 1);
2562 S9xPackStatus();
2563 PushB(Registers.PL);
2564 OpenBus = Registers.PL;
2565 ClearDecimal();
2566 SetIRQ();
2567
2568 addr = S9xGetWord(0xFFE6);
2569 }
2570 else
2571 {
2572 PushWE(Registers.PCw + 1);
2573 S9xPackStatus();
2574 PushBE(Registers.PL);
2575 OpenBus = Registers.PL;
2576 ClearDecimal();
2577 SetIRQ();
2578
2579 addr = S9xGetWord(0xFFFE);
2580 }
2581
2582 S9xSetPCBase(addr);
2583 OpenBus = addr >> 8;
2584}
2585
2586/* IRQ ********************************************************************* */
2587
2588void S9xOpcode_IRQ (void)
2589{
2590#ifdef DEBUGGER
2591 if (CPU.Flags & TRACE_FLAG)
2592 #ifdef SA1_OPCODES
2593 S9xTraceMessage("*** SA1 IRQ");
2594 #else
2595 S9xTraceMessage("*** IRQ");
2596 #endif
2597#endif
2598
2599 // IRQ and NMI do an opcode fetch as their first "IO" cycle.
2600 AddCycles(CPU.MemSpeed + ONE_CYCLE);
2601
2602 if (!CheckEmulation())
2603 {
2604 PushB(Registers.PB);
2605 PushW(Registers.PCw);
2606 S9xPackStatus();
2607 PushB(Registers.PL);
2608 OpenBus = Registers.PL;
2609 ClearDecimal();
2610 SetIRQ();
2611
2612 #ifdef SA1_OPCODES
2613 OpenBus = Memory.FillRAM[0x2208];
2614 AddCycles(2 * ONE_CYCLE);
2615 S9xSA1SetPCBase(Memory.FillRAM[0x2207] | (Memory.FillRAM[0x2208] << 8));
2616 #else
2617 if (Settings.SA1 && (Memory.FillRAM[0x2209] & 0x40))
2618 {
2619 OpenBus = Memory.FillRAM[0x220f];
2620 AddCycles(2 * ONE_CYCLE);
2621 S9xSetPCBase(Memory.FillRAM[0x220e] | (Memory.FillRAM[0x220f] << 8));
2622 }
2623 else
2624 {
2625 uint16 addr = S9xGetWord(0xFFEE);
2626 OpenBus = addr >> 8;
2627 S9xSetPCBase(addr);
2628 }
2629 #endif
2630 }
2631 else
2632 {
2633 PushWE(Registers.PCw);
2634 S9xPackStatus();
2635 PushBE(Registers.PL);
2636 OpenBus = Registers.PL;
2637 ClearDecimal();
2638 SetIRQ();
2639
2640 #ifdef SA1_OPCODES
2641 OpenBus = Memory.FillRAM[0x2208];
2642 AddCycles(2 * ONE_CYCLE);
2643 S9xSA1SetPCBase(Memory.FillRAM[0x2207] | (Memory.FillRAM[0x2208] << 8));
2644 #else
2645 if (Settings.SA1 && (Memory.FillRAM[0x2209] & 0x40))
2646 {
2647 OpenBus = Memory.FillRAM[0x220f];
2648 AddCycles(2 * ONE_CYCLE);
2649 S9xSetPCBase(Memory.FillRAM[0x220e] | (Memory.FillRAM[0x220f] << 8));
2650 }
2651 else
2652 {
2653 uint16 addr = S9xGetWord(0xFFFE);
2654 OpenBus = addr >> 8;
2655 S9xSetPCBase(addr);
2656 }
2657 #endif
2658 }
2659}
2660
2661/* NMI ********************************************************************* */
2662
2663void S9xOpcode_NMI (void)
2664{
2665#ifdef DEBUGGER
2666 if (CPU.Flags & TRACE_FLAG)
2667 #ifdef SA1_OPCODES
2668 S9xTraceMessage("*** SA1 NMI");
2669 #else
2670 S9xTraceMessage("*** NMI");
2671 #endif
2672#endif
2673
2674 // IRQ and NMI do an opcode fetch as their first "IO" cycle.
2675 AddCycles(CPU.MemSpeed + ONE_CYCLE);
2676
2677 if (!CheckEmulation())
2678 {
2679 PushB(Registers.PB);
2680 PushW(Registers.PCw);
2681 S9xPackStatus();
2682 PushB(Registers.PL);
2683 OpenBus = Registers.PL;
2684 ClearDecimal();
2685 SetIRQ();
2686
2687 #ifdef SA1_OPCODES
2688 OpenBus = Memory.FillRAM[0x2206];
2689 AddCycles(2 * ONE_CYCLE);
2690 S9xSA1SetPCBase(Memory.FillRAM[0x2205] | (Memory.FillRAM[0x2206] << 8));
2691 #else
2692 if (Settings.SA1 && (Memory.FillRAM[0x2209] & 0x10))
2693 {
2694 OpenBus = Memory.FillRAM[0x220d];
2695 AddCycles(2 * ONE_CYCLE);
2696 S9xSetPCBase(Memory.FillRAM[0x220c] | (Memory.FillRAM[0x220d] << 8));
2697 }
2698 else
2699 {
2700 uint16 addr = S9xGetWord(0xFFEA);
2701 OpenBus = addr >> 8;
2702 S9xSetPCBase(addr);
2703 }
2704 #endif
2705 }
2706 else
2707 {
2708 PushWE(Registers.PCw);
2709 S9xPackStatus();
2710 PushBE(Registers.PL);
2711 OpenBus = Registers.PL;
2712 ClearDecimal();
2713 SetIRQ();
2714
2715 #ifdef SA1_OPCODES
2716 OpenBus = Memory.FillRAM[0x2206];
2717 AddCycles(2 * ONE_CYCLE);
2718 S9xSA1SetPCBase(Memory.FillRAM[0x2205] | (Memory.FillRAM[0x2206] << 8));
2719 #else
2720 if (Settings.SA1 && (Memory.FillRAM[0x2209] & 0x10))
2721 {
2722 OpenBus = Memory.FillRAM[0x220d];
2723 AddCycles(2 * ONE_CYCLE);
2724 S9xSetPCBase(Memory.FillRAM[0x220c] | (Memory.FillRAM[0x220d] << 8));
2725 }
2726 else
2727 {
2728 uint16 addr = S9xGetWord(0xFFFA);
2729 OpenBus = addr >> 8;
2730 S9xSetPCBase(addr);
2731 }
2732 #endif
2733 }
2734}
2735
2736/* COP ********************************************************************* */
2737
2738static void Op02 (void)
2739{
2740#ifdef DEBUGGER
2741 if (CPU.Flags & TRACE_FLAG)
2742 S9xTraceMessage("*** COP");
2743#endif
2744
2745 AddCycles(CPU.MemSpeed);
2746
2747 uint16 addr;
2748
2749 if (!CheckEmulation())
2750 {
2751 PushB(Registers.PB);
2752 PushW(Registers.PCw + 1);
2753 S9xPackStatus();
2754 PushB(Registers.PL);
2755 OpenBus = Registers.PL;
2756 ClearDecimal();
2757 SetIRQ();
2758
2759 addr = S9xGetWord(0xFFE4);
2760 }
2761 else
2762 {
2763 PushWE(Registers.PCw + 1);
2764 S9xPackStatus();
2765 PushBE(Registers.PL);
2766 OpenBus = Registers.PL;
2767 ClearDecimal();
2768 SetIRQ();
2769
2770 addr = S9xGetWord(0xFFF4);
2771 }
2772
2773 S9xSetPCBase(addr);
2774 OpenBus = addr >> 8;
2775}
2776
2777/* JML ********************************************************************* */
2778
2779static void OpDC (void)
2780{
2781 S9xSetPCBase(AbsoluteIndirectLong(JUMP));
2782#ifdef SA1_OPCODES
2783 AddCycles(ONE_CYCLE);
2784#endif
2785}
2786
2787static void OpDCSlow (void)
2788{
2789 S9xSetPCBase(AbsoluteIndirectLongSlow(JUMP));
2790#ifdef SA1_OPCODES
2791 AddCycles(ONE_CYCLE);
2792#endif
2793}
2794
2795static void Op5C (void)
2796{
2797 S9xSetPCBase(AbsoluteLong(JUMP));
2798#ifdef SA1_OPCODES
2799 AddCycles(ONE_CYCLE);
2800#endif
2801}
2802
2803static void Op5CSlow (void)
2804{
2805 S9xSetPCBase(AbsoluteLongSlow(JUMP));
2806#ifdef SA1_OPCODES
2807 AddCycles(ONE_CYCLE);
2808#endif
2809}
2810
2811/* JMP ********************************************************************* */
2812
2813static void Op4C (void)
2814{
2815 S9xSetPCBase(ICPU.ShiftedPB + ((uint16) Absolute(JUMP)));
2816}
2817
2818static void Op4CSlow (void)
2819{
2820 S9xSetPCBase(ICPU.ShiftedPB + ((uint16) AbsoluteSlow(JUMP)));
2821}
2822
2823static void Op6C (void)
2824{
2825 S9xSetPCBase(ICPU.ShiftedPB + ((uint16) AbsoluteIndirect(JUMP)));
2826}
2827
2828static void Op6CSlow (void)
2829{
2830 S9xSetPCBase(ICPU.ShiftedPB + ((uint16) AbsoluteIndirectSlow(JUMP)));
2831}
2832
2833static void Op7C (void)
2834{
2835 S9xSetPCBase(ICPU.ShiftedPB + ((uint16) AbsoluteIndexedIndirect(JUMP)));
2836}
2837
2838static void Op7CSlow (void)
2839{
2840 S9xSetPCBase(ICPU.ShiftedPB + ((uint16) AbsoluteIndexedIndirectSlow(JUMP)));
2841}
2842
2843/* JSL/RTL ***************************************************************** */
2844
2845static void Op22E1 (void)
2846{
2847 // Note: JSL is a new instruction,
2848 // and so doesn't respect the emu-mode stack bounds.
2849 uint32 addr = AbsoluteLong(JSR);
2850 PushB(Registers.PB);
2851 PushW(Registers.PCw - 1);
2852 Registers.SH = 1;
2853 S9xSetPCBase(addr);
2854}
2855
2856static void Op22E0 (void)
2857{
2858 uint32 addr = AbsoluteLong(JSR);
2859 PushB(Registers.PB);
2860 PushW(Registers.PCw - 1);
2861 S9xSetPCBase(addr);
2862}
2863
2864static void Op22Slow (void)
2865{
2866 uint32 addr = AbsoluteLongSlow(JSR);
2867 PushB(Registers.PB);
2868 PushW(Registers.PCw - 1);
2869 if (CheckEmulation())
2870 Registers.SH = 1;
2871 S9xSetPCBase(addr);
2872}
2873
2874static void Op6BE1 (void)
2875{
2876 // Note: RTL is a new instruction,
2877 // and so doesn't respect the emu-mode stack bounds.
2878 AddCycles(TWO_CYCLES);
2879 PullW(Registers.PCw);
2880 PullB(Registers.PB);
2881 Registers.SH = 1;
2882 Registers.PCw++;
2883 S9xSetPCBase(Registers.PBPC);
2884}
2885
2886static void Op6BE0 (void)
2887{
2888 AddCycles(TWO_CYCLES);
2889 PullW(Registers.PCw);
2890 PullB(Registers.PB);
2891 Registers.PCw++;
2892 S9xSetPCBase(Registers.PBPC);
2893}
2894
2895static void Op6BSlow (void)
2896{
2897 AddCycles(TWO_CYCLES);
2898 PullW(Registers.PCw);
2899 PullB(Registers.PB);
2900 if (CheckEmulation())
2901 Registers.SH = 1;
2902 Registers.PCw++;
2903 S9xSetPCBase(Registers.PBPC);
2904}
2905
2906/* JSR/RTS ***************************************************************** */
2907
2908static void Op20E1 (void)
2909{
2910 uint16 addr = Absolute(JSR);
2911 AddCycles(ONE_CYCLE);
2912 PushWE(Registers.PCw - 1);
2913 S9xSetPCBase(ICPU.ShiftedPB + addr);
2914}
2915
2916static void Op20E0 (void)
2917{
2918 uint16 addr = Absolute(JSR);
2919 AddCycles(ONE_CYCLE);
2920 PushW(Registers.PCw - 1);
2921 S9xSetPCBase(ICPU.ShiftedPB + addr);
2922}
2923
2924static void Op20Slow (void)
2925{
2926 uint16 addr = AbsoluteSlow(JSR);
2927
2928 AddCycles(ONE_CYCLE);
2929
2930 if (CheckEmulation())
2931 {
2932 PushWE(Registers.PCw - 1);
2933 }
2934 else
2935 {
2936 PushW(Registers.PCw - 1);
2937 }
2938
2939 S9xSetPCBase(ICPU.ShiftedPB + addr);
2940}
2941
2942static void OpFCE1 (void)
2943{
2944 // Note: JSR (a,X) is a new instruction,
2945 // and so doesn't respect the emu-mode stack bounds.
2946 uint16 addr = AbsoluteIndexedIndirect(JSR);
2947 PushW(Registers.PCw - 1);
2948 Registers.SH = 1;
2949 S9xSetPCBase(ICPU.ShiftedPB + addr);
2950}
2951
2952static void OpFCE0 (void)
2953{
2954 uint16 addr = AbsoluteIndexedIndirect(JSR);
2955 PushW(Registers.PCw - 1);
2956 S9xSetPCBase(ICPU.ShiftedPB + addr);
2957}
2958
2959static void OpFCSlow (void)
2960{
2961 uint16 addr = AbsoluteIndexedIndirectSlow(JSR);
2962 PushW(Registers.PCw - 1);
2963 if (CheckEmulation())
2964 Registers.SH = 1;
2965 S9xSetPCBase(ICPU.ShiftedPB + addr);
2966}
2967
2968static void Op60E1 (void)
2969{
2970 AddCycles(TWO_CYCLES);
2971 PullWE(Registers.PCw);
2972 AddCycles(ONE_CYCLE);
2973 Registers.PCw++;
2974 S9xSetPCBase(Registers.PBPC);
2975}
2976
2977static void Op60E0 (void)
2978{
2979 AddCycles(TWO_CYCLES);
2980 PullW(Registers.PCw);
2981 AddCycles(ONE_CYCLE);
2982 Registers.PCw++;
2983 S9xSetPCBase(Registers.PBPC);
2984}
2985
2986static void Op60Slow (void)
2987{
2988 AddCycles(TWO_CYCLES);
2989
2990 if (CheckEmulation())
2991 {
2992 PullWE(Registers.PCw);
2993 }
2994 else
2995 {
2996 PullW(Registers.PCw);
2997 }
2998
2999 AddCycles(ONE_CYCLE);
3000 Registers.PCw++;
3001 S9xSetPCBase(Registers.PBPC);
3002}
3003
3004/* MVN/MVP ***************************************************************** */
3005
3006static void Op54X1 (void)
3007{
3008 uint32 SrcBank;
3009
3010 Registers.DB = Immediate8(NONE);
3011 ICPU.ShiftedDB = Registers.DB << 16;
3012 OpenBus = SrcBank = Immediate8(NONE);
3013
3014 S9xSetByte(OpenBus = S9xGetByte((SrcBank << 16) + Registers.X.W), ICPU.ShiftedDB + Registers.Y.W);
3015
3016 Registers.XL++;
3017 Registers.YL++;
3018 Registers.A.W--;
3019 if (Registers.A.W != 0xffff)
3020 Registers.PCw -= 3;
3021
3022 AddCycles(TWO_CYCLES);
3023}
3024
3025static void Op54X0 (void)
3026{
3027 uint32 SrcBank;
3028
3029 Registers.DB = Immediate8(NONE);
3030 ICPU.ShiftedDB = Registers.DB << 16;
3031 OpenBus = SrcBank = Immediate8(NONE);
3032
3033 S9xSetByte(OpenBus = S9xGetByte((SrcBank << 16) + Registers.X.W), ICPU.ShiftedDB + Registers.Y.W);
3034
3035 Registers.X.W++;
3036 Registers.Y.W++;
3037 Registers.A.W--;
3038 if (Registers.A.W != 0xffff)
3039 Registers.PCw -= 3;
3040
3041 AddCycles(TWO_CYCLES);
3042}
3043
3044static void Op54Slow (void)
3045{
3046 uint32 SrcBank;
3047
3048 OpenBus = Registers.DB = Immediate8Slow(NONE);
3049 ICPU.ShiftedDB = Registers.DB << 16;
3050 OpenBus = SrcBank = Immediate8Slow(NONE);
3051
3052 S9xSetByte(OpenBus = S9xGetByte((SrcBank << 16) + Registers.X.W), ICPU.ShiftedDB + Registers.Y.W);
3053
3054 if (CheckIndex())
3055 {
3056 Registers.XL++;
3057 Registers.YL++;
3058 }
3059 else
3060 {
3061 Registers.X.W++;
3062 Registers.Y.W++;
3063 }
3064
3065 Registers.A.W--;
3066 if (Registers.A.W != 0xffff)
3067 Registers.PCw -= 3;
3068
3069 AddCycles(TWO_CYCLES);
3070}
3071
3072static void Op44X1 (void)
3073{
3074 uint32 SrcBank;
3075
3076 Registers.DB = Immediate8(NONE);
3077 ICPU.ShiftedDB = Registers.DB << 16;
3078 OpenBus = SrcBank = Immediate8(NONE);
3079
3080 S9xSetByte(OpenBus = S9xGetByte((SrcBank << 16) + Registers.X.W), ICPU.ShiftedDB + Registers.Y.W);
3081
3082 Registers.XL--;
3083 Registers.YL--;
3084 Registers.A.W--;
3085 if (Registers.A.W != 0xffff)
3086 Registers.PCw -= 3;
3087
3088 AddCycles(TWO_CYCLES);
3089}
3090
3091static void Op44X0 (void)
3092{
3093 uint32 SrcBank;
3094
3095 Registers.DB = Immediate8(NONE);
3096 ICPU.ShiftedDB = Registers.DB << 16;
3097 OpenBus = SrcBank = Immediate8(NONE);
3098
3099 S9xSetByte(OpenBus = S9xGetByte((SrcBank << 16) + Registers.X.W), ICPU.ShiftedDB + Registers.Y.W);
3100
3101 Registers.X.W--;
3102 Registers.Y.W--;
3103 Registers.A.W--;
3104 if (Registers.A.W != 0xffff)
3105 Registers.PCw -= 3;
3106
3107 AddCycles(TWO_CYCLES);
3108}
3109
3110static void Op44Slow (void)
3111{
3112 uint32 SrcBank;
3113
3114 OpenBus = Registers.DB = Immediate8Slow(NONE);
3115 ICPU.ShiftedDB = Registers.DB << 16;
3116 OpenBus = SrcBank = Immediate8Slow(NONE);
3117
3118 S9xSetByte(OpenBus = S9xGetByte((SrcBank << 16) + Registers.X.W), ICPU.ShiftedDB + Registers.Y.W);
3119
3120 if (CheckIndex())
3121 {
3122 Registers.XL--;
3123 Registers.YL--;
3124 }
3125 else
3126 {
3127 Registers.X.W--;
3128 Registers.Y.W--;
3129 }
3130
3131 Registers.A.W--;
3132 if (Registers.A.W != 0xffff)
3133 Registers.PCw -= 3;
3134
3135 AddCycles(TWO_CYCLES);
3136}
3137
3138/* REP/SEP ***************************************************************** */
3139
3140static void OpC2 (void)
3141{
3142 uint8 Work8 = ~Immediate8(READ);
3143 Registers.PL &= Work8;
3144 ICPU._Carry &= Work8;
3145 ICPU._Overflow &= (Work8 >> 6);
3146 ICPU._Negative &= Work8;
3147 ICPU._Zero |= ~Work8 & Zero;
3148
3149 AddCycles(ONE_CYCLE);
3150
3151 if (CheckEmulation())
3152 {
3153 SetFlags(MemoryFlag | IndexFlag);
3154 #ifdef DEBUGGER
3155 missing.emulate6502 = 1;
3156 #endif
3157 }
3158
3159 if (CheckIndex())
3160 {
3161 Registers.XH = 0;
3162 Registers.YH = 0;
3163 }
3164
3165 S9xFixCycles();
3166 CHECK_FOR_IRQ();
3167}
3168
3169static void OpC2Slow (void)
3170{
3171 uint8 Work8 = ~Immediate8Slow(READ);
3172 Registers.PL &= Work8;
3173 ICPU._Carry &= Work8;
3174 ICPU._Overflow &= (Work8 >> 6);
3175 ICPU._Negative &= Work8;
3176 ICPU._Zero |= ~Work8 & Zero;
3177
3178 AddCycles(ONE_CYCLE);
3179
3180 if (CheckEmulation())
3181 {
3182 SetFlags(MemoryFlag | IndexFlag);
3183 #ifdef DEBUGGER
3184 missing.emulate6502 = 1;
3185 #endif
3186 }
3187
3188 if (CheckIndex())
3189 {
3190 Registers.XH = 0;
3191 Registers.YH = 0;
3192 }
3193
3194 S9xFixCycles();
3195 CHECK_FOR_IRQ();
3196}
3197
3198static void OpE2 (void)
3199{
3200 uint8 Work8 = Immediate8(READ);
3201 Registers.PL |= Work8;
3202 ICPU._Carry |= Work8 & 1;
3203 ICPU._Overflow |= (Work8 >> 6) & 1;
3204 ICPU._Negative |= Work8;
3205 if (Work8 & Zero)
3206 ICPU._Zero = 0;
3207
3208 AddCycles(ONE_CYCLE);
3209
3210 if (CheckEmulation())
3211 {
3212 SetFlags(MemoryFlag | IndexFlag);
3213 #ifdef DEBUGGER
3214 missing.emulate6502 = 1;
3215 #endif
3216 }
3217
3218 if (CheckIndex())
3219 {
3220 Registers.XH = 0;
3221 Registers.YH = 0;
3222 }
3223
3224 S9xFixCycles();
3225}
3226
3227static void OpE2Slow (void)
3228{
3229 uint8 Work8 = Immediate8Slow(READ);
3230 Registers.PL |= Work8;
3231 ICPU._Carry |= Work8 & 1;
3232 ICPU._Overflow |= (Work8 >> 6) & 1;
3233 ICPU._Negative |= Work8;
3234 if (Work8 & Zero)
3235 ICPU._Zero = 0;
3236
3237 AddCycles(ONE_CYCLE);
3238
3239 if (CheckEmulation())
3240 {
3241 SetFlags(MemoryFlag | IndexFlag);
3242 #ifdef DEBUGGER
3243 missing.emulate6502 = 1;
3244 #endif
3245 }
3246
3247 if (CheckIndex())
3248 {
3249 Registers.XH = 0;
3250 Registers.YH = 0;
3251 }
3252
3253 S9xFixCycles();
3254}
3255
3256/* XBA ********************************************************************* */
3257
3258static void OpEB (void)
3259{
3260 uint8 Work8 = Registers.AL;
3261 Registers.AL = Registers.AH;
3262 Registers.AH = Work8;
3263 SetZN(Registers.AL);
3264 AddCycles(TWO_CYCLES);
3265}
3266
3267/* RTI ********************************************************************* */
3268
3269static void Op40Slow (void)
3270{
3271 AddCycles(TWO_CYCLES);
3272
3273 if (!CheckEmulation())
3274 {
3275 PullB(Registers.PL);
3276 S9xUnpackStatus();
3277 PullW(Registers.PCw);
3278 PullB(Registers.PB);
3279 OpenBus = Registers.PB;
3280 ICPU.ShiftedPB = Registers.PB << 16;
3281 }
3282 else
3283 {
3284 PullBE(Registers.PL);
3285 S9xUnpackStatus();
3286 PullWE(Registers.PCw);
3287 OpenBus = Registers.PCh;
3288 SetFlags(MemoryFlag | IndexFlag);
3289 #ifdef DEBUGGER
3290 missing.emulate6502 = 1;
3291 #endif
3292 }
3293
3294 S9xSetPCBase(Registers.PBPC);
3295
3296 if (CheckIndex())
3297 {
3298 Registers.XH = 0;
3299 Registers.YH = 0;
3300 }
3301
3302 S9xFixCycles();
3303 CHECK_FOR_IRQ();
3304}
3305
3306/* STP/WAI ***************************************************************** */
3307
3308// WAI
3309static void OpCB (void)
3310{
3311#ifdef SA1_OPCODES
3312 SA1.WaitingForInterrupt = TRUE;
3313 Registers.PCw--;
3314 AddCycles(TWO_CYCLES);
3315#else
3316 CPU.WaitingForInterrupt = TRUE;
3317
3318 Registers.PCw--;
3319 AddCycles(ONE_CYCLE);
3320#endif
3321}
3322
3323// STP
3324static void OpDB (void)
3325{
3326 Registers.PCw--;
3327 CPU.Flags |= DEBUG_MODE_FLAG | HALTED_FLAG;
3328}
3329
3330/* WDM (Reserved S9xOpcode) ************************************************ */
3331
3332#ifdef DEBUGGER
3333extern FILE *trace, *trace2;
3334#endif
3335
3336static void Op42 (void)
3337{
3338#ifdef DEBUGGER
3339 uint8 byte = (uint8) S9xGetWord(Registers.PBPC);
3340#else
3341 S9xGetWord(Registers.PBPC);
3342#endif
3343 Registers.PCw++;
3344
3345#ifdef DEBUGGER
3346 // Hey, let's use this to trigger debug modes.
3347 switch (byte)
3348 {
3349 case 0xdb: // "STP" = Enter debug mode
3350 CPU.Flags |= DEBUG_MODE_FLAG;
3351 break;
3352
3353 #ifndef SA1_OPCODES
3354 case 0xe2: // "SEP" = Trace on
3355 if (!(CPU.Flags & TRACE_FLAG))
3356 {
3357 char buf[25];
3358 CPU.Flags |= TRACE_FLAG;
3359 snprintf(buf, 25, "WDM trace on at $%02X:%04X", Registers.PB, Registers.PCw);
3360 S9xMessage(S9X_DEBUG, S9X_DEBUG_OUTPUT, buf);
3361 if (trace != NULL)
3362 fclose(trace);
3363 ENSURE_TRACE_OPEN(trace, "WDMtrace.log", "ab")
3364 }
3365
3366 break;
3367
3368 case 0xc2: // "REP" = Trace off
3369 if (CPU.Flags & TRACE_FLAG)
3370 {
3371 char buf[26];
3372 CPU.Flags &= ~TRACE_FLAG;
3373 snprintf(buf, 26, "WDM trace off at $%02X:%04X", Registers.PB, Registers.PCw);
3374 S9xMessage(S9X_DEBUG, S9X_DEBUG_OUTPUT, buf);
3375 if (trace != NULL)
3376 fclose(trace);
3377 trace = NULL;
3378 }
3379
3380 break;
3381 #endif
3382
3383 case 0x42: // "WDM" = Snapshot
3384 char filename[PATH_MAX + 1], drive[_MAX_DRIVE + 1], dir[_MAX_DIR + 1], def[PATH_MAX + 1], ext[_MAX_EXT + 1];
3385
3386 _splitpath(Memory.ROMFilename, drive, dir, def, ext);
3387 snprintf(filename, PATH_MAX, "%s%s%s-%06X.wdm", S9xGetDirectory(SNAPSHOT_DIR), SLASH_STR, def, Registers.PBPC & 0xffffff);
3388 sprintf(def, "WDM Snapshot at $%02X:%04X: %s", Registers.PB, Registers.PCw, filename);
3389 S9xMessage(S9X_DEBUG, S9X_DEBUG_OUTPUT, def);
3390 S9xFreezeGame(filename);
3391
3392 break;
3393
3394 default:
3395 break;
3396 }
3397#endif
3398}
3399
3400/* CPU-S9xOpcodes Definitions ************************************************/
3401
3402struct SOpcodes S9xOpcodesM1X1[256] =
3403{
3404 { Op00 }, { Op01E0M1 }, { Op02 }, { Op03M1 }, { Op04M1 },
3405 { Op05M1 }, { Op06M1 }, { Op07M1 }, { Op08E0 }, { Op09M1 },
3406 { Op0AM1 }, { Op0BE0 }, { Op0CM1 }, { Op0DM1 }, { Op0EM1 },
3407 { Op0FM1 }, { Op10E0 }, { Op11E0M1X1 }, { Op12E0M1 }, { Op13M1 },
3408 { Op14M1 }, { Op15E0M1 }, { Op16E0M1 }, { Op17M1 }, { Op18 },
3409 { Op19M1X1 }, { Op1AM1 }, { Op1B }, { Op1CM1 }, { Op1DM1X1 },
3410 { Op1EM1X1 }, { Op1FM1 }, { Op20E0 }, { Op21E0M1 }, { Op22E0 },
3411 { Op23M1 }, { Op24M1 }, { Op25M1 }, { Op26M1 }, { Op27M1 },
3412 { Op28E0 }, { Op29M1 }, { Op2AM1 }, { Op2BE0 }, { Op2CM1 },
3413 { Op2DM1 }, { Op2EM1 }, { Op2FM1 }, { Op30E0 }, { Op31E0M1X1 },
3414 { Op32E0M1 }, { Op33M1 }, { Op34E0M1 }, { Op35E0M1 }, { Op36E0M1 },
3415 { Op37M1 }, { Op38 }, { Op39M1X1 }, { Op3AM1 }, { Op3B },
3416 { Op3CM1X1 }, { Op3DM1X1 }, { Op3EM1X1 }, { Op3FM1 }, { Op40Slow },
3417 { Op41E0M1 }, { Op42 }, { Op43M1 }, { Op44X1 }, { Op45M1 },
3418 { Op46M1 }, { Op47M1 }, { Op48E0M1 }, { Op49M1 }, { Op4AM1 },
3419 { Op4BE0 }, { Op4C }, { Op4DM1 }, { Op4EM1 }, { Op4FM1 },
3420 { Op50E0 }, { Op51E0M1X1 }, { Op52E0M1 }, { Op53M1 }, { Op54X1 },
3421 { Op55E0M1 }, { Op56E0M1 }, { Op57M1 }, { Op58 }, { Op59M1X1 },
3422 { Op5AE0X1 }, { Op5B }, { Op5C }, { Op5DM1X1 }, { Op5EM1X1 },
3423 { Op5FM1 }, { Op60E0 }, { Op61E0M1 }, { Op62E0 }, { Op63M1 },
3424 { Op64M1 }, { Op65M1 }, { Op66M1 }, { Op67M1 }, { Op68E0M1 },
3425 { Op69M1 }, { Op6AM1 }, { Op6BE0 }, { Op6C }, { Op6DM1 },
3426 { Op6EM1 }, { Op6FM1 }, { Op70E0 }, { Op71E0M1X1 }, { Op72E0M1 },
3427 { Op73M1 }, { Op74E0M1 }, { Op75E0M1 }, { Op76E0M1 }, { Op77M1 },
3428 { Op78 }, { Op79M1X1 }, { Op7AE0X1 }, { Op7B }, { Op7C },
3429 { Op7DM1X1 }, { Op7EM1X1 }, { Op7FM1 }, { Op80E0 }, { Op81E0M1 },
3430 { Op82 }, { Op83M1 }, { Op84X1 }, { Op85M1 }, { Op86X1 },
3431 { Op87M1 }, { Op88X1 }, { Op89M1 }, { Op8AM1 }, { Op8BE0 },
3432 { Op8CX1 }, { Op8DM1 }, { Op8EX1 }, { Op8FM1 }, { Op90E0 },
3433 { Op91E0M1X1 }, { Op92E0M1 }, { Op93M1 }, { Op94E0X1 }, { Op95E0M1 },
3434 { Op96E0X1 }, { Op97M1 }, { Op98M1 }, { Op99M1X1 }, { Op9A },
3435 { Op9BX1 }, { Op9CM1 }, { Op9DM1X1 }, { Op9EM1X1 }, { Op9FM1 },
3436 { OpA0X1 }, { OpA1E0M1 }, { OpA2X1 }, { OpA3M1 }, { OpA4X1 },
3437 { OpA5M1 }, { OpA6X1 }, { OpA7M1 }, { OpA8X1 }, { OpA9M1 },
3438 { OpAAX1 }, { OpABE0 }, { OpACX1 }, { OpADM1 }, { OpAEX1 },
3439 { OpAFM1 }, { OpB0E0 }, { OpB1E0M1X1 }, { OpB2E0M1 }, { OpB3M1 },
3440 { OpB4E0X1 }, { OpB5E0M1 }, { OpB6E0X1 }, { OpB7M1 }, { OpB8 },
3441 { OpB9M1X1 }, { OpBAX1 }, { OpBBX1 }, { OpBCX1 }, { OpBDM1X1 },
3442 { OpBEX1 }, { OpBFM1 }, { OpC0X1 }, { OpC1E0M1 }, { OpC2 },
3443 { OpC3M1 }, { OpC4X1 }, { OpC5M1 }, { OpC6M1 }, { OpC7M1 },
3444 { OpC8X1 }, { OpC9M1 }, { OpCAX1 }, { OpCB }, { OpCCX1 },
3445 { OpCDM1 }, { OpCEM1 }, { OpCFM1 }, { OpD0E0 }, { OpD1E0M1X1 },
3446 { OpD2E0M1 }, { OpD3M1 }, { OpD4E0 }, { OpD5E0M1 }, { OpD6E0M1 },
3447 { OpD7M1 }, { OpD8 }, { OpD9M1X1 }, { OpDAE0X1 }, { OpDB },
3448 { OpDC }, { OpDDM1X1 }, { OpDEM1X1 }, { OpDFM1 }, { OpE0X1 },
3449 { OpE1E0M1 }, { OpE2 }, { OpE3M1 }, { OpE4X1 }, { OpE5M1 },
3450 { OpE6M1 }, { OpE7M1 }, { OpE8X1 }, { OpE9M1 }, { OpEA },
3451 { OpEB }, { OpECX1 }, { OpEDM1 }, { OpEEM1 }, { OpEFM1 },
3452 { OpF0E0 }, { OpF1E0M1X1 }, { OpF2E0M1 }, { OpF3M1 }, { OpF4E0 },
3453 { OpF5E0M1 }, { OpF6E0M1 }, { OpF7M1 }, { OpF8 }, { OpF9M1X1 },
3454 { OpFAE0X1 }, { OpFB }, { OpFCE0 }, { OpFDM1X1 }, { OpFEM1X1 },
3455 { OpFFM1 }
3456};
3457
3458struct SOpcodes S9xOpcodesE1[256] =
3459{
3460 { Op00 }, { Op01E1 }, { Op02 }, { Op03M1 }, { Op04M1 },
3461 { Op05M1 }, { Op06M1 }, { Op07M1 }, { Op08E1 }, { Op09M1 },
3462 { Op0AM1 }, { Op0BE1 }, { Op0CM1 }, { Op0DM1 }, { Op0EM1 },
3463 { Op0FM1 }, { Op10E1 }, { Op11E1 }, { Op12E1 }, { Op13M1 },
3464 { Op14M1 }, { Op15E1 }, { Op16E1 }, { Op17M1 }, { Op18 },
3465 { Op19M1X1 }, { Op1AM1 }, { Op1B }, { Op1CM1 }, { Op1DM1X1 },
3466 { Op1EM1X1 }, { Op1FM1 }, { Op20E1 }, { Op21E1 }, { Op22E1 },
3467 { Op23M1 }, { Op24M1 }, { Op25M1 }, { Op26M1 }, { Op27M1 },
3468 { Op28E1 }, { Op29M1 }, { Op2AM1 }, { Op2BE1 }, { Op2CM1 },
3469 { Op2DM1 }, { Op2EM1 }, { Op2FM1 }, { Op30E1 }, { Op31E1 },
3470 { Op32E1 }, { Op33M1 }, { Op34E1 }, { Op35E1 }, { Op36E1 },
3471 { Op37M1 }, { Op38 }, { Op39M1X1 }, { Op3AM1 }, { Op3B },
3472 { Op3CM1X1 }, { Op3DM1X1 }, { Op3EM1X1 }, { Op3FM1 }, { Op40Slow },
3473 { Op41E1 }, { Op42 }, { Op43M1 }, { Op44X1 }, { Op45M1 },
3474 { Op46M1 }, { Op47M1 }, { Op48E1 }, { Op49M1 }, { Op4AM1 },
3475 { Op4BE1 }, { Op4C }, { Op4DM1 }, { Op4EM1 }, { Op4FM1 },
3476 { Op50E1 }, { Op51E1 }, { Op52E1 }, { Op53M1 }, { Op54X1 },
3477 { Op55E1 }, { Op56E1 }, { Op57M1 }, { Op58 }, { Op59M1X1 },
3478 { Op5AE1 }, { Op5B }, { Op5C }, { Op5DM1X1 }, { Op5EM1X1 },
3479 { Op5FM1 }, { Op60E1 }, { Op61E1 }, { Op62E1 }, { Op63M1 },
3480 { Op64M1 }, { Op65M1 }, { Op66M1 }, { Op67M1 }, { Op68E1 },
3481 { Op69M1 }, { Op6AM1 }, { Op6BE1 }, { Op6C }, { Op6DM1 },
3482 { Op6EM1 }, { Op6FM1 }, { Op70E1 }, { Op71E1 }, { Op72E1 },
3483 { Op73M1 }, { Op74E1 }, { Op75E1 }, { Op76E1 }, { Op77M1 },
3484 { Op78 }, { Op79M1X1 }, { Op7AE1 }, { Op7B }, { Op7C },
3485 { Op7DM1X1 }, { Op7EM1X1 }, { Op7FM1 }, { Op80E1 }, { Op81E1 },
3486 { Op82 }, { Op83M1 }, { Op84X1 }, { Op85M1 }, { Op86X1 },
3487 { Op87M1 }, { Op88X1 }, { Op89M1 }, { Op8AM1 }, { Op8BE1 },
3488 { Op8CX1 }, { Op8DM1 }, { Op8EX1 }, { Op8FM1 }, { Op90E1 },
3489 { Op91E1 }, { Op92E1 }, { Op93M1 }, { Op94E1 }, { Op95E1 },
3490 { Op96E1 }, { Op97M1 }, { Op98M1 }, { Op99M1X1 }, { Op9A },
3491 { Op9BX1 }, { Op9CM1 }, { Op9DM1X1 }, { Op9EM1X1 }, { Op9FM1 },
3492 { OpA0X1 }, { OpA1E1 }, { OpA2X1 }, { OpA3M1 }, { OpA4X1 },
3493 { OpA5M1 }, { OpA6X1 }, { OpA7M1 }, { OpA8X1 }, { OpA9M1 },
3494 { OpAAX1 }, { OpABE1 }, { OpACX1 }, { OpADM1 }, { OpAEX1 },
3495 { OpAFM1 }, { OpB0E1 }, { OpB1E1 }, { OpB2E1 }, { OpB3M1 },
3496 { OpB4E1 }, { OpB5E1 }, { OpB6E1 }, { OpB7M1 }, { OpB8 },
3497 { OpB9M1X1 }, { OpBAX1 }, { OpBBX1 }, { OpBCX1 }, { OpBDM1X1 },
3498 { OpBEX1 }, { OpBFM1 }, { OpC0X1 }, { OpC1E1 }, { OpC2 },
3499 { OpC3M1 }, { OpC4X1 }, { OpC5M1 }, { OpC6M1 }, { OpC7M1 },
3500 { OpC8X1 }, { OpC9M1 }, { OpCAX1 }, { OpCB }, { OpCCX1 },
3501 { OpCDM1 }, { OpCEM1 }, { OpCFM1 }, { OpD0E1 }, { OpD1E1 },
3502 { OpD2E1 }, { OpD3M1 }, { OpD4E1 }, { OpD5E1 }, { OpD6E1 },
3503 { OpD7M1 }, { OpD8 }, { OpD9M1X1 }, { OpDAE1 }, { OpDB },
3504 { OpDC }, { OpDDM1X1 }, { OpDEM1X1 }, { OpDFM1 }, { OpE0X1 },
3505 { OpE1E1 }, { OpE2 }, { OpE3M1 }, { OpE4X1 }, { OpE5M1 },
3506 { OpE6M1 }, { OpE7M1 }, { OpE8X1 }, { OpE9M1 }, { OpEA },
3507 { OpEB }, { OpECX1 }, { OpEDM1 }, { OpEEM1 }, { OpEFM1 },
3508 { OpF0E1 }, { OpF1E1 }, { OpF2E1 }, { OpF3M1 }, { OpF4E1 },
3509 { OpF5E1 }, { OpF6E1 }, { OpF7M1 }, { OpF8 }, { OpF9M1X1 },
3510 { OpFAE1 }, { OpFB }, { OpFCE1 }, { OpFDM1X1 }, { OpFEM1X1 },
3511 { OpFFM1 }
3512};
3513
3514struct SOpcodes S9xOpcodesM1X0[256] =
3515{
3516 { Op00 }, { Op01E0M1 }, { Op02 }, { Op03M1 }, { Op04M1 },
3517 { Op05M1 }, { Op06M1 }, { Op07M1 }, { Op08E0 }, { Op09M1 },
3518 { Op0AM1 }, { Op0BE0 }, { Op0CM1 }, { Op0DM1 }, { Op0EM1 },
3519 { Op0FM1 }, { Op10E0 }, { Op11E0M1X0 }, { Op12E0M1 }, { Op13M1 },
3520 { Op14M1 }, { Op15E0M1 }, { Op16E0M1 }, { Op17M1 }, { Op18 },
3521 { Op19M1X0 }, { Op1AM1 }, { Op1B }, { Op1CM1 }, { Op1DM1X0 },
3522 { Op1EM1X0 }, { Op1FM1 }, { Op20E0 }, { Op21E0M1 }, { Op22E0 },
3523 { Op23M1 }, { Op24M1 }, { Op25M1 }, { Op26M1 }, { Op27M1 },
3524 { Op28E0 }, { Op29M1 }, { Op2AM1 }, { Op2BE0 }, { Op2CM1 },
3525 { Op2DM1 }, { Op2EM1 }, { Op2FM1 }, { Op30E0 }, { Op31E0M1X0 },
3526 { Op32E0M1 }, { Op33M1 }, { Op34E0M1 }, { Op35E0M1 }, { Op36E0M1 },
3527 { Op37M1 }, { Op38 }, { Op39M1X0 }, { Op3AM1 }, { Op3B },
3528 { Op3CM1X0 }, { Op3DM1X0 }, { Op3EM1X0 }, { Op3FM1 }, { Op40Slow },
3529 { Op41E0M1 }, { Op42 }, { Op43M1 }, { Op44X0 }, { Op45M1 },
3530 { Op46M1 }, { Op47M1 }, { Op48E0M1 }, { Op49M1 }, { Op4AM1 },
3531 { Op4BE0 }, { Op4C }, { Op4DM1 }, { Op4EM1 }, { Op4FM1 },
3532 { Op50E0 }, { Op51E0M1X0 }, { Op52E0M1 }, { Op53M1 }, { Op54X0 },
3533 { Op55E0M1 }, { Op56E0M1 }, { Op57M1 }, { Op58 }, { Op59M1X0 },
3534 { Op5AE0X0 }, { Op5B }, { Op5C }, { Op5DM1X0 }, { Op5EM1X0 },
3535 { Op5FM1 }, { Op60E0 }, { Op61E0M1 }, { Op62E0 }, { Op63M1 },
3536 { Op64M1 }, { Op65M1 }, { Op66M1 }, { Op67M1 }, { Op68E0M1 },
3537 { Op69M1 }, { Op6AM1 }, { Op6BE0 }, { Op6C }, { Op6DM1 },
3538 { Op6EM1 }, { Op6FM1 }, { Op70E0 }, { Op71E0M1X0 }, { Op72E0M1 },
3539 { Op73M1 }, { Op74E0M1 }, { Op75E0M1 }, { Op76E0M1 }, { Op77M1 },
3540 { Op78 }, { Op79M1X0 }, { Op7AE0X0 }, { Op7B }, { Op7C },
3541 { Op7DM1X0 }, { Op7EM1X0 }, { Op7FM1 }, { Op80E0 }, { Op81E0M1 },
3542 { Op82 }, { Op83M1 }, { Op84X0 }, { Op85M1 }, { Op86X0 },
3543 { Op87M1 }, { Op88X0 }, { Op89M1 }, { Op8AM1 }, { Op8BE0 },
3544 { Op8CX0 }, { Op8DM1 }, { Op8EX0 }, { Op8FM1 }, { Op90E0 },
3545 { Op91E0M1X0 }, { Op92E0M1 }, { Op93M1 }, { Op94E0X0 }, { Op95E0M1 },
3546 { Op96E0X0 }, { Op97M1 }, { Op98M1 }, { Op99M1X0 }, { Op9A },
3547 { Op9BX0 }, { Op9CM1 }, { Op9DM1X0 }, { Op9EM1X0 }, { Op9FM1 },
3548 { OpA0X0 }, { OpA1E0M1 }, { OpA2X0 }, { OpA3M1 }, { OpA4X0 },
3549 { OpA5M1 }, { OpA6X0 }, { OpA7M1 }, { OpA8X0 }, { OpA9M1 },
3550 { OpAAX0 }, { OpABE0 }, { OpACX0 }, { OpADM1 }, { OpAEX0 },
3551 { OpAFM1 }, { OpB0E0 }, { OpB1E0M1X0 }, { OpB2E0M1 }, { OpB3M1 },
3552 { OpB4E0X0 }, { OpB5E0M1 }, { OpB6E0X0 }, { OpB7M1 }, { OpB8 },
3553 { OpB9M1X0 }, { OpBAX0 }, { OpBBX0 }, { OpBCX0 }, { OpBDM1X0 },
3554 { OpBEX0 }, { OpBFM1 }, { OpC0X0 }, { OpC1E0M1 }, { OpC2 },
3555 { OpC3M1 }, { OpC4X0 }, { OpC5M1 }, { OpC6M1 }, { OpC7M1 },
3556 { OpC8X0 }, { OpC9M1 }, { OpCAX0 }, { OpCB }, { OpCCX0 },
3557 { OpCDM1 }, { OpCEM1 }, { OpCFM1 }, { OpD0E0 }, { OpD1E0M1X0 },
3558 { OpD2E0M1 }, { OpD3M1 }, { OpD4E0 }, { OpD5E0M1 }, { OpD6E0M1 },
3559 { OpD7M1 }, { OpD8 }, { OpD9M1X0 }, { OpDAE0X0 }, { OpDB },
3560 { OpDC }, { OpDDM1X0 }, { OpDEM1X0 }, { OpDFM1 }, { OpE0X0 },
3561 { OpE1E0M1 }, { OpE2 }, { OpE3M1 }, { OpE4X0 }, { OpE5M1 },
3562 { OpE6M1 }, { OpE7M1 }, { OpE8X0 }, { OpE9M1 }, { OpEA },
3563 { OpEB }, { OpECX0 }, { OpEDM1 }, { OpEEM1 }, { OpEFM1 },
3564 { OpF0E0 }, { OpF1E0M1X0 }, { OpF2E0M1 }, { OpF3M1 }, { OpF4E0 },
3565 { OpF5E0M1 }, { OpF6E0M1 }, { OpF7M1 }, { OpF8 }, { OpF9M1X0 },
3566 { OpFAE0X0 }, { OpFB }, { OpFCE0 }, { OpFDM1X0 }, { OpFEM1X0 },
3567 { OpFFM1 }
3568};
3569
3570struct SOpcodes S9xOpcodesM0X0[256] =
3571{
3572 { Op00 }, { Op01E0M0 }, { Op02 }, { Op03M0 }, { Op04M0 },
3573 { Op05M0 }, { Op06M0 }, { Op07M0 }, { Op08E0 }, { Op09M0 },
3574 { Op0AM0 }, { Op0BE0 }, { Op0CM0 }, { Op0DM0 }, { Op0EM0 },
3575 { Op0FM0 }, { Op10E0 }, { Op11E0M0X0 }, { Op12E0M0 }, { Op13M0 },
3576 { Op14M0 }, { Op15E0M0 }, { Op16E0M0 }, { Op17M0 }, { Op18 },
3577 { Op19M0X0 }, { Op1AM0 }, { Op1B }, { Op1CM0 }, { Op1DM0X0 },
3578 { Op1EM0X0 }, { Op1FM0 }, { Op20E0 }, { Op21E0M0 }, { Op22E0 },
3579 { Op23M0 }, { Op24M0 }, { Op25M0 }, { Op26M0 }, { Op27M0 },
3580 { Op28E0 }, { Op29M0 }, { Op2AM0 }, { Op2BE0 }, { Op2CM0 },
3581 { Op2DM0 }, { Op2EM0 }, { Op2FM0 }, { Op30E0 }, { Op31E0M0X0 },
3582 { Op32E0M0 }, { Op33M0 }, { Op34E0M0 }, { Op35E0M0 }, { Op36E0M0 },
3583 { Op37M0 }, { Op38 }, { Op39M0X0 }, { Op3AM0 }, { Op3B },
3584 { Op3CM0X0 }, { Op3DM0X0 }, { Op3EM0X0 }, { Op3FM0 }, { Op40Slow },
3585 { Op41E0M0 }, { Op42 }, { Op43M0 }, { Op44X0 }, { Op45M0 },
3586 { Op46M0 }, { Op47M0 }, { Op48E0M0 }, { Op49M0 }, { Op4AM0 },
3587 { Op4BE0 }, { Op4C }, { Op4DM0 }, { Op4EM0 }, { Op4FM0 },
3588 { Op50E0 }, { Op51E0M0X0 }, { Op52E0M0 }, { Op53M0 }, { Op54X0 },
3589 { Op55E0M0 }, { Op56E0M0 }, { Op57M0 }, { Op58 }, { Op59M0X0 },
3590 { Op5AE0X0 }, { Op5B }, { Op5C }, { Op5DM0X0 }, { Op5EM0X0 },
3591 { Op5FM0 }, { Op60E0 }, { Op61E0M0 }, { Op62E0 }, { Op63M0 },
3592 { Op64M0 }, { Op65M0 }, { Op66M0 }, { Op67M0 }, { Op68E0M0 },
3593 { Op69M0 }, { Op6AM0 }, { Op6BE0 }, { Op6C }, { Op6DM0 },
3594 { Op6EM0 }, { Op6FM0 }, { Op70E0 }, { Op71E0M0X0 }, { Op72E0M0 },
3595 { Op73M0 }, { Op74E0M0 }, { Op75E0M0 }, { Op76E0M0 }, { Op77M0 },
3596 { Op78 }, { Op79M0X0 }, { Op7AE0X0 }, { Op7B }, { Op7C },
3597 { Op7DM0X0 }, { Op7EM0X0 }, { Op7FM0 }, { Op80E0 }, { Op81E0M0 },
3598 { Op82 }, { Op83M0 }, { Op84X0 }, { Op85M0 }, { Op86X0 },
3599 { Op87M0 }, { Op88X0 }, { Op89M0 }, { Op8AM0 }, { Op8BE0 },
3600 { Op8CX0 }, { Op8DM0 }, { Op8EX0 }, { Op8FM0 }, { Op90E0 },
3601 { Op91E0M0X0 }, { Op92E0M0 }, { Op93M0 }, { Op94E0X0 }, { Op95E0M0 },
3602 { Op96E0X0 }, { Op97M0 }, { Op98M0 }, { Op99M0X0 }, { Op9A },
3603 { Op9BX0 }, { Op9CM0 }, { Op9DM0X0 }, { Op9EM0X0 }, { Op9FM0 },
3604 { OpA0X0 }, { OpA1E0M0 }, { OpA2X0 }, { OpA3M0 }, { OpA4X0 },
3605 { OpA5M0 }, { OpA6X0 }, { OpA7M0 }, { OpA8X0 }, { OpA9M0 },
3606 { OpAAX0 }, { OpABE0 }, { OpACX0 }, { OpADM0 }, { OpAEX0 },
3607 { OpAFM0 }, { OpB0E0 }, { OpB1E0M0X0 }, { OpB2E0M0 }, { OpB3M0 },
3608 { OpB4E0X0 }, { OpB5E0M0 }, { OpB6E0X0 }, { OpB7M0 }, { OpB8 },
3609 { OpB9M0X0 }, { OpBAX0 }, { OpBBX0 }, { OpBCX0 }, { OpBDM0X0 },
3610 { OpBEX0 }, { OpBFM0 }, { OpC0X0 }, { OpC1E0M0 }, { OpC2 },
3611 { OpC3M0 }, { OpC4X0 }, { OpC5M0 }, { OpC6M0 }, { OpC7M0 },
3612 { OpC8X0 }, { OpC9M0 }, { OpCAX0 }, { OpCB }, { OpCCX0 },
3613 { OpCDM0 }, { OpCEM0 }, { OpCFM0 }, { OpD0E0 }, { OpD1E0M0X0 },
3614 { OpD2E0M0 }, { OpD3M0 }, { OpD4E0 }, { OpD5E0M0 }, { OpD6E0M0 },
3615 { OpD7M0 }, { OpD8 }, { OpD9M0X0 }, { OpDAE0X0 }, { OpDB },
3616 { OpDC }, { OpDDM0X0 }, { OpDEM0X0 }, { OpDFM0 }, { OpE0X0 },
3617 { OpE1E0M0 }, { OpE2 }, { OpE3M0 }, { OpE4X0 }, { OpE5M0 },
3618 { OpE6M0 }, { OpE7M0 }, { OpE8X0 }, { OpE9M0 }, { OpEA },
3619 { OpEB }, { OpECX0 }, { OpEDM0 }, { OpEEM0 }, { OpEFM0 },
3620 { OpF0E0 }, { OpF1E0M0X0 }, { OpF2E0M0 }, { OpF3M0 }, { OpF4E0 },
3621 { OpF5E0M0 }, { OpF6E0M0 }, { OpF7M0 }, { OpF8 }, { OpF9M0X0 },
3622 { OpFAE0X0 }, { OpFB }, { OpFCE0 }, { OpFDM0X0 }, { OpFEM0X0 },
3623 { OpFFM0 }
3624};
3625
3626struct SOpcodes S9xOpcodesM0X1[256] =
3627{
3628 { Op00 }, { Op01E0M0 }, { Op02 }, { Op03M0 }, { Op04M0 },
3629 { Op05M0 }, { Op06M0 }, { Op07M0 }, { Op08E0 }, { Op09M0 },
3630 { Op0AM0 }, { Op0BE0 }, { Op0CM0 }, { Op0DM0 }, { Op0EM0 },
3631 { Op0FM0 }, { Op10E0 }, { Op11E0M0X1 }, { Op12E0M0 }, { Op13M0 },
3632 { Op14M0 }, { Op15E0M0 }, { Op16E0M0 }, { Op17M0 }, { Op18 },
3633 { Op19M0X1 }, { Op1AM0 }, { Op1B }, { Op1CM0 }, { Op1DM0X1 },
3634 { Op1EM0X1 }, { Op1FM0 }, { Op20E0 }, { Op21E0M0 }, { Op22E0 },
3635 { Op23M0 }, { Op24M0 }, { Op25M0 }, { Op26M0 }, { Op27M0 },
3636 { Op28E0 }, { Op29M0 }, { Op2AM0 }, { Op2BE0 }, { Op2CM0 },
3637 { Op2DM0 }, { Op2EM0 }, { Op2FM0 }, { Op30E0 }, { Op31E0M0X1 },
3638 { Op32E0M0 }, { Op33M0 }, { Op34E0M0 }, { Op35E0M0 }, { Op36E0M0 },
3639 { Op37M0 }, { Op38 }, { Op39M0X1 }, { Op3AM0 }, { Op3B },
3640 { Op3CM0X1 }, { Op3DM0X1 }, { Op3EM0X1 }, { Op3FM0 }, { Op40Slow },
3641 { Op41E0M0 }, { Op42 }, { Op43M0 }, { Op44X1 }, { Op45M0 },
3642 { Op46M0 }, { Op47M0 }, { Op48E0M0 }, { Op49M0 }, { Op4AM0 },
3643 { Op4BE0 }, { Op4C }, { Op4DM0 }, { Op4EM0 }, { Op4FM0 },
3644 { Op50E0 }, { Op51E0M0X1 }, { Op52E0M0 }, { Op53M0 }, { Op54X1 },
3645 { Op55E0M0 }, { Op56E0M0 }, { Op57M0 }, { Op58 }, { Op59M0X1 },
3646 { Op5AE0X1 }, { Op5B }, { Op5C }, { Op5DM0X1 }, { Op5EM0X1 },
3647 { Op5FM0 }, { Op60E0 }, { Op61E0M0 }, { Op62E0 }, { Op63M0 },
3648 { Op64M0 }, { Op65M0 }, { Op66M0 }, { Op67M0 }, { Op68E0M0 },
3649 { Op69M0 }, { Op6AM0 }, { Op6BE0 }, { Op6C }, { Op6DM0 },
3650 { Op6EM0 }, { Op6FM0 }, { Op70E0 }, { Op71E0M0X1 }, { Op72E0M0 },
3651 { Op73M0 }, { Op74E0M0 }, { Op75E0M0 }, { Op76E0M0 }, { Op77M0 },
3652 { Op78 }, { Op79M0X1 }, { Op7AE0X1 }, { Op7B }, { Op7C },
3653 { Op7DM0X1 }, { Op7EM0X1 }, { Op7FM0 }, { Op80E0 }, { Op81E0M0 },
3654 { Op82 }, { Op83M0 }, { Op84X1 }, { Op85M0 }, { Op86X1 },
3655 { Op87M0 }, { Op88X1 }, { Op89M0 }, { Op8AM0 }, { Op8BE0 },
3656 { Op8CX1 }, { Op8DM0 }, { Op8EX1 }, { Op8FM0 }, { Op90E0 },
3657 { Op91E0M0X1 }, { Op92E0M0 }, { Op93M0 }, { Op94E0X1 }, { Op95E0M0 },
3658 { Op96E0X1 }, { Op97M0 }, { Op98M0 }, { Op99M0X1 }, { Op9A },
3659 { Op9BX1 }, { Op9CM0 }, { Op9DM0X1 }, { Op9EM0X1 }, { Op9FM0 },
3660 { OpA0X1 }, { OpA1E0M0 }, { OpA2X1 }, { OpA3M0 }, { OpA4X1 },
3661 { OpA5M0 }, { OpA6X1 }, { OpA7M0 }, { OpA8X1 }, { OpA9M0 },
3662 { OpAAX1 }, { OpABE0 }, { OpACX1 }, { OpADM0 }, { OpAEX1 },
3663 { OpAFM0 }, { OpB0E0 }, { OpB1E0M0X1 }, { OpB2E0M0 }, { OpB3M0 },
3664 { OpB4E0X1 }, { OpB5E0M0 }, { OpB6E0X1 }, { OpB7M0 }, { OpB8 },
3665 { OpB9M0X1 }, { OpBAX1 }, { OpBBX1 }, { OpBCX1 }, { OpBDM0X1 },
3666 { OpBEX1 }, { OpBFM0 }, { OpC0X1 }, { OpC1E0M0 }, { OpC2 },
3667 { OpC3M0 }, { OpC4X1 }, { OpC5M0 }, { OpC6M0 }, { OpC7M0 },
3668 { OpC8X1 }, { OpC9M0 }, { OpCAX1 }, { OpCB }, { OpCCX1 },
3669 { OpCDM0 }, { OpCEM0 }, { OpCFM0 }, { OpD0E0 }, { OpD1E0M0X1 },
3670 { OpD2E0M0 }, { OpD3M0 }, { OpD4E0 }, { OpD5E0M0 }, { OpD6E0M0 },
3671 { OpD7M0 }, { OpD8 }, { OpD9M0X1 }, { OpDAE0X1 }, { OpDB },
3672 { OpDC }, { OpDDM0X1 }, { OpDEM0X1 }, { OpDFM0 }, { OpE0X1 },
3673 { OpE1E0M0 }, { OpE2 }, { OpE3M0 }, { OpE4X1 }, { OpE5M0 },
3674 { OpE6M0 }, { OpE7M0 }, { OpE8X1 }, { OpE9M0 }, { OpEA },
3675 { OpEB }, { OpECX1 }, { OpEDM0 }, { OpEEM0 }, { OpEFM0 },
3676 { OpF0E0 }, { OpF1E0M0X1 }, { OpF2E0M0 }, { OpF3M0 }, { OpF4E0 },
3677 { OpF5E0M0 }, { OpF6E0M0 }, { OpF7M0 }, { OpF8 }, { OpF9M0X1 },
3678 { OpFAE0X1 }, { OpFB }, { OpFCE0 }, { OpFDM0X1 }, { OpFEM0X1 },
3679 { OpFFM0 }
3680};
3681
3682struct SOpcodes S9xOpcodesSlow[256] =
3683{
3684 { Op00 }, { Op01Slow }, { Op02 }, { Op03Slow }, { Op04Slow },
3685 { Op05Slow }, { Op06Slow }, { Op07Slow }, { Op08Slow }, { Op09Slow },
3686 { Op0ASlow }, { Op0BSlow }, { Op0CSlow }, { Op0DSlow }, { Op0ESlow },
3687 { Op0FSlow }, { Op10Slow }, { Op11Slow }, { Op12Slow }, { Op13Slow },
3688 { Op14Slow }, { Op15Slow }, { Op16Slow }, { Op17Slow }, { Op18 },
3689 { Op19Slow }, { Op1ASlow }, { Op1B }, { Op1CSlow }, { Op1DSlow },
3690 { Op1ESlow }, { Op1FSlow }, { Op20Slow }, { Op21Slow }, { Op22Slow },
3691 { Op23Slow }, { Op24Slow }, { Op25Slow }, { Op26Slow }, { Op27Slow },
3692 { Op28Slow }, { Op29Slow }, { Op2ASlow }, { Op2BSlow }, { Op2CSlow },
3693 { Op2DSlow }, { Op2ESlow }, { Op2FSlow }, { Op30Slow }, { Op31Slow },
3694 { Op32Slow }, { Op33Slow }, { Op34Slow }, { Op35Slow }, { Op36Slow },
3695 { Op37Slow }, { Op38 }, { Op39Slow }, { Op3ASlow }, { Op3B },
3696 { Op3CSlow }, { Op3DSlow }, { Op3ESlow }, { Op3FSlow }, { Op40Slow },
3697 { Op41Slow }, { Op42 }, { Op43Slow }, { Op44Slow }, { Op45Slow },
3698 { Op46Slow }, { Op47Slow }, { Op48Slow }, { Op49Slow }, { Op4ASlow },
3699 { Op4BSlow }, { Op4CSlow }, { Op4DSlow }, { Op4ESlow }, { Op4FSlow },
3700 { Op50Slow }, { Op51Slow }, { Op52Slow }, { Op53Slow }, { Op54Slow },
3701 { Op55Slow }, { Op56Slow }, { Op57Slow }, { Op58 }, { Op59Slow },
3702 { Op5ASlow }, { Op5B }, { Op5CSlow }, { Op5DSlow }, { Op5ESlow },
3703 { Op5FSlow }, { Op60Slow }, { Op61Slow }, { Op62Slow }, { Op63Slow },
3704 { Op64Slow }, { Op65Slow }, { Op66Slow }, { Op67Slow }, { Op68Slow },
3705 { Op69Slow }, { Op6ASlow }, { Op6BSlow }, { Op6CSlow }, { Op6DSlow },
3706 { Op6ESlow }, { Op6FSlow }, { Op70Slow }, { Op71Slow }, { Op72Slow },
3707 { Op73Slow }, { Op74Slow }, { Op75Slow }, { Op76Slow }, { Op77Slow },
3708 { Op78 }, { Op79Slow }, { Op7ASlow }, { Op7B }, { Op7CSlow },
3709 { Op7DSlow }, { Op7ESlow }, { Op7FSlow }, { Op80Slow }, { Op81Slow },
3710 { Op82Slow }, { Op83Slow }, { Op84Slow }, { Op85Slow }, { Op86Slow },
3711 { Op87Slow }, { Op88Slow }, { Op89Slow }, { Op8ASlow }, { Op8BSlow },
3712 { Op8CSlow }, { Op8DSlow }, { Op8ESlow }, { Op8FSlow }, { Op90Slow },
3713 { Op91Slow }, { Op92Slow }, { Op93Slow }, { Op94Slow }, { Op95Slow },
3714 { Op96Slow }, { Op97Slow }, { Op98Slow }, { Op99Slow }, { Op9A },
3715 { Op9BSlow }, { Op9CSlow }, { Op9DSlow }, { Op9ESlow }, { Op9FSlow },
3716 { OpA0Slow }, { OpA1Slow }, { OpA2Slow }, { OpA3Slow }, { OpA4Slow },
3717 { OpA5Slow }, { OpA6Slow }, { OpA7Slow }, { OpA8Slow }, { OpA9Slow },
3718 { OpAASlow }, { OpABSlow }, { OpACSlow }, { OpADSlow }, { OpAESlow },
3719 { OpAFSlow }, { OpB0Slow }, { OpB1Slow }, { OpB2Slow }, { OpB3Slow },
3720 { OpB4Slow }, { OpB5Slow }, { OpB6Slow }, { OpB7Slow }, { OpB8 },
3721 { OpB9Slow }, { OpBASlow }, { OpBBSlow }, { OpBCSlow }, { OpBDSlow },
3722 { OpBESlow }, { OpBFSlow }, { OpC0Slow }, { OpC1Slow }, { OpC2Slow },
3723 { OpC3Slow }, { OpC4Slow }, { OpC5Slow }, { OpC6Slow }, { OpC7Slow },
3724 { OpC8Slow }, { OpC9Slow }, { OpCASlow }, { OpCB }, { OpCCSlow },
3725 { OpCDSlow }, { OpCESlow }, { OpCFSlow }, { OpD0Slow }, { OpD1Slow },
3726 { OpD2Slow }, { OpD3Slow }, { OpD4Slow }, { OpD5Slow }, { OpD6Slow },
3727 { OpD7Slow }, { OpD8 }, { OpD9Slow }, { OpDASlow }, { OpDB },
3728 { OpDCSlow }, { OpDDSlow }, { OpDESlow }, { OpDFSlow }, { OpE0Slow },
3729 { OpE1Slow }, { OpE2Slow }, { OpE3Slow }, { OpE4Slow }, { OpE5Slow },
3730 { OpE6Slow }, { OpE7Slow }, { OpE8Slow }, { OpE9Slow }, { OpEA },
3731 { OpEB }, { OpECSlow }, { OpEDSlow }, { OpEESlow }, { OpEFSlow },
3732 { OpF0Slow }, { OpF1Slow }, { OpF2Slow }, { OpF3Slow }, { OpF4Slow },
3733 { OpF5Slow }, { OpF6Slow }, { OpF7Slow }, { OpF8 }, { OpF9Slow },
3734 { OpFASlow }, { OpFB }, { OpFCSlow }, { OpFDSlow }, { OpFESlow },
3735 { OpFFSlow }
3736};
3737