X-Git-Url: https://notaz.gp2x.de/cgi-bin/gitweb.cgi?p=fceu.git;a=blobdiff_plain;f=ncpu.S;h=e7b07a635b6358b1d6e1fa0b6e7f9b8159877bbf;hp=d649f9a9add7414091de117da49dd8d4e8dd5191;hb=87e3eef5be4a5de92f97ee211ae4035d8d4b6494;hpb=370cff9a997d3bbdb65602b597a1a10e1e9a1542 diff --git a/ncpu.S b/ncpu.S index d649f9a..e7b07a6 100644 --- a/ncpu.S +++ b/ncpu.S @@ -3,11 +3,15 @@ File : ncpu.S Authors : FCA author modified and adapted by Yoyo. - adapted for fceu by notaz, 2007. + timing fixed, missing opcodes added + and adapted for fceu by notaz, 2007. **************************************/ #include "ncpu.h" +/* emulate (some) dummy reads (may need that because they affect open bus) */ +#define DO_DUMMY_READS 1 + @@@ @@@ Offets from REG_OP_TABLE @@@ @@ -16,7 +20,7 @@ #define OTOFFS_NES_REGS (nes_registers - cpu_exec_table) #define OTOFFS_PC_BASE (pc_base - cpu_exec_table) #define OTOFFS_IRQ_HOOK (MapIRQHook - cpu_exec_table) -#define OTOFFS_IRQH_CYC (MapIRQHookCyc - cpu_exec_table) +#define OTOFFS_TIMESTAMP (timestamp - cpu_exec_table) #define OTOFFS_X (X_ - cpu_exec_table) @ fceu @@ -33,9 +37,14 @@ /* bbbb: -.ascii "rebase: %04x" +.ascii "ab_a: %04x" .byte 0x0a,0 .align 4 +stmfd sp!,{r0-r3,r12,lr} +mov r1,r0 +ldr r0,=bbbb +bl printf +ldmfd sp!,{r0-r3,r12,lr} */ @@@ @@ -62,6 +71,19 @@ bbbb: .endm +@ updates fceu "timestamp" variable +@ loads cycles to reg, reg!=r1, trashes r1, kills flags +.macro FLUSH_TIMESTAMP reg + ands \reg, REG_CYCLE, #0xff + beq 1f + ldr r1, [REG_OP_TABLE, #OTOFFS_TIMESTAMP] + orr REG_CYCLE, REG_CYCLE, \reg, lsl #8 @ put cycles for do_irq_hook + add r1, r1, \reg + bic REG_CYCLE, REG_CYCLE, #0xff + str r1, [REG_OP_TABLE, #OTOFFS_TIMESTAMP] +1: +.endm + @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -73,22 +95,25 @@ bbbb: @@@ @@@ ¤Ê¤ó¤«Ì¾Á°¤¬ÊѤÀ¤Ê(¤É¡¼¤Ç¤â¤¤¡¼¤±¤É¡¼ @@@ -.macro CYCLE_NEXT n, hook_check=1 +.macro CYCLE_NEXT n, unused=0, do_cyc_add=1 @@DEBUG_INFO - subs REG_CYCLE, REG_CYCLE, #\n*48 +.if \do_cyc_add + add REG_CYCLE, REG_CYCLE, #\n +.endif + subs REG_CYCLE, REG_CYCLE, #\n*48<<16 ble cpu_exec_end -.if \hook_check tst REG_P_REST, #1<<16 - blne do_irq_hook -.endif + bne do_irq_hook + ldrb r0, [REG_PC], #1 tst REG_P_REST, #0xff<<8 ldreq pc, [REG_OP_TABLE, r0, lsl #2] @ do some messing to find out which IRQ is pending.. - tst REG_P_REST, #FCEU_IQNMI<<8 - bne do_int + @ assumption: NMI can be set only on very first run, because it is only set once before vblank.. +@ tst REG_P_REST, #FCEU_IQNMI<<8 +@ bne do_int tst REG_P_REST, #P_REST_I_FLAG @@ if I_FLAG=1, continue execution, don't trigger IRQ bicne REG_P_REST, REG_P_REST, #FCEU_IQTEMP<<8 @@ -97,6 +122,12 @@ bbbb: b do_int .endm +@ fceu needs timestamp cycles to be inremented before doing actual opcode. +@ this is only needed for ops which do memory i/o +.macro CYCLE_PRE n + add REG_CYCLE, REG_CYCLE, #\n +.endm + @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -107,11 +138,6 @@ bbbb: @@@ CLI¡¦PHP¤Ê¤É¥Õ¥é¥°¤òÊѹ¹¤·¤¿¾ì¹ç¤Ï¤³¤ì @@@ .macro CYCLE_NEXT_INT n -@ @@DEBUG_INFO -@ -@ subs REG_CYCLE, REG_CYCLE, #\n*48 -@ bgt cpu_exec_check_int -@ RETURN_FROM_CPU_EXEC CYCLE_NEXT \n .endm @@ -135,10 +161,13 @@ bbbb: @@@ @@@ ¥¢¥É¥ì¥¹¤òÆɤà @@@ -.macro ZP_READ_ADDR +.macro ZP_READ_ADDR update_db=0 ZP_READ ldrb REG_ADDR, [REG_ADDR, #1] orr REG_ADDR, r0, REG_ADDR, lsl #8 +.if \update_db + strb r0, [REG_OP_TABLE, #(OTOFFS_X + 0x10)] @ X.DB +.endif .endm @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -180,59 +209,16 @@ bbbb: @@@ ¥¹¥È¥¢¤¹¤ë¤À¤±¤ÎÌ¿Îá @@@ -@@@ 16¥Ó¥Ã¥È¥¢¥É¥ì¥¹¤«¤é¥í¡¼¥É¤Î¤ß -@@@ -@@@ RAM¤«¤é¤Î¥í¡¼¥É¤¬°ìÈÖ¿¤¤¤Î¤ÇÍ¥À褹¤ë -@@@ -@@@ READ_1 -@@@ OP -@@@ READ_2 -@@@ OP +@@@ Read byte @@@ -@@@ ¤Î¤è¤¦¤Ë»È¤¦ - -.macro READ_1 - movs r1, REG_ADDR, lsr #13 - adr lr, 9999f - @@ 0¤Ç¤Ê¤¤»þ¤Ï¥¸¥ã¥ó¥×¤¹¤ë¡£ - @@ ¤Á¤ç¤Ã¤È¹©Éפ·¤Æ1¥¯¥í¥Ã¥¯¸º¤é¤¹ - ldrne pc, [lr, -r1, lsl #2] - @@ RAM¤«¤é¥í¡¼¥É - bic r0, REG_ADDR, #0x1800 - add r0, r0, #OTOFFS_NES_RAM - ldrb r0, [r0, REG_OP_TABLE] -.endm - -.macro READ_2 - .long read_rom_byte - .long read_rom_byte - .long read_rom_byte - .long read_rom_byte - .long read_save_ram - .long read_high_reg - .long read_ppu_reg -9999: -.endm -.macro READ - mov r1, REG_ADDR, lsr #13 - adr lr, 1f - ldr pc, [pc, r1, lsl #2] - nop - .long 2f @ fast path - .long read_ppu_reg - .long read_high_reg - .long read_save_ram - .long read_rom_byte - .long read_rom_byte - .long read_rom_byte - .long read_rom_byte -2: - bic r0, REG_ADDR, #0x1800 - add r0, r0, #OTOFFS_NES_RAM - ldrb r0, [r0, REG_OP_TABLE] - @@ ¤È¤¤¤¦¤ï¤±¤Ç¥¸¥ã¥ó¥×¤¹¤ëɬÍפϤʤ¤ -1: +.macro READ unused_param + tst REG_ADDR, #0xe000 + @ RAM + biceq r0, REG_ADDR, #0x1800 + addeq r0, r0, #OTOFFS_NES_RAM + ldreqb r0, [r0, REG_OP_TABLE] + blne read_byte .endm @@@ @@ -249,12 +235,10 @@ bbbb: @@@ OP¤Ç¤Ïr3¤òÊݸ¤·¤Ê¤±¤ì¤Ð¤Ê¤é¤Ê¤¤ .macro READ_WRITE_1 - movs r3, REG_ADDR, lsr #13 - adr lr, 9999f - @@ 0¤Ç¤Ê¤¤»þ¤Ï¥¸¥ã¥ó¥×¤¹¤ë¡£ - @@ ¤Á¤ç¤Ã¤È¹©Éפ·¤Æ1¥¯¥í¥Ã¥¯¸º¤é¤¹ - ldrne pc, [lr, -r3, lsl #2] - @@ RAM¤«¤é¥í¡¼¥É + tst REG_ADDR, #0xe000 + adrne lr, 9999f + bne read_byte + @ RAM bic REG_ADDR, REG_ADDR, #0x1800 add REG_ADDR, REG_ADDR, #OTOFFS_NES_RAM ldrb r0, [REG_ADDR, REG_OP_TABLE]! @@ -265,61 +249,27 @@ bbbb: .endm .macro READ_WRITE_3 - .long read_rom_byte - .long read_rom_byte - .long read_rom_byte - .long read_rom_byte - .long read_save_ram - .long read_high_reg - .long read_ppu_reg 9999: + bl write_byte @ rmw first writes unmodified data .endm .macro READ_WRITE_4 - adr lr, 1f - ldr pc, [pc, r3, lsl #2] - nop - nop - .long write_ppu_reg - .long write_high_reg - .long write_save_ram - .long write_rom_byte - .long write_rom_byte - .long write_rom_byte - .long write_rom_byte -1: + bl write_byte @ and only then modified (Blaster Master) .endm @@@ -@@@ ½ñ¤­¹þ¤ß¤À¤±¤Î¾ì¹ç +@@@ Write r0 to [addr] @@@ -@@@ WRITE_1 -@@@ TAIL -@@@ WRITE_2 -@@@ TAIL -@@@ ¤È¤¹¤ë .macro WRITE_1 @@DEBUG_INFO - movs r1, REG_ADDR, lsr #13 - adr lr, 9999f - ldrne pc, [lr, -r1, lsl #2] - bic REG_ADDR, REG_ADDR, #0x1800 - add REG_ADDR, REG_ADDR, #OTOFFS_NES_RAM - - strb r0, [REG_ADDR, REG_OP_TABLE] -.endm + tst REG_ADDR, #0xe000 + biceq REG_ADDR, REG_ADDR, #0x1800 + addeq REG_ADDR, REG_ADDR, #OTOFFS_NES_RAM -.macro WRITE_2 - .long write_rom_byte - .long write_rom_byte - .long write_rom_byte - .long write_rom_byte - .long write_save_ram - .long write_high_reg - .long write_ppu_reg -9999: + streqb r0, [REG_ADDR, REG_OP_TABLE] + blne write_byte .endm @@@ @@ -330,10 +280,10 @@ bbbb: @@@ REG_ADDR¤òÊѹ¹¤¹¤ë¤¬µ¤¤Ë¤¹¤ë¤Ê @@@ .macro READ_WORD - READ + READ 0 mov REG_PC, r0 add REG_ADDR, REG_ADDR, #1 - READ + READ 0 orr r0, REG_PC, r0, lsl #8 .endm @@ -435,12 +385,13 @@ bbbb: @@@ ($nn), Y .macro INDY_ADDR ZERO_ADDR - ZP_READ_ADDR + ZP_READ_ADDR 1 @ SMB3 relies on open bus here add REG_ADDR, REG_ADDR, REG_Y bic REG_ADDR, REG_ADDR, #0x10000 and r0,REG_ADDR,#0xff cmp REG_Y,r0 - subgt REG_CYCLE,REG_CYCLE,#1*48 + addgt REG_CYCLE, REG_CYCLE, #1 + subgt REG_CYCLE, REG_CYCLE, #1*48<<16 .endm @ Indirect Indexed (for writes and rmws) @@ -461,23 +412,31 @@ bbbb: @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@ $nnnn -.macro ABS_ADDR +.macro ABS_ADDR update_db=0 +.if \update_db + ldrb r0, [REG_PC, #1] + ldrb REG_ADDR, [REG_PC], #2 + strb r0, [REG_OP_TABLE, #(OTOFFS_X + 0x10)] @ X.DB + orr REG_ADDR, REG_ADDR, r0, lsl #8 +.else tst REG_PC, #1 ldrneb REG_ADDR, [REG_PC], #1 ldrneb r0, [REG_PC], #1 ldreqh REG_ADDR, [REG_PC], #2 orrne REG_ADDR, REG_ADDR, r0, lsl #8 +.endif .endm @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@ $nnnn, X .macro ABSX_ADDR - ABS_ADDR + ABS_ADDR DO_DUMMY_READS add REG_ADDR, REG_ADDR, REG_X bic REG_ADDR, REG_ADDR, #0x10000 and r0,REG_ADDR,#0xff cmp REG_X,r0 - subgt REG_CYCLE,REG_CYCLE,#1*48 + addgt REG_CYCLE, REG_CYCLE, #1 + subgt REG_CYCLE, REG_CYCLE, #1*48<<16 .endm @ Absolute Indexed (for writes and rmws) @@ -490,12 +449,13 @@ bbbb: @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@ $nnnn, Y .macro ABSY_ADDR - ABS_ADDR + ABS_ADDR DO_DUMMY_READS @ a hack needed for Paperboy, Dirty Harry controls to work add REG_ADDR, REG_ADDR, REG_Y bic REG_ADDR, REG_ADDR, #0x10000 and r0,REG_ADDR,#0xff cmp REG_Y,r0 - subgt REG_CYCLE,REG_CYCLE,#1*48 + addgt REG_CYCLE, REG_CYCLE, #1 + subgt REG_CYCLE, REG_CYCLE, #1*48<<16 .endm @ Absolute Indexed (for writes and rmws) @@ -578,12 +538,12 @@ op38: @ SEC opD8: @ CLD IMPLIED - @@bic REG_P_REST, REG_P_REST, #P_REST_D_FLAG + bic REG_P_REST, REG_P_REST, #P_REST_D_FLAG CYCLE_NEXT 2 opF8: @ SED IMPLIED - @@orr REG_P_REST, REG_P_REST, #P_REST_D_FLAG + orr REG_P_REST, REG_P_REST, #P_REST_D_FLAG CYCLE_NEXT 2 op58: @ CLI @@ -727,50 +687,39 @@ opB5: @ LDA $nn, X CYCLE_NEXT 4 opAD: @ LDA $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_LDA - CYCLE_NEXT 4 - READ_2 + READ OP_LDA - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opBD: @ LDA $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_LDA - CYCLE_NEXT 4 - READ_2 + READ OP_LDA - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opB9: @ LDA $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_LDA - CYCLE_NEXT 4 - READ_2 + READ OP_LDA - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opA1: @ LDA ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_LDA - CYCLE_NEXT 6 - READ_2 + READ OP_LDA - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opB1: @ LDA ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_LDA - CYCLE_NEXT 5 - READ_2 + READ OP_LDA - CYCLE_NEXT 5 - + CYCLE_NEXT 5,1,0 opA2: @ LDX #$nn IMM_VALUE @@ -790,22 +739,18 @@ opB6: @ LDX $nn, Y CYCLE_NEXT 4 opAE: @ LDX $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_LDX - CYCLE_NEXT 4 - READ_2 + READ OP_LDX - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opBE: @ LDX $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_LDX - CYCLE_NEXT 4 - READ_2 + READ OP_LDX - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 @@ -829,22 +774,18 @@ opB4: @ LDY $nn, X opAC: @ LDY $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_LDY - CYCLE_NEXT 4 - READ_2 + READ OP_LDY - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opBC: @ LDY $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_LDY - CYCLE_NEXT 4 - READ_2 + READ OP_LDY - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -873,44 +814,39 @@ op95: @ STA $nn, X CYCLE_NEXT 4 op8D: @ STA $nnnn + CYCLE_PRE 4 ABS_ADDR OP_STA WRITE_1 - CYCLE_NEXT 4 - WRITE_2 - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op9D: @ STA $nnnn, X + CYCLE_PRE 5 ABSX_ADDR_W OP_STA WRITE_1 - CYCLE_NEXT 5 - WRITE_2 - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 op99: @ STA $nnnn, Y + CYCLE_PRE 5 ABSY_ADDR_W OP_STA WRITE_1 - CYCLE_NEXT 5 - WRITE_2 - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 op81: @ STA ($nn, X) + CYCLE_PRE 6 INDX_ADDR OP_STA WRITE_1 - CYCLE_NEXT 6 - WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op91: @ STA ($nn), Y + CYCLE_PRE 6 INDY_ADDR_W OP_STA WRITE_1 - CYCLE_NEXT 6 - WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op86: @ STX $nn @@ -924,12 +860,11 @@ op96: @ STX $nn, Y CYCLE_NEXT 4 op8E: @ STX $nnnn + CYCLE_PRE 4 ABS_ADDR mov r0, REG_X WRITE_1 - CYCLE_NEXT 4 - WRITE_2 - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op84: @ STY $nn @@ -943,12 +878,11 @@ op94: @ STY $nn, X CYCLE_NEXT 4 op8C: @ STY $nnnn + CYCLE_PRE 4 ABS_ADDR mov r0, REG_Y WRITE_1 - CYCLE_NEXT 4 - WRITE_2 - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -1001,26 +935,28 @@ opF6: @ INC $nn, X CYCLE_NEXT 6 opEE: @ INC $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_INC READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_INC READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opFE: @ INC $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_INC READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_INC READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 opE8: @ INX IMPLIED @@ -1047,26 +983,28 @@ opD6: @ DEC $nn, X CYCLE_NEXT 6 opCE: @ DEC $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_DEC READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_DEC READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opDE: @ DEC $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_DEC READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_DEC READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 opCA: @ DEX IMPLIED @@ -1129,49 +1067,39 @@ op75: @ ADC $nn, X CYCLE_NEXT 4 op6D: @ ADC $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_ADC - CYCLE_NEXT 4 - READ_2 + READ OP_ADC - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op7D: @ ADC $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_ADC - CYCLE_NEXT 4 - READ_2 + READ OP_ADC - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op79: @ ADC $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_ADC - CYCLE_NEXT 4 - READ_2 + READ OP_ADC - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op61: @ ADC ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_ADC - CYCLE_NEXT 6 - READ_2 + READ OP_ADC - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op71: @ ADC ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_ADC - CYCLE_NEXT 5 - READ_2 + READ OP_ADC - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 opEB: @ USBC #$nn opE9: @ SBC #$nn @@ -1192,49 +1120,39 @@ opF5: @ SBC $nn, X CYCLE_NEXT 4 opED: @ SBC $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_SBC - CYCLE_NEXT 4 - READ_2 + READ OP_SBC - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opFD: @ SBC $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_SBC - CYCLE_NEXT 4 - READ_2 + READ OP_SBC - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opF9: @ SBC $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_SBC - CYCLE_NEXT 4 - READ_2 + READ OP_SBC - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opE1: @ SBC ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_SBC - CYCLE_NEXT 6 - READ_2 + READ OP_SBC - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opF1: @ SBC ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_SBC - CYCLE_NEXT 5 - READ_2 + READ OP_SBC - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -1280,49 +1198,39 @@ op35: @ AND $nn, X CYCLE_NEXT 4 op2D: @ AND $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_AND - CYCLE_NEXT 4 - READ_2 + READ OP_AND - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op3D: @ AND $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_AND - CYCLE_NEXT 4 - READ_2 + READ OP_AND - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op39: @ AND $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_AND - CYCLE_NEXT 4 - READ_2 + READ OP_AND - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op21: @ AND ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_AND - CYCLE_NEXT 6 - READ_2 + READ OP_AND - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op31: @ AND ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_AND - CYCLE_NEXT 5 - READ_2 + READ OP_AND - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 op49: @ EOR #$nn @@ -1343,49 +1251,39 @@ op55: @ EOR $nn, X CYCLE_NEXT 4 op4D: @ EOR $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_EOR - CYCLE_NEXT 4 - READ_2 + READ OP_EOR - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op5D: @ EOR $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_EOR - CYCLE_NEXT 4 - READ_2 + READ OP_EOR - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op59: @ EOR $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_EOR - CYCLE_NEXT 4 - READ_2 + READ OP_EOR - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op41: @ EOR ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_EOR - CYCLE_NEXT 6 - READ_2 + READ OP_EOR - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op51: @ EOR ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_EOR - CYCLE_NEXT 5 - READ_2 + READ OP_EOR - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 op09: @ ORA #$nn @@ -1406,49 +1304,39 @@ op15: @ ORA $nn, X CYCLE_NEXT 4 op0D: @ ORA $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_ORA - CYCLE_NEXT 4 - READ_2 + READ OP_ORA - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op1D: @ ORA $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_ORA - CYCLE_NEXT 4 - READ_2 + READ OP_ORA - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op19: @ ORA $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_ORA - CYCLE_NEXT 4 - READ_2 + READ OP_ORA - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 op01: @ ORA ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_ORA - CYCLE_NEXT 6 - READ_2 + READ OP_ORA - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op11: @ ORA ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_ORA - CYCLE_NEXT 5 - READ_2 + READ OP_ORA - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 @@ -1503,49 +1391,39 @@ opD5: @ CMP $nn, X CYCLE_NEXT 4 opCD: @ CMP $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_CMP - CYCLE_NEXT 4 - READ_2 + READ OP_CMP - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opDD: @ CMP $nnnn, X + CYCLE_PRE 4 ABSX_ADDR - READ_1 - OP_CMP - CYCLE_NEXT 4 - READ_2 + READ OP_CMP - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opD9: @ CMP $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_CMP - CYCLE_NEXT 4 - READ_2 + READ OP_CMP - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opC1: @ CMP ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_CMP - CYCLE_NEXT 6 - READ_2 + READ OP_CMP - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opD1: @ CMP ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_CMP - CYCLE_NEXT 5 - READ_2 + READ OP_CMP - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 opE0: @ CPX #$nn @@ -1560,13 +1438,11 @@ opE4: @ CPX $nn CYCLE_NEXT 3 opEC: @ CPX $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_CPX - CYCLE_NEXT 4 - READ_2 + READ OP_CPX - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opC0: @ CPY #$nn @@ -1581,13 +1457,11 @@ opC4: @ CPY $nn CYCLE_NEXT 3 opCC: @ CPY $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_CPY - CYCLE_NEXT 4 - READ_2 + READ OP_CPY - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -1618,13 +1492,11 @@ op24: @ BIT $nn CYCLE_NEXT 3 op2C: @ BIT $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_BIT - CYCLE_NEXT 4 - READ_2 + READ OP_BIT - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -1687,26 +1559,28 @@ op16: @ ASL $nn, X CYCLE_NEXT 6 op0E: @ ASL $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_ASL READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_ASL READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op1E: @ ASL $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_ASL READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_ASL READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op4A: @ LSR A @@ -1729,26 +1603,28 @@ op56: @ LSR $nn, X CYCLE_NEXT 6 op4E: @ LSR $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_LSR READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_LSR READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op5E: @ LSR $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_LSR READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_LSR READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -1816,27 +1692,29 @@ op36: @ ROL $nn, X CYCLE_NEXT 6 op2E: @ ROL $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_ROL READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_ROL READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op3E: @ ROL $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_ROL READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_ROL READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op6A: @ ROR A @@ -1859,26 +1737,28 @@ op76: @ ROR $nn, X CYCLE_NEXT 6 op6E: @ ROR $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_ROR READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_ROR READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op7E: @ ROR $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_ROR READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_ROR READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -1901,14 +1781,16 @@ op7E: @ ROR $nnnn, X and r1,r1,#0xff add r1,r3,r1 tst r1,#0x100 - subne REG_CYCLE,REG_CYCLE, #1*48 + addne REG_CYCLE, REG_CYCLE, #1 + subne REG_CYCLE, REG_CYCLE, #1*48<<16 .endm .macro BRANCH_EQ ldreqsb r1, [REG_PC], #1 movne r1, #1 add REG_PC, REG_PC, r1 - subeq REG_CYCLE, REG_CYCLE, #1*48 + addeq REG_CYCLE, REG_CYCLE, #1 + subeq REG_CYCLE, REG_CYCLE, #1*48<<16 bne 1f HAD_BRANCH 1: @@ -1918,7 +1800,8 @@ op7E: @ ROR $nnnn, X ldrnesb r1, [REG_PC], #1 moveq r1, #1 add REG_PC, REG_PC, r1 - subne REG_CYCLE, REG_CYCLE, #1*48 + addne REG_CYCLE, REG_CYCLE, #1 + subne REG_CYCLE, REG_CYCLE, #1*48<<16 beq 1f HAD_BRANCH 1: @@ -2002,12 +1885,6 @@ op70: @ BVS $nn and r0, r0, #0xFF .endm -.macro OP_SHY - mov r0,REG_ADDR, lsr #8 - add r0,r0,#1 - and r0,r0,REG_Y -.endm - .macro OP_SRE movs r0, r0, lsr #1 @@set C flag @@ -2043,13 +1920,9 @@ op70: @ BVS $nn @@ ¥­¥ã¥ê¡¼¤òÊݸ adc REG_P_REST, r1, r1 and REG_A,REG_A,r0,lsl #24 + orr REG_NZ, REG_A, REG_A, lsr #24 @ according to fceu .endm -.macro OP_RRA - movs r1, REG_P_REST, lsr #1 - orrcs r0, r0, #0x100 - movs r0, r0, lsr #1 -.endm @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -2072,69 +1945,66 @@ op57: @ SRE $nn, X CYCLE_NEXT 6 op4F: @ SRE $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_SRE READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_SRE READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op5F: @ SRE $nnnn, X - ABSX_ADDR + CYCLE_PRE 7 + ABSX_ADDR_W READ_WRITE_1 OP_SRE READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_SRE READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op5B: @ SRE $nnnn, Y - ABSY_ADDR + CYCLE_PRE 7 + ABSY_ADDR_W READ_WRITE_1 OP_SRE READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_SRE READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op43: @ SRE ($nn, X) + CYCLE_PRE 8 INDX_ADDR READ_WRITE_1 OP_SRE READ_WRITE_2 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_SRE READ_WRITE_4 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op53: @ SRE ($nn), Y + CYCLE_PRE 8 INDY_ADDR_W READ_WRITE_1 OP_SRE READ_WRITE_2 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_SRE READ_WRITE_4 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 -op9C: @ SHY $nnnn, X - ABSX_ADDR_W - OP_SHY - WRITE_1 - CYCLE_NEXT 5 - WRITE_2 - CYCLE_NEXT 5 - opE7: @ ISB $nn ZERO_ADDR ZP_READ_W @@ -2152,70 +2022,75 @@ opF7: @ ISB $nn, X CYCLE_NEXT 6 opEF: @ ISB $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_ISB READ_WRITE_2 OP_SBC - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_ISB READ_WRITE_4 OP_SBC - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opFF: @ ISB $nnnn,X - ABSX_ADDR + CYCLE_PRE 7 + ABSX_ADDR_W READ_WRITE_1 OP_ISB READ_WRITE_2 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_ISB READ_WRITE_4 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 opFB: @ ISB $nnnn, Y - ABSY_ADDR + CYCLE_PRE 7 + ABSY_ADDR_W READ_WRITE_1 OP_ISB READ_WRITE_2 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_ISB READ_WRITE_4 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 opE3: @ ISB ($nn, X) + CYCLE_PRE 8 INDX_ADDR READ_WRITE_1 OP_ISB READ_WRITE_2 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_ISB READ_WRITE_4 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 8,1,0 opF3: @ ISB ($nn), Y + CYCLE_PRE 8 INDY_ADDR READ_WRITE_1 OP_ISB READ_WRITE_2 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_ISB READ_WRITE_4 OP_SBC - CYCLE_NEXT 7 + CYCLE_NEXT 8,1,0 opA7: @ LAX $nn ZERO_ADDR @@ -2230,47 +2105,40 @@ opB7: @ LAX $nn, Y CYCLE_NEXT 4 opAF: @ LAX $nnnn + CYCLE_PRE 4 ABS_ADDR - READ_1 - OP_LAX - CYCLE_NEXT 4 - READ_2 + READ OP_LAX - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opBF: @ LAX $nnnn, Y + CYCLE_PRE 4 ABSY_ADDR - READ_1 - OP_LAX - CYCLE_NEXT 4 - READ_2 + READ OP_LAX - CYCLE_NEXT 4 + CYCLE_NEXT 4,1,0 opA3: @ LAX ($nn, X) + CYCLE_PRE 6 INDX_ADDR - READ_1 - OP_LAX - CYCLE_NEXT 6 - READ_2 + READ OP_LAX - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opB3: @ LAX ($nn), Y + CYCLE_PRE 5 INDY_ADDR - READ_1 - OP_LAX - CYCLE_NEXT 5 - READ_2 + READ OP_LAX - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 op07: @ SLO $nn + CYCLE_PRE 5 ZERO_ADDR ZP_READ_W OP_SLO ZP_WRITE_W - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 op17: @ SLO $nn, X ZEROX_ADDR @@ -2280,59 +2148,64 @@ op17: @ SLO $nn, X CYCLE_NEXT 6 op0F: @ SLO $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_SLO READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_SLO READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op1F: @ SLO $nnnn, X - ABSX_ADDR + CYCLE_PRE 7 + ABSX_ADDR_W READ_WRITE_1 OP_SLO READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_SLO READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op1B: @ SLO $nnnn, Y + CYCLE_PRE 7 ABSY_ADDR_W READ_WRITE_1 OP_SLO READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_SLO READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op03: @ SLO ($nn, X) + CYCLE_PRE 8 INDX_ADDR READ_WRITE_1 OP_SLO READ_WRITE_2 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_SLO READ_WRITE_4 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op13: @ SLO ($nn), Y + CYCLE_PRE 8 INDY_ADDR_W READ_WRITE_1 OP_SLO READ_WRITE_2 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_SLO READ_WRITE_4 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 opCB: @ SBX #$nn IMM_VALUE @@ -2356,70 +2229,75 @@ opD7: @ DCP $nn, X CYCLE_NEXT 6 opCF: @ DCP $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_DCP READ_WRITE_2 OP_CMP - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_DCP READ_WRITE_4 OP_CMP - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 opDF: @ DCP $nnnn, X - ABSX_ADDR + CYCLE_PRE 7 + ABSX_ADDR_W READ_WRITE_1 OP_DCP READ_WRITE_2 OP_CMP - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_DCP READ_WRITE_4 OP_CMP - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 opDB: @ DCP $nnnn, Y - ABSY_ADDR + CYCLE_PRE 7 + ABSY_ADDR_W READ_WRITE_1 OP_DCP READ_WRITE_2 OP_CMP - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_DCP READ_WRITE_4 OP_CMP - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 opC3: @ DCP ($nn, X) + CYCLE_PRE 8 INDX_ADDR READ_WRITE_1 OP_DCP READ_WRITE_2 OP_CMP - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_DCP READ_WRITE_4 OP_CMP - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 opD3: @ DCP ($nn), Y - INDY_ADDR + CYCLE_PRE 8 + INDY_ADDR_W READ_WRITE_1 OP_DCP READ_WRITE_2 OP_CMP - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_DCP READ_WRITE_4 OP_CMP - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op27: @ RLA $nn ZERO_ADDR @@ -2436,64 +2314,69 @@ op37: @ RLA $nn, X CYCLE_NEXT 6 op2F: @ RLA $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 OP_RLA READ_WRITE_2 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 OP_RLA READ_WRITE_4 - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op3F: @ RLA $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 OP_RLA READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_RLA READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op3B: @ RLA $nnnn, Y + CYCLE_PRE 7 ABSY_ADDR_W READ_WRITE_1 OP_RLA READ_WRITE_2 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 OP_RLA READ_WRITE_4 - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op23: @ RLA ($nn, X) + CYCLE_PRE 8 INDX_ADDR READ_WRITE_1 OP_RLA READ_WRITE_2 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_RLA READ_WRITE_4 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op33: @ RLA ($nn), Y + CYCLE_PRE 8 INDY_ADDR_W READ_WRITE_1 OP_RLA READ_WRITE_2 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 OP_RLA READ_WRITE_4 - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op67: @ RRA $nn ZERO_ADDR ZP_READ_W - OP_RRA + OP_ROR ZP_WRITE_W OP_ADC CYCLE_NEXT 5 @@ -2501,75 +2384,80 @@ op67: @ RRA $nn op77: @ RRA $nn, X ZEROX_ADDR ZP_READ_W - OP_RRA + OP_ROR ZP_WRITE_W OP_ADC CYCLE_NEXT 6 op6F: @ RRA $nnnn + CYCLE_PRE 6 ABS_ADDR READ_WRITE_1 - OP_RRA + OP_ROR READ_WRITE_2 OP_ADC - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 READ_WRITE_3 - OP_RRA + OP_ROR READ_WRITE_4 OP_ADC - CYCLE_NEXT 6 + CYCLE_NEXT 6,1,0 op7F: @ RRA $nnnn, X + CYCLE_PRE 7 ABSX_ADDR_W READ_WRITE_1 - OP_RRA + OP_ROR READ_WRITE_2 OP_ADC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 - OP_RRA + OP_ROR READ_WRITE_4 OP_ADC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op7B: @ RRA $nnnn, Y + CYCLE_PRE 7 ABSY_ADDR_W READ_WRITE_1 - OP_RRA + OP_ROR READ_WRITE_2 OP_ADC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 READ_WRITE_3 - OP_RRA + OP_ROR READ_WRITE_4 OP_ADC - CYCLE_NEXT 7 + CYCLE_NEXT 7,1,0 op63: @ RRA ($nn, X) + CYCLE_PRE 8 INDX_ADDR READ_WRITE_1 - OP_RRA + OP_ROR READ_WRITE_2 OP_ADC - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 - OP_RRA + OP_ROR READ_WRITE_4 OP_ADC - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op73: @ RRA ($nn), Y + CYCLE_PRE 8 INDY_ADDR_W READ_WRITE_1 - OP_RRA + OP_ROR READ_WRITE_2 OP_ADC - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 READ_WRITE_3 - OP_RRA + OP_ROR READ_WRITE_4 OP_ADC - CYCLE_NEXT 8 + CYCLE_NEXT 8,1,0 op04: @ NOP $nn @@ -2579,8 +2467,14 @@ op64: CYCLE_NEXT 3 op0C: @ NOP $nnnn + CYCLE_PRE 4 +#if DO_DUMMY_READS + ABS_ADDR + READ +#else add REG_PC,REG_PC,#2 - CYCLE_NEXT 4 +#endif + CYCLE_NEXT 4,1,0 op14: @ NOP $nn, X op34: @@ -2605,17 +2499,177 @@ op5C: op7C: opDC: opFC: + CYCLE_PRE 4 +#if DO_DUMMY_READS + ABSX_ADDR + READ +#else add REG_PC,REG_PC,#2 - CYCLE_NEXT 4 +#endif + CYCLE_NEXT 4,1,0 op80: @ NOP #$nn op82: op89: opC2: + add REG_PC,REG_PC,#1 + CYCLE_NEXT 2 + opE2: add REG_PC,REG_PC,#1 + CYCLE_NEXT 3 + +op02: @ JAM: try to be compatible with fceu +op12: +op22: +op32: +op42: +op52: +op62: +op72: +op92: +opB2: +opD2: +opF2: + sub REG_PC,REG_PC,#1 + add REG_CYCLE, REG_CYCLE, #0x10 + FLUSH_TIMESTAMP r0 + add REG_CYCLE, REG_CYCLE, #0xef + sub REG_CYCLE, REG_CYCLE, #0x00d00000 @ 0xff*48<<16 + sub REG_CYCLE, REG_CYCLE, #0x2f000000 + CYCLE_NEXT 2 + +op0B: @ ANC #$nn +op2B: @ ANC #$nn + IMM_VALUE + OP_AND + bic REG_P_REST, REG_P_REST, #P_REST_C_FLAG + orr REG_P_REST, REG_P_REST, REG_A, lsr #31 + CYCLE_NEXT 2 + +op4B: @ ASR #$nn + IMM_VALUE + OP_AND + OP_LSR_A CYCLE_NEXT 2 +op6B: @ ARR #$nn + IMM_VALUE + OP_AND + bic REG_P_REST, REG_P_REST, #P_REST_C_FLAG + eor r0, REG_A, REG_A, lsr #1 + and r0, r0, #0x40000000 + orr REG_P_REST, REG_P_REST, r0, lsr #24 + OP_ROR_A + CYCLE_NEXT 2 + +op83: @ SAX/AAX ($nn, X) + CYCLE_PRE 6 + INDX_ADDR + and r0, REG_X, REG_A, lsr #24 + WRITE_1 + CYCLE_NEXT 6,1,0 + +op87: @ SAX/AAX $nn + ZERO_ADDR + and r0, REG_X, REG_A, lsr #24 + ZP_WRITE + CYCLE_NEXT 3 + +op8B: @ ANE/XAA #$nn + orr REG_A, REG_A, #0xee000000 + and REG_A, REG_A, REG_X, lsl #24 + IMM_VALUE + OP_AND + CYCLE_NEXT 2 + +op8F: @ SAX/AAX $nnnn + CYCLE_PRE 4 + ABS_ADDR + and r0, REG_X, REG_A, lsr #24 + WRITE_1 + CYCLE_NEXT 4,1,0 + +.macro AMY_MSB + sub r0, REG_ADDR, REG_Y + mov r0, r0, lsr #8 + add r0, r0, #1 +.endm + +op93: @ SHA/AXA ($nn), Y + CYCLE_PRE 6 + INDY_ADDR_W + AMY_MSB + and r0, r0, REG_X + and r0, r0, REG_A, lsr #24 + WRITE_1 + CYCLE_NEXT 6,1,0 + +op97: @ SAX,AAX $nn, Y + ZEROY_ADDR + and r0, REG_X, REG_A, lsr #24 + ZP_WRITE + CYCLE_NEXT 4 + +op9B: @ SHS/XAS $nnnn, Y + and r0, REG_X, REG_A, lsr #24 + bic REG_S, REG_S, #0xFF << 24 + orr REG_S, REG_S, r0, lsl #24 + ABSY_ADDR_W + AMY_MSB + and r0, r0, REG_S, lsr #24 + WRITE_1 + CYCLE_NEXT 5 + +op9C: @ SHY/SYA $nnnn, X + CYCLE_PRE 5 + ABSX_ADDR_W + sub r0, REG_ADDR, REG_X + mov r0, r0, lsr #8 + add r0, r0, #1 + and r0, r0, REG_Y + WRITE_1 + CYCLE_NEXT 5,1,0 + +op9E: @ SHX/SXA $nnnn, Y + ABSY_ADDR_W + AMY_MSB + and r0, r0, REG_X + WRITE_1 + CYCLE_NEXT 5 + +op9F: @ SHA/AXA $nnnn, Y + CYCLE_PRE 5 + ABSY_ADDR_W + AMY_MSB + and r0, r0, REG_X + and r0, r0, REG_A, lsr #24 + WRITE_1 + CYCLE_NEXT 5,1,0 + +opAB: @ LXA/ATX/OAL #$nn + IMM_VALUE + orr REG_A, REG_A, #0xee000000 + OP_AND + mov REG_X, REG_A, lsr #24 + CYCLE_NEXT 2 + +opBB: @ LAS/LAR $nnnn,Y + CYCLE_PRE 4 + ABSY_ADDR_W + READ_WRITE_1 + READ_WRITE_2 + b opBB_ + READ_WRITE_3 + READ_WRITE_4 +opBB_: and REG_X, r0, REG_S, lsr #24 + bic REG_S, REG_S, #0xff<<24 + orr REG_S, REG_S, REG_X, lsl #24 + mov REG_A, REG_X, lsl #24 + orr REG_NZ, REG_A, REG_A, lsr #24 + CYCLE_NEXT 4,1,0 + + @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -2628,26 +2682,27 @@ opE2: @@@ ---- @ JMP ($nnnn) op6C: + CYCLE_PRE 5 ABS_ADDR and r0, REG_ADDR, #0xFF teq r0, #0xFF beq jmp_indirect_bug READ_WORD REBASE_PC - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 jmp_indirect_bug: @@ @@ BUG is : to not read word at REG_ADDR, because it loops @@ but read low part at REG_ADDR and high part at REG_ADDR&0xFF00 instead of REG_ADDR+1 @@ - READ + READ 0 mov REG_PC, r0 and REG_ADDR, REG_ADDR, #0xff00 - READ + READ 0 orr r0, REG_PC, r0, lsl #8 REBASE_PC - CYCLE_NEXT 5 + CYCLE_NEXT 5,1,0 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ -2749,6 +2804,7 @@ op60: @@@ WARNING: decrements REG_PC @@@ do_int: + add REG_CYCLE, REG_CYCLE, #7 ldr r0, [REG_OP_TABLE, #OTOFFS_PC_BASE] sub REG_PC, REG_PC, #1 sub r0, REG_PC, r0 @@ -2766,7 +2822,7 @@ do_int: REBASE_PC @ CYCLE_NEXT 7 - subs REG_CYCLE, REG_CYCLE, #7*48 + subs REG_CYCLE, REG_CYCLE, #7*48<<16 ble cpu_exec_end ldrb r0, [REG_PC], #1 tst REG_P_REST, #0xff<<8 @@ -2820,28 +2876,30 @@ reset_cpu: @@@ low-level memhandlers @@@ +/* +@ disabled because no improvements noticed, only causes trouble (with gg for example) read_rom_byte: -#ifndef DEBUG_ASM_6502 +@ try to avoid lookup of every address at least for ROM and RAM areas +@ I've verified that if ARead[0xfff0] points to CartBR, it is always normal ROM read. ldr r0, =CartBR ldr r2, =ARead mov r1, #0xff00 orr r1, r1, r1, lsr #4 ldr r1, [r2, r1, lsl #2] @ if (ARead[0xfff0] == CartBR) cmp r0, r1 - bne read_ppu_reg + bne read_byte ldr r2, =Page mov r1, REG_ADDR, lsr #11 ldr r2, [r2, r1, lsl #2] ldrb r0, [r2, REG_ADDR] bx lr -#endif +*/ -read_ppu_reg: -read_high_reg: -read_save_ram: +read_byte: @ must preserve r3 for the callers too @ TODO: check if all of saves are needed, _DB (is full needed?) + FLUSH_TIMESTAMP r2 @ needed for TryFixit1 str REG_PC, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x0c)] @ might get rebased str REG_P_REST, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x10)] @ might set irq str REG_CYCLE, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x1c)] @ might get used @@ -2872,17 +2930,16 @@ read_save_ram: bx lr -write_ppu_reg: -write_high_reg: -write_save_ram: -write_rom_byte: +write_byte: + FLUSH_TIMESTAMP r2 @ Blaster Master, more... #ifndef DEBUG_ASM_6502 - @ must preserve r3 for the callers too + @ must preserve r0 (data) and r3 for the callers str REG_PC, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x0c)] @ might get rebased str REG_P_REST, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x10)] @ might set irq str REG_CYCLE, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x1c)] @ might get used mov REG_PC, lr @ r7 mov REG_P_REST, r3 @ r8 + mov REG_CYCLE, r0 @ r11 ldr r2, =BWrite mov r1, r0 @@ -2893,6 +2950,7 @@ write_rom_byte: ldr REG_OP_TABLE, =cpu_exec_table @ got trashed because was in r12 mov lr, REG_PC mov r3, REG_P_REST + mov r0, REG_CYCLE ldr REG_PC, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x0c)] @ might get rebased ldr REG_P_REST, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x10)] @ might set irq ldr REG_CYCLE, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x1c)] @ might get used @@ -2906,6 +2964,7 @@ write_rom_byte: ldr r2, =dwrite_count_a add r1, r1, #1 str r1, [r2] + and r0, r0, #0xff #endif bx lr @@ -2930,14 +2989,26 @@ cpu_exec: @ ldr REG_OP_TABLE, = cpu_exec_table @ set on init - tst REG_P_REST, #1<<16 - strne REG_CYCLE, [REG_OP_TABLE, #OTOFFS_IRQH_CYC] + ldrb r0, [REG_PC], #1 + tst REG_P_REST, #0xff<<8 + ldreq pc, [REG_OP_TABLE, r0, lsl #2] + + @ assumption: NMI can be set only on very first run, because it is only set once before vblank.. + tst REG_P_REST, #FCEU_IQNMI<<8 + bne do_int + tst REG_P_REST, #P_REST_I_FLAG + @@ if I_FLAG=1, continue execution, don't trigger IRQ + bicne REG_P_REST, REG_P_REST, #FCEU_IQTEMP<<8 + ldrne pc, [REG_OP_TABLE, r0, lsl #2] + @@ I_FLAG=0 and REST is checked, we have a IRQ + b do_int - CYCLE_NEXT 0, 0 cpu_exec_end: + FLUSH_TIMESTAMP r0 + tst REG_P_REST, #1<<16 - blne do_irq_hook + bne do_irq_hook_final ldr r0, =nes_registers stmia r0, {r4-r12} @@ -3016,14 +3087,12 @@ nes_internal_ram: .fill 0x100, 1, 0 nes_stack: .fill 0x700, 1, 0 -@ TODO: write code which keeps it up-to-date pc_base: .long 0 MapIRQHook: .long 0 -MapIRQHookCyc: - .long 0 timestamp: +timestamp_a: .long 0 #ifndef DEBUG_ASM_6502 X: @@ -3037,92 +3106,6 @@ X_: .fill 0x20, 1, 0 ALIGN -@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ -@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ -@@@ -@@@ Undefined Opcodes -@@@ -op0B: @ ANC #$nn -op2B: @ ANC #$nn -op8B: @ ANE #$nn -op6B: @ ARR #$nn -op4B: @ ASR #$nn -@opC7: @ DCP $nn -@opD7: @ DCP $nn, X -@opCF: @ DCP $nnnn -@opDF: @ DCP $nnnn, X -@opDB: @ DCP $nnnn, Y -@opC3: @ DCP ($nn, X) -@opD3: @ DCP ($nn), Y - - - -@opE7: @ ISB $nn -@opF7: @ ISB $nn, X -@opEF: @ ISB $nnnn -@opFF: @ ISB $nnnn, X -@opFB: @ ISB $nnnn, Y -@opE3: @ ISB ($nn, X) -@opF3: @ ISB ($nn), Y - - -op02: @ JAM -op12: -op22: -op32: -op42: -op52: -op62: -op72: -op92: -opB2: -opD2: -opF2: - - -opBB: @ LAS $nnnn,Y -@opA3: @ LAX ($nn, X) -@opA7: @ LAX $nn -@opB7: @ LAX $nn, Y -@opAF: @ LAX $nnnn -@opBF: @ LAX $nnnn, Y - -@opB3: @ LAX ($nn), Y -opAB: @ LXA #$nn -@op27: @ RLA $nn -@op37: @ RLA $nn, X -@op2F: @ RLA $nnnn -@op3F: @ RLA $nnnn, X -@op23: @ RLA ($nn, X) -@op67: @ RRA $nn -@op77: @ RRA $nn, X -@op6F: @ RRA $nnnn -@op7F: @ RRA $nnnn, X -@op63: @ RRA ($nn, X) -op87: @ SAX $nn -op97: @ SAX $nn, Y -op8F: @ SAX $nnnn -op83: @ SAX ($nn, X) -@opCB: @ SBX #$nn -op9F: @ SHA $nnnn, Y -op93: @ SHA ($nn), Y -op9B: @ SHS $nnnn, Y -op9E: @ SHX $nnnn, Y -@op03: @ SLO ($nn, X) -@op07: @ SLO $nn -@op17: @ SLO $nn, X -@op0F: @ SLO $nnnn -@op1F: @ SLO $nnnn, X -@op47: @ SRE $nn -@op57: @ SRE $nn, X -@op4F: @ SRE $nnnn -@op5F: @ SRE $nnnn, X -@op5B: @ SRE $nnnn, Y -@op43: @ SRE ($nn, X) - CYCLE_NEXT 1 -@ emu_panic? - - @@@@@@@@@@@@@@@@@@@@@@@@@@ @ fceu stuff... @@ -3145,14 +3128,15 @@ op9E: @ SHX $nnnn, Y .globl RAM .globl timestamp #else + .globl X_ .globl nes_internal_ram + .globl timestamp_a #endif .globl X6502_Reset_a @ (void); .globl X6502_Power_a @ (void); .globl X6502_Run_a @ (int32 cycles); .globl TriggerIRQ_a @ (void); .globl TriggerNMI_a @ (void); - .globl TriggerNMINSF_a @ (void); .globl X6502_AddCycles_a @ (int x); .globl X6502_IRQBegin_a @ (int w); .globl X6502_IRQEnd_a @ (int w); @@ -3207,18 +3191,21 @@ TriggerNMI_a: b X6502_IRQBegin_a -TriggerNMINSF_a: - @ not implemented - bx lr - - X6502_AddCycles_a: + ldr r3, =timestamp ldr r2, =nes_registers - ldr r1, [r2, #0x1c] + ldr r1, [r3] + add r1, r1, r0 + str r1, [r3] + ldrsh r1, [r2, #0x1e] mvn r3, #47 @ r3=-48 - mla r0, r3, r0, r1 - str r0, [r2, #0x1c] - bx lr + mla r3, r0, r3, r1 + ldr r1, =MapIRQHook @ hack.. + strh r3, [r2, #0x1e] + ldr r1, [r1] + tst r1, r1 + bxeq lr + bx r1 @ rebase PC when not executing or in memhandlers @@ -3238,32 +3225,62 @@ X6502_Rebase_a: @ the nasty MapIRQHook thing from FCE.. @ test Gradius 2 (J) if you change this do_irq_hook: - @ ((cycles >> 4) * 43) >> 7; // aproximating /= 48 - ldr r1, [REG_OP_TABLE, #OTOFFS_IRQH_CYC] - str REG_CYCLE, [REG_OP_TABLE, #OTOFFS_IRQH_CYC] - mov r0, #43 - sub r1, r1, REG_CYCLE - mul r0, r1, r0 - mov r0, r0, lsr #11 + FLUSH_TIMESTAMP r0 + @ get irqhook cycles + and r0, REG_CYCLE, #0xff00 + mov r0, r0, lsr #8 #ifndef DEBUG_ASM_6502 @ I have reviewed all MapIRQHook functions, they only seem to cause IRQs, not messing cycles or something str REG_P_REST, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x10)] @ might set irq - mov REG_P_REST, lr @ r8 + mov REG_P_REST, REG_OP_TABLE @ r8 @ if somebody modifies MapIRQHook without calling reset, we are doomed mov lr, pc ldr pc, [REG_OP_TABLE, #OTOFFS_IRQ_HOOK] - ldr REG_OP_TABLE, =cpu_exec_table @ got trashed because was in r12 - mov lr, REG_P_REST + mov REG_OP_TABLE, REG_P_REST @ got trashed because was in r12 ldr REG_P_REST, [REG_OP_TABLE, #(OTOFFS_NES_REGS + 0x10)] @ might set irq #else ldr r1, =mapirq_cyc_a str r0, [r1] mov r1, r0 #endif + + ldrb r0, [REG_PC], #1 + bic REG_CYCLE, REG_CYCLE, #0xff00 + tst REG_P_REST, #0xff<<8 + ldreq pc, [REG_OP_TABLE, r0, lsl #2] + + @ do some messing to find out which IRQ is pending.. + tst REG_P_REST, #P_REST_I_FLAG + @@ if I_FLAG=1, continue execution, don't trigger IRQ + bicne REG_P_REST, REG_P_REST, #FCEU_IQTEMP<<8 + ldrne pc, [REG_OP_TABLE, r0, lsl #2] + @@ I_FLAG=0 and REST is checked, we have a IRQ + b do_int + + +do_irq_hook_final: + ldr r1, =nes_registers + + @ get irqhook cycles + and r0, REG_CYCLE, #0xff00 + bic REG_CYCLE, REG_CYCLE, #0xff00 + mov r0, r0, lsr #8 + + stmia r1, {r4-r12} + + ldmfd r13!,{r4-r11,lr} + +#ifndef DEBUG_ASM_6502 + ldr pc, [REG_OP_TABLE, #OTOFFS_IRQ_HOOK] +#else + ldr r1, =mapirq_cyc_a + str r0, [r1] + mov r1, r0 bx lr +#endif @ vim:filetype=armasm