1 ; Z80 emulator with CP/M support. The Z80-specific instructions themselves actually aren't
2 ; implemented yet, making this more of an i8080 emulator.
4 ; Copyright (C) 2010 Sprite_tm
6 ; This program is free software: you can redistribute it and/or modify
7 ; it under the terms of the GNU General Public License as published by
8 ; the Free Software Foundation, either version 3 of the License, or
9 ; (at your option) any later version.
11 ; This program is distributed in the hope that it will be useful,
12 ; but WITHOUT ANY WARRANTY; without even the implied warranty of
13 ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 ; GNU General Public License for more details.
16 ; You should have received a copy of the GNU General Public License
17 ; along with this program. If not, see <http://www.gnu.org/licenses/>.
22 #elif defined atmega168
32 #ifndef DRAM_DQ_ORDER /* If this is set to 1, the portbits */
33 #define DRAM_DQ_ORDER 0 /* for DRAM D1 and WE are swapped. */
38 #define F_CPU 20000000 /* system clock in Hz; defaults to 20MHz */
41 #define BAUD 38400 /* console baud rate */
45 #define UBRR_VAL ((F_CPU+BAUD*8)/(BAUD*16)-1) /* clever rounding */
47 #define RXBUFSIZE 64 /* USART recieve buffer size. Must be power of 2 */
49 #define REFR_RATE 64000 /* dram refresh rate in cycles/s. */
50 /* Most drams need 1/15.6µs. */
51 #define REFR_PRE 8 /* timer prescale factor */
52 #define REFR_CS 0x02 /* timer clock select for 1/8 */
53 #define REFR_CNT F_CPU / REFR_RATE / REFR_PRE
56 #if defined __ATmega8__
57 .equ refr_vect = OC2addr
59 .equ refr_vect = OC2Aaddr
63 #define EM_Z80 0 /* we don't have any z80 instructions yet */
87 .equ RAM_AH_MASK = 0xE0 ; ram_a[7..5]
88 .equ PD_OUTPUT_MASK = 0xFE
102 .equ RAM_AL_MASK = 0x1F ; ram_a[4..0]
103 .equ PB_OUTPUT_MASK = 0x3F
106 #if DRAM_DQ_ORDER == 1
118 .equ RAM_DQ_MASK = (1<<ram_d3)|(1<<ram_d2)|(1<<ram_d1)|(1<<ram_d0)
119 .equ PC_OUTPUT_MASK = (1<<ram_cas)|(1<<ram_w)
122 ;Flag bits in z_flags
130 ;Register definitions
148 .def temp = R16 ;The temp register
149 .def temp2 = R17 ;Second temp register
164 ; This is the base z80 port address for clock access
165 #define TIMERPORT 0x40
166 #define TIMER_CTL TIMERPORT
167 #define TIMER_MSECS TIMERPORT+1
168 #define TIMER_SECS TIMER_MSECS+2
170 #define starttimercmd 1
171 #define quitTimerCmd 2
172 #define printTimerCmd 15
180 ;Sector buffer for 512 byte reads/writes from/to SD-card
188 rjmp start ; reset vector
190 rjmp refrint ; tim2cmpa
191 .org OC1Aaddr ; Timer/Counter1 Compare Match A
192 rjmp sysclockint ; 1ms system timer
194 rjmp rxint ; USART receive int.
198 .org INT_VECTORS_SIZE
201 ldi temp,low(RAMEND) ; top of memory
202 out SPL,temp ; init stack pointer
203 ldi temp,high(RAMEND) ; top of memory
204 out SPH,temp ; init stack pointer
208 #if defined __ATmega8__
212 ldi temp,(1<<WDCE) | (1<<WDE)
220 ldi temp,(1<<WDCE) | (1<<WDE)
227 ldi temp,PB_OUTPUT_MASK
229 ldi temp,PD_OUTPUT_MASK
231 ldi temp,PC_OUTPUT_MASK
243 ldi temp,0 ; reset receive buffer
249 #if defined __ATmega8__
250 ldi temp, (1<<TXEN) | (1<<RXEN) | (1<<RXCIE)
252 ldi temp, (1<<URSEL) | (1<<UCSZ1) | (1<<UCSZ0)
254 ldi temp, HIGH(UBRR_VAL)
256 ldi temp, LOW(UBRR_VAL)
259 ldi temp, (1<<TXEN0) | (1<<RXEN0) | (1<<RXCIE0)
261 ldi temp, (1<<UCSZ01) | (1<<UCSZ00)
263 ldi temp, HIGH(UBRR_VAL)
265 ldi temp, LOW(UBRR_VAL)
269 ;Init timer2. Refresh-call should happen every (8ms/512)=312 cycles.
272 ldi temp,REFR_CNT*2 ; 2 cycles per int
274 ldi temp,(1<<WGM21) | REFR_CS ;CTC, clk/REFR_PRE
279 ldi temp,REFR_CNT ;=312 cycles
283 ldi temp, REFR_CS ;clk/REFR_PRE
290 ; Init clock/timer system
292 ldi zl,low(timer_base)
293 ldi zh,high(timer_base)
301 ; Init timer 1 as 1 ms system clock tick.
304 ldi temp,high(F_CPU/1000)
306 ldi temp,low(F_CPU/1000)
308 ldi temp,(1<<WGM12) | (1<<CS10) ;CTC, clk/1
314 ldi temp,high(F_CPU/1000)
316 ldi temp,low(F_CPU/1000)
318 ldi temp,(1<<WGM12) | (1<<CS10) ;CTC, clk/1
337 brne bootwait1 ;2 (3*256 + 5) * 256 = 198K cycles
342 .db "CPM on an AVR, v1.0",13,0,0
346 .db "Initing mmc...",13,0
352 .db "Testing RAM...",13,0
400 ;Fill ram with cbs, which (for now) will trigger an invalid opcode error.
415 ;Load initial sector from MMC (512 bytes)
420 ;Save to Z80 RAM (only 128 bytes because that's retro)
422 ldi zh,high(sectbuff)
436 cpi zl,low(sectbuff+128)
438 cpi zh,high(sectbuff+128)
451 .db 13,"Ok, CPU is live!",13,0,0
480 ; *** Stage 1: Fetch next opcode
504 ; *** Stage 2: Decode it using the ins_table.
506 ldi zl,low(inst_table*2)
507 ldi zh,high(inst_table*2)
529 ; *** Stage 3: Fetch operand. Use the fetch jumptable for this.
536 ldi zl,low(fetchjumps*2)
537 ldi zh,high(fetchjumps*2)
561 ; *** Stage 4: Execute operation :) Use the op jumptable for this.
567 ldi zl,low(opjumps*2)
568 ldi zh,high(opjumps*2)
591 ; *** Stage 5: Store operand. Use the store jumptable for this.
599 ldi zl,low(storejumps*2)
600 ldi zh,high(storejumps*2)
632 ; ----------------Virtual peripherial interface ------
634 ;The hw is modelled to make writing a CPM BIOS easier.
636 ;0 - Con status. Returns 0xFF if the UART has a byte, 0 otherwise.
637 ;1 - Console input, aka UDR.
643 ;22 - Trigger - write 1 to read, 2 to write a sector using the above info.
644 ; This will automatically move track, sector and dma addr to the next sector.
646 ;Called with port in temp2. Should return value in temp.
653 cpi temp2,TIMER_MSECS
655 cpi temp2,TIMER_MSECS+6
663 ;Called with port in temp2 and value in temp.
682 cpi temp2,TIMER_MSECS+6
736 .db "Disk read: track ",0
754 ;First, convert track/sector to an LBA address (in 128byte blocks)
771 ;Now, see what has to be done.
779 ;Convert from 128-byte LBA blocks to 512-byte LBA blocks
784 ;Read 512-byte sector
788 ;Now, move the correct portion of the sector from AVR ram to Z80 ram
790 ldi zh,high(sectbuff)
818 brne dskDoItReadMemLoop
822 ;The write routines is a bit naive: it'll read the 512-byte sector the 128byte CPM-sector
823 ;resides in into memory, will overwrite the needed 128 byte with the Z80s memory buffer
824 ;and will then write it back to disk. In theory, this would mean that every 512 bytes
825 ;written will take 4 write cycles, while theoretically the writes could be deferred so we
826 ;would only have to do one write cycle.
831 .db "Disk write: track ",0
852 ;Convert from 128-byte LBA blocks to 512-byte LBA blocks
857 ;Read 512-byte sector
865 ;Copy the data from the Z80 DMA buffer in external memory to the right place in the
867 ;Now, move the correct portion of the sector from AVR ram to Z80 ram
869 ldi zh,high(sectbuff)
897 brne dskDoItWriteMemLoop
902 ;Convert from 128-byte LBA blocks to 512-byte LBA blocks
907 ;Write the sector back.
914 ; ----------------- MMC/SD routines ------------------
949 ;Wait till the mmc answers with the response in temp2, or till a timeout happens.
956 brne mmcWaitResploopEnd
969 .db ": Error: MMC resp timeout!",13,0
976 ;Init start: send 80 clocks with cs disabled
1001 ldi temp,0xff ;dummy
1003 ldi temp,0xff ;dummy
1017 ldi temp,0xff ;return byte
1027 ;Read OCR till card is ready
1033 ldi temp,0xff ;dummy
1052 breq mmcInitOcrLoopDone
1075 ;Call this with adrh:adrl = sector number
1076 ;16bit lba address means a max reach of 32M.
1083 ldi temp,0x51 ;cmd (read sector)
1098 ldi temp,0xff ;return byte
1109 ;Read sector to AVR RAM
1110 ldi zl,low(sectbuff)
1111 ldi zh,high(sectbuff)
1115 cpi zl,low(sectbuff+512)
1117 cpi zh,high(sectbuff+512)
1132 ;Call this with adrh:adrl = sector number
1133 ;16bit lba address means a max reach of 32M.
1141 ldi temp,0x58 ;cmd (write sector)
1156 ldi temp,0xff ;return byte
1167 ;Write sector from AVR RAM
1168 ldi zl,low(sectbuff)
1169 ldi zh,high(sectbuff)
1173 cpi zl,low(sectbuff+512)
1175 cpi zh,high(sectbuff+512)
1182 ;Status. Ignored for now.
1185 ;Wait till the mmc has written everything
1199 ;Set up wdt to time out after 1 sec.
1202 #if defined __ATmega8__
1205 ldi temp,(1<<WDCE) | (1<<WDE) | (110<<WDP0)
1210 ldi temp,(1<<WDCE) | (1<<WDE) | (110<<WDP0)
1217 ; ------------------ DRAM routines -------------
1221 #if DRAM_DQ_ORDER == 1
1222 #define CLASSIC_DRAM 0
1224 #define CLASSIC_DRAM 1 /* Change manualy, if you want new hw w/ old sw */
1228 #if DRAM_DQ_ORDER == 0
1229 #if CLASSIC_DRAM == 1
1230 #error "Old harware can not work with new software!"
1234 ; ****************************************************************************
1238 ; ********************** DRAM routines from Sprite_tm ************************
1240 ;Sends the address in zh:zl to the ram
1285 andi temp2,~RAM_DQ_MASK
1288 ori temp2,(1<<ram_d0)
1290 ori temp2,(1<<ram_d1)
1292 ori temp2,(1<<ram_d2)
1294 ori temp2,(1<<ram_d3)
1301 ;Loads the byte on address adrh:adrl into temp.
1324 rcall dram_getnibble
1339 rcall dram_getnibble
1347 ;Writes the byte in temp to adrh:adrl
1352 ori temp2,RAM_DQ_MASK
1355 rcall dram_sendnibble
1391 rcall dram_sendnibble
1405 andi temp,~RAM_DQ_MASK
1408 andi temp,~RAM_DQ_MASK
1412 #endif /* CLASSIC_DRAM == 1 */
1414 ; ****************************************************************************
1418 ; ***************************** New DRAM routines ****************************
1420 ; Defines how the dram nibbles are arganized.
1421 ; RAMORG == 0 : A7 == 0: low nibble, A7 == 1: high nibble (Original Sprite_tm design)
1422 ; RAMORG == 1 : A8 == 0: low nibble, A8 == 1: high nibble (faster)
1427 ;Sends the address in zh:zl to the ram
1431 andi temp,~RAM_AL_MASK
1433 ori temp,(1<<ram_a0)
1435 ori temp,(1<<ram_a1)
1437 ori temp,(1<<ram_a2)
1439 ori temp,(1<<ram_a3)
1441 ori temp,(1<<ram_a4)
1445 andi temp,~RAM_AH_MASK
1447 ori temp,(1<<ram_a5)
1449 ori temp,(1<<ram_a6)
1451 ori temp,(1<<ram_a7)
1453 ori temp,(1<<ram_a8)
1456 #else /* RAMORG == 1 */
1460 andi temp,~RAM_AL_MASK
1462 ori temp,(1<<ram_a0)
1464 ori temp,(1<<ram_a1)
1466 ori temp,(1<<ram_a2)
1468 ori temp,(1<<ram_a3)
1470 ori temp,(1<<ram_a4)
1474 andi temp,~RAM_AH_MASK
1476 ori temp,(1<<ram_a5)
1478 ori temp,(1<<ram_a6)
1480 ori temp,(1<<ram_a7)
1487 .macro DRAM_SENDNIBBLE
1489 andi temp2,~RAM_DQ_MASK
1490 andi temp,RAM_DQ_MASK
1496 ;Loads the byte on address adrh:adrl into temp.
1497 ;must not alter adrh:adrl
1566 ;Writes the byte in temp to adrh:adrl
1567 ;must not alter adrh:adrl
1572 in temp2,DDRC ;DRAM data ports as outputs
1573 ori temp2,RAM_DQ_MASK
1593 cbi PORTC,ram_w ;early write
1612 andi temp,~RAM_DQ_MASK
1615 andi temp,~RAM_DQ_MASK
1617 #else /* RAMORG == 1 */
1618 in temp2,DDRC ;DRAM data ports as outputs
1619 ori temp2,RAM_DQ_MASK
1630 cbi PORTC,ram_w ;early write
1647 andi temp,~RAM_DQ_MASK
1650 andi temp,~RAM_DQ_MASK
1656 #endif /* CLASSIC_DRAM == 0 */
1658 ; ****************************************************************************
1660 ; refresh interupt; exec 2 cbr cycles
1671 ; ****************************************************************************
1673 ; ------------- system timer 10ms ---------------
1681 ; don't change order here, clock put/get depends on it.
1682 cntms_out: ; register for ms
1684 utime_io: ; register for uptime.
1691 .equ timer_size = timer_top - timer_base
1693 .equ clkofs = cnt_1ms-cntms_out
1694 .equ timerofs = cnt_1ms-timer_ms
1710 ldi zl,high(1000) ;doesn't change flags
1744 subi temp2,TIMER_MSECS
1745 brcs clkget_end ;Port number in range?
1746 ldi zl,low(cntms_out)
1747 ldi zh,high(cntms_out)
1748 breq clkget_copy ;lowest byte requestet, latch clock
1750 brsh clkget_end ;Port number to high?
1775 subi temp2,TIMERPORT
1776 brcs clkput_end ;Port number in range?
1781 cpi temp,starttimercmd
1783 cpi temp,quitTimerCmd
1785 cpi temp,printTimerCmd
1799 ldi zl,low(cntms_out)
1800 ldi zh,high(cntms_out)
1801 breq clkput_copy ;lowest byte requestet, latch clock
1803 brsh clkput_end ;Port number to high?
1828 ldi zl,low(timer_ms)
1829 ldi zh,high(timer_ms)
1849 ldi zl,low(timer_ms)
1850 ldi zh,high(timer_ms)
1852 ; put ms on stack (16 bit)
1863 subi adrl,low(-1000)
1864 sbci adrh,high(-1000)
1876 ldd temp2,z+timerofs
1890 .db 13,"Timer running. Elapsed: ",0
1914 ldi zh,high(cnt_1ms)
1949 ; --------------- Debugging stuff ---------------
1951 ;Print a unsigned lonng value to the uart
1952 ; oph:opl:temp2:temp = value
1959 clr adrl ;adrl = stack level
1961 ultoa1: ldi yl, 32 ;adrh = oph:temp % 10
1962 clr adrh ;oph:temp /= 10
1974 cpi adrh, 10 ;adrh is a numeral digit '0'-'9'
1979 cp temp,yl ;Repeat until oph:temp gets zero
1985 ultoa6: pop temp ;Flush stacked digits
1996 ;Prints the lower nibble of temp in hex to the uart
2012 ;Prints temp in hex to the uart
2020 ;Prints the zero-terminated string following the call statement. WARNING: Destroys temp.
2051 ; --------------- AVR HW <-> Z80 periph stuff ------------------
2053 .equ memReadByte = dram_read
2054 .equ memWriteByte = dram_write
2056 ; --------------------------------------------------------------
2060 #define RXBUFMASK RXBUFSIZE-1
2074 ; Save received character in a circular buffer. Do nothing if buffer overflows.
2112 ;Fetches a char from the buffer to temp. If none available, waits till one is.
2115 lds temp,rxcount ; Number of characters in buffer
2135 ld temp,z ;don't forget to get the char
2142 ;Sends a char from temp to the uart.
2144 #if defined __ATmega8__
2160 ; ------------ Fetch phase stuff -----------------
2162 .equ FETCH_NOP = (0<<0)
2163 .equ FETCH_A = (1<<0)
2164 .equ FETCH_B = (2<<0)
2165 .equ FETCH_C = (3<<0)
2166 .equ FETCH_D = (4<<0)
2167 .equ FETCH_E = (5<<0)
2168 .equ FETCH_H = (6<<0)
2169 .equ FETCH_L = (7<<0)
2170 .equ FETCH_AF = (8<<0)
2171 .equ FETCH_BC = (9<<0)
2172 .equ FETCH_DE = (10<<0)
2173 .equ FETCH_HL = (11<<0)
2174 .equ FETCH_SP = (12<<0)
2175 .equ FETCH_MBC = (13<<0)
2176 .equ FETCH_MDE = (14<<0)
2177 .equ FETCH_MHL = (15<<0)
2178 .equ FETCH_MSP = (16<<0)
2179 .equ FETCH_DIR8 = (17<<0)
2180 .equ FETCH_DIR16= (18<<0)
2181 .equ FETCH_RST = (19<<0)
2184 ;Jump table for fetch routines. Make sure to keep this in sync with the .equs!
2332 ; ------------ Store phase stuff -----------------
2334 .equ STORE_NOP = (0<<5)
2335 .equ STORE_A = (1<<5)
2336 .equ STORE_B = (2<<5)
2337 .equ STORE_C = (3<<5)
2338 .equ STORE_D = (4<<5)
2339 .equ STORE_E = (5<<5)
2340 .equ STORE_H = (6<<5)
2341 .equ STORE_L = (7<<5)
2342 .equ STORE_AF = (8<<5)
2343 .equ STORE_BC = (9<<5)
2344 .equ STORE_DE = (10<<5)
2345 .equ STORE_HL = (11<<5)
2346 .equ STORE_SP = (12<<5)
2347 .equ STORE_PC = (13<<5)
2348 .equ STORE_MBC = (14<<5)
2349 .equ STORE_MDE = (15<<5)
2350 .equ STORE_MHL = (16<<5)
2351 .equ STORE_MSP = (17<<5)
2352 .equ STORE_RET = (18<<5)
2353 .equ STORE_CALL = (19<<5)
2354 .equ STORE_AM = (20<<5)
2356 ;Jump table for store routines. Make sure to keep this in sync with the .equs!
2502 ; ------------ Operation phase stuff -----------------
2505 .equ OP_NOP = (0<<10)
2506 .equ OP_INC = (1<<10)
2507 .equ OP_DEC = (2<<10)
2508 .equ OP_INC16 = (3<<10)
2509 .equ OP_DEC16 = (4<<10)
2510 .equ OP_RLC = (5<<10)
2511 .equ OP_RRC = (6<<10)
2512 .equ OP_RR = (7<<10)
2513 .equ OP_RL = (8<<10)
2514 .equ OP_ADDA = (9<<10)
2515 .equ OP_ADCA = (10<<10)
2516 .equ OP_SUBFA = (11<<10)
2517 .equ OP_SBCFA = (12<<10)
2518 .equ OP_ANDA = (13<<10)
2519 .equ OP_ORA = (14<<10)
2520 .equ OP_XORA = (15<<10)
2521 .equ OP_ADDHL = (16<<10)
2522 .equ OP_STHL = (17<<10) ;store HL in fetched address
2523 .equ OP_RMEM16 = (18<<10) ;read mem at fetched address
2524 .equ OP_RMEM8 = (19<<10) ;read mem at fetched address
2525 .equ OP_DA = (20<<10)
2526 .equ OP_SCF = (21<<10)
2527 .equ OP_CPL = (22<<10)
2528 .equ OP_CCF = (23<<10)
2529 .equ OP_POP16 = (24<<10)
2530 .equ OP_PUSH16 = (25<<10)
2531 .equ OP_IFNZ = (26<<10)
2532 .equ OP_IFZ = (27<<10)
2533 .equ OP_IFNC = (28<<10)
2534 .equ OP_IFC = (29<<10)
2535 .equ OP_IFPO = (30<<10)
2536 .equ OP_IFPE = (31<<10)
2537 .equ OP_IFP = (32<<10)
2538 .equ OP_IFM = (33<<10)
2539 .equ OP_OUTA = (34<<10)
2540 .equ OP_IN = (35<<10)
2541 .equ OP_EXHL = (36<<10)
2542 .equ OP_DI = (37<<10)
2543 .equ OP_EI = (38<<10)
2544 .equ OP_INV = (39<<10)
2589 ;How the flags are supposed to work:
2590 ;7 ZFL_S - Sign flag (=MSBit of result)
2591 ;6 ZFL_Z - Zero flag. Is 1 when the result is 0
2592 ;4 ZFL_H - Half-carry (carry from bit 3 to 4)
2593 ;2 ZFL_P - Parity/2-complement Overflow
2594 ;1 ZFL_N - Subtract - set if last op was a subtract
2597 ;I sure hope I got the mapping between flags and instructions correct...
2599 ;----------------------------------------------------------------
2603 ;| ZZZZZZZ 88888 000 |
2609 ;| ZZZZZZZ 88888 000 |
2611 ;| Z80 MICROPROCESSOR Instruction Set Summary |
2613 ;----------------------------------------------------------------
2614 ;----------------------------------------------------------------
2615 ;|Mnemonic |SZHPNC|Description |Notes |
2616 ;|----------+------+---------------------+----------------------|
2617 ;|ADC A,s |***V0*|Add with Carry |A=A+s+CY |
2618 ;|ADC HL,ss |**?V0*|Add with Carry |HL=HL+ss+CY |
2619 ;|ADD A,s |***V0*|Add |A=A+s |
2620 ;|ADD HL,ss |--?-0*|Add |HL=HL+ss |
2621 ;|ADD IX,pp |--?-0*|Add |IX=IX+pp |
2622 ;|ADD IY,rr |--?-0*|Add |IY=IY+rr |
2623 ;|AND s |**1P00|Logical AND |A=A&s |
2624 ;|BIT b,m |?*1?0-|Test Bit |m&{2^b} |
2625 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
2626 ;|CALL nn |------|Unconditional Call |-[SP]=PC,PC=nn |
2627 ;|CCF |--?-0*|Complement Carry Flag|CY=~CY |
2628 ;|CP s |***V1*|Compare |A-s |
2629 ;|CPD |****1-|Compare and Decrement|A-[HL],HL=HL-1,BC=BC-1|
2630 ;|CPDR |****1-|Compare, Dec., Repeat|CPD till A=[HL]or BC=0|
2631 ;|CPI |****1-|Compare and Increment|A-[HL],HL=HL+1,BC=BC-1|
2632 ;|CPIR |****1-|Compare, Inc., Repeat|CPI till A=[HL]or BC=0|
2633 ;|CPL |--1-1-|Complement |A=~A |
2634 ;|DAA |***P-*|Decimal Adjust Acc. |A=BCD format |
2635 ;|DEC s |***V1-|Decrement |s=s-1 |
2636 ;|DEC xx |------|Decrement |xx=xx-1 |
2637 ;|DEC ss |------|Decrement |ss=ss-1 |
2638 ;|DI |------|Disable Interrupts | |
2639 ;|DJNZ e |------|Dec., Jump Non-Zero |B=B-1 till B=0 |
2640 ;|EI |------|Enable Interrupts | |
2641 ;|EX [SP],HL|------|Exchange |[SP]<->HL |
2642 ;|EX [SP],xx|------|Exchange |[SP]<->xx |
2643 ;|EX AF,AF' |------|Exchange |AF<->AF' |
2644 ;|EX DE,HL |------|Exchange |DE<->HL |
2645 ;|EXX |------|Exchange |qq<->qq' (except AF)|
2646 ;|HALT |------|Halt | |
2647 ;|IM n |------|Interrupt Mode | (n=0,1,2)|
2648 ;|IN A,[n] |------|Input |A=[n] |
2649 ;|IN r,[C] |***P0-|Input |r=[C] |
2650 ;|INC r |***V0-|Increment |r=r+1 |
2651 ;|INC [HL] |***V0-|Increment |[HL]=[HL]+1 |
2652 ;|INC xx |------|Increment |xx=xx+1 |
2653 ;|INC [xx+d]|***V0-|Increment |[xx+d]=[xx+d]+1 |
2654 ;|INC ss |------|Increment |ss=ss+1 |
2655 ;|IND |?*??1-|Input and Decrement |[HL]=[C],HL=HL-1,B=B-1|
2656 ;|INDR |?1??1-|Input, Dec., Repeat |IND till B=0 |
2657 ;|INI |?*??1-|Input and Increment |[HL]=[C],HL=HL+1,B=B-1|
2658 ;|INIR |?1??1-|Input, Inc., Repeat |INI till B=0 |
2659 ;|JP [HL] |------|Unconditional Jump |PC=[HL] |
2660 ;|JP [xx] |------|Unconditional Jump |PC=[xx] |
2661 ;|JP nn |------|Unconditional Jump |PC=nn |
2662 ;|JP cc,nn |------|Conditional Jump |If cc JP |
2663 ;|JR e |------|Unconditional Jump |PC=PC+e |
2664 ;|JR cc,e |------|Conditional Jump |If cc JR(cc=C,NC,NZ,Z)|
2665 ;|LD dst,src|------|Load |dst=src |
2666 ;|LD A,i |**0*0-|Load |A=i (i=I,R)|
2667 ;|LDD |--0*0-|Load and Decrement |[DE]=[HL],HL=HL-1,# |
2668 ;|LDDR |--000-|Load, Dec., Repeat |LDD till BC=0 |
2669 ;|LDI |--0*0-|Load and Increment |[DE]=[HL],HL=HL+1,# |
2670 ;|LDIR |--000-|Load, Inc., Repeat |LDI till BC=0 |
2671 ;|NEG |***V1*|Negate |A=-A |
2672 ;|NOP |------|No Operation | |
2673 ;|OR s |**0P00|Logical inclusive OR |A=Avs |
2674 ;|OTDR |?1??1-|Output, Dec., Repeat |OUTD till B=0 |
2675 ;|OTIR |?1??1-|Output, Inc., Repeat |OUTI till B=0 |
2676 ;|OUT [C],r |------|Output |[C]=r |
2677 ;|OUT [n],A |------|Output |[n]=A |
2678 ;|OUTD |?*??1-|Output and Decrement |[C]=[HL],HL=HL-1,B=B-1|
2679 ;|OUTI |?*??1-|Output and Increment |[C]=[HL],HL=HL+1,B=B-1|
2680 ;|POP xx |------|Pop |xx=[SP]+ |
2681 ;|POP qq |------|Pop |qq=[SP]+ |
2682 ;|PUSH xx |------|Push |-[SP]=xx |
2683 ;|PUSH qq |------|Push |-[SP]=qq |
2684 ;|RES b,m |------|Reset bit |m=m&{~2^b} |
2685 ;|RET |------|Return |PC=[SP]+ |
2686 ;|RET cc |------|Conditional Return |If cc RET |
2687 ;|RETI |------|Return from Interrupt|PC=[SP]+ |
2688 ;|RETN |------|Return from NMI |PC=[SP]+ |
2689 ;|RL m |**0P0*|Rotate Left |m={CY,m}<- |
2690 ;|RLA |--0-0*|Rotate Left Acc. |A={CY,A}<- |
2691 ;|RLC m |**0P0*|Rotate Left Circular |m=m<- |
2692 ;|RLCA |--0-0*|Rotate Left Circular |A=A<- |
2693 ;|RLD |**0P0-|Rotate Left 4 bits |{A,[HL]}={A,[HL]}<- ##|
2694 ;|RR m |**0P0*|Rotate Right |m=->{CY,m} |
2695 ;|RRA |--0-0*|Rotate Right Acc. |A=->{CY,A} |
2696 ;|RRC m |**0P0*|Rotate Right Circular|m=->m |
2697 ;|RRCA |--0-0*|Rotate Right Circular|A=->A |
2698 ;|RRD |**0P0-|Rotate Right 4 bits |{A,[HL]}=->{A,[HL]} ##|
2699 ;|RST p |------|Restart | (p=0H,8H,10H,...,38H)|
2700 ;|SBC A,s |***V1*|Subtract with Carry |A=A-s-CY |
2701 ;|SBC HL,ss |**?V1*|Subtract with Carry |HL=HL-ss-CY |
2702 ;|SCF |--0-01|Set Carry Flag |CY=1 |
2703 ;|SET b,m |------|Set bit |m=mv{2^b} |
2704 ;|SLA m |**0P0*|Shift Left Arithmetic|m=m*2 |
2705 ;|SRA m |**0P0*|Shift Right Arith. |m=m/2 |
2706 ;|SRL m |**0P0*|Shift Right Logical |m=->{0,m,CY} |
2707 ;|SUB s |***V1*|Subtract |A=A-s |
2708 ;|XOR s |**0P00|Logical Exclusive OR |A=Axs |
2709 ;|----------+------+--------------------------------------------|
2720 ;------------------------------------------------;
2721 ; Move single bit between two registers
2723 ; bmov dstreg,dstbit,srcreg.srcbit
2731 ;------------------------------------------------;
2732 ; Load table value from flash indexed by source reg.
2734 ; ldpmx dstreg,tablebase,indexreg
2736 ; (6 words, 8 cycles)
2747 .macro do_z80_flags_HP
2749 bmov z_flags, ZFL_P, temp, AVR_V
2750 bmov z_flags, ZFL_H, temp, AVR_H
2754 .macro do_z80_flags_set_N
2756 ori z_flags, (1<<ZFL_N) ; Negation auf 1
2760 .macro do_z80_flags_set_HN
2762 ori z_flags,(1<<ZFL_N)|(1<<ZFL_H)
2766 .macro do_z80_flags_clear_N
2768 andi z_flags,~(1<<ZFL_N)
2772 .macro do_z80_flags_op_rotate
2773 ; must not change avr carry flag!
2775 andi z_flags, ~( (1<<ZFL_H) | (1<<ZFL_N) | (1<<ZFL_C) )
2777 andi z_flags, ~( (1<<ZFL_C) )
2781 .macro do_z80_flags_op_and
2783 ori z_flags,(1<<ZFL_H)
2785 ori z_flags,(1<<ZFL_H)
2789 .macro do_z80_flags_op_or
2798 ;----------------------------------------------------------------
2799 ;|Mnemonic |SZHPNC|Description |Notes |
2800 ;----------------------------------------------------------------
2801 ;|INC r |***V0-|Increment |r=r+1 |
2802 ;|INC [HL] |***V0-|Increment |[HL]=[HL]+1 |
2803 ;|INC [xx+d]|***V0-|Increment |[xx+d]=[xx+d]+1 |
2804 ;|----------|SZHP C|---------- 8080 ----------------------------|
2805 ;|INC r |**-P0-|Increment |r=r+1 |
2806 ;|INC [HL] |**-P0-|Increment |[HL]=[HL]+1 |
2813 andi z_flags,(1<<ZFL_H)|(1<<ZFL_C) ; preserve C-, and H-flag
2814 ldpmx temp2, sz53p_tab, opl
2819 ;----------------------------------------------------------------
2820 ;|Mnemonic |SZHPNC|Description |Notes |
2821 ;----------------------------------------------------------------
2822 ;|DEC r |***V1-|Decrement |s=s-1 |
2823 ;|INC [HL] |***V0-|Increment |[HL]=[HL]+1 |
2824 ;|INC [xx+d]|***V0-|Increment |[xx+d]=[xx+d]+1 |
2825 ;|----------|SZHP C|---------- 8080 ----------------------------|
2826 ;|DEC r |**-P -|Increment |r=r+1 |
2827 ;|DEC [HL] |**-P -|Increment |[HL]=[HL]+1 |
2833 andi z_flags,(1<<ZFL_H)|(1<<ZFL_C) ; preserve C-, and H-flag
2834 ldpmx temp2, sz53p_tab, opl
2841 ;----------------------------------------------------------------
2842 ;|Mnemonic |SZHPNC|Description |Notes |
2843 ;----------------------------------------------------------------
2844 ;|INC xx |------|Increment |xx=xx+1 |
2845 ;|INC ss |------|Increment |ss=ss+1 |
2855 ;----------------------------------------------------------------
2856 ;|Mnemonic |SZHPNC|Description |Notes |
2857 ;----------------------------------------------------------------
2858 ;|DEC xx |------|Decrement |xx=xx-1 |
2859 ;|DEC ss |------|Decrement |ss=ss-1 |
2867 ;----------------------------------------------------------------
2868 ;|Mnemonic |SZHPNC|Description |Notes |
2869 ;----------------------------------------------------------------
2870 ;|RLCA |--0-0*|Rotate Left Circular |A=A<- |
2871 ;|----------|SZHP C|---------- 8080 ----------------------------|
2872 ;|RLCA |---- *|Rotate Left Circular |A=A<- |
2876 ;Rotate Left Cyclical. All bits move 1 to the
2877 ;left, the msb becomes c and lsb.
2878 do_z80_flags_op_rotate
2882 ori z_flags, (1<<ZFL_C)
2886 ;----------------------------------------------------------------
2887 ;|Mnemonic |SZHPNC|Description |Notes |
2888 ;----------------------------------------------------------------
2889 ;|RRCA |--0-0*|Rotate Right Circular|A=->A |
2890 ;|----------|SZHP C|---------- 8080 ----------------------------|
2891 ;|RRCA |---- *|Rotate Right Circular|A=->A |
2895 ;Rotate Right Cyclical. All bits move 1 to the
2896 ;right, the lsb becomes c and msb.
2897 do_z80_flags_op_rotate
2901 ori z_flags, (1<<ZFL_C)
2905 ;----------------------------------------------------------------
2906 ;|Mnemonic |SZHPNC|Description |Notes |
2907 ;----------------------------------------------------------------
2908 ;|RRA |--0-0*|Rotate Right Acc. |A=->{CY,A} |
2909 ;|----------|SZHP C|---------- 8080 ----------------------------|
2910 ;|RRA |---- *|Rotate Right Acc. |A=->{CY,A} |
2914 ;Rotate Right. All bits move 1 to the right, the lsb
2915 ;becomes c, c becomes msb.
2916 clc ; get z80 carry to avr carry
2919 do_z80_flags_op_rotate ; (clear ZFL_C, doesn't change AVR_C)
2920 bmov z_flags,ZFL_C, opl,0 ; Bit 0 --> CY
2924 ;----------------------------------------------------------------
2925 ;|Mnemonic |SZHPNC|Description |Notes |
2926 ;----------------------------------------------------------------
2927 ;|RLA |--0-0*|Rotate Left Acc. |A={CY,A}<- |
2928 ;|----------|SZHP C|---------- 8080 ----------------------------|
2929 ;|RLA |---- *|Rotate Left Acc. |A={CY,A}<- |
2933 ;Rotate Left. All bits move 1 to the left, the msb
2934 ;becomes c, c becomes lsb.
2938 do_z80_flags_op_rotate ; (clear ZFL_C, doesn't change AVR_C)
2939 bmov z_flags,ZFL_C, opl,7 ; Bit 7 --> CY
2943 ;----------------------------------------------------------------
2944 ;|Mnemonic |SZHPNC|Description |Notes |
2945 ;----------------------------------------------------------------
2946 ;|ADD A,s |***V0*|Add |A=A+s |
2947 ;|----------|SZHP C|---------- 8080 ----------------------------|
2948 ;|ADD A,s |***P *|Add |A=A+s |
2954 ldpmx z_flags,sz53p_tab,opl ;S,Z,P flag
2955 bmov z_flags,ZFL_C, temp,AVR_C
2959 ;----------------------------------------------------------------
2960 ;|Mnemonic |SZHPNC|Description |Notes |
2961 ;----------------------------------------------------------------
2962 ;|ADC A,s |***V0*|Add with Carry |A=A+s+CY |
2963 ;|----------|SZHP C|---------- 8080 ----------------------------|
2964 ;|ADC A,s |***P *|Add with Carry |A=A+s+CY |
2973 ldpmx z_flags,sz53p_tab,opl ;S,Z,P
2974 bmov z_flags,ZFL_C, temp,AVR_C
2978 ;----------------------------------------------------------------
2979 ;|Mnemonic |SZHPNC|Description |Notes |
2980 ;----------------------------------------------------------------
2981 ;|SUB s |***V1*|Subtract |A=A-s |
2982 ;|CP s |***V1*|Compare |A-s |
2983 ;|----------|SZHP C|---------- 8080 ----------------------------|
2984 ;|SUB s |***P *|Subtract |A=A-s |
2985 ;|CP s |***P *|Compare |A-s |
2993 ldpmx z_flags,sz53p_tab,opl ;S,Z,P
2994 bmov z_flags,ZFL_C, temp,AVR_C
2999 ;----------------------------------------------------------------
3000 ;|Mnemonic |SZHPNC|Description |Notes |
3001 ;----------------------------------------------------------------
3002 ;|SBC A,s |***V1*|Subtract with Carry |A=A-s-CY |
3003 ;|----------|SZHP C|---------- 8080 ----------------------------|
3004 ;|SBC A,s |***P *|Subtract with Carry |A=A-s-CY |
3015 ldpmx z_flags,sz53p_tab,opl ;S,Z,P
3016 bmov z_flags,ZFL_C, temp,AVR_C
3021 ;----------------------------------------------------------------
3022 ;|Mnemonic |SZHPNC|Description |Notes |
3023 ;----------------------------------------------------------------
3024 ;|AND s |**1P00|Logical AND |A=A&s |
3025 ;|----------|SZHP C|---------- 8080 ----------------------------|
3026 ;|AND s |**-P 0|Logical AND |A=A&s |
3031 ldpmx z_flags,sz53p_tab,opl ;S,Z,P,N,C
3036 ;----------------------------------------------------------------
3037 ;|Mnemonic |SZHPNC|Description |Notes |
3038 ;----------------------------------------------------------------
3039 ;|OR s |**0P00|Logical inclusive OR |A=Avs |
3040 ;|----------|SZHP C|---------- 8080 ----------------------------|
3041 ;|OR s |**-P00|Logical inclusive OR |A=Avs |
3046 ldpmx z_flags,sz53p_tab,opl ;S,Z,H,P,N,C
3050 ;----------------------------------------------------------------
3051 ;|Mnemonic |SZHPNC|Description |Notes |
3052 ;----------------------------------------------------------------
3053 ;|XOR s |**0P00|Logical Exclusive OR |A=Axs |
3054 ;|----------|SZHP C|---------- 8080 ----------------------------|
3055 ;|XOR s |**-P 0|Logical Exclusive OR |A=Axs |
3060 ldpmx z_flags,sz53p_tab,opl ;S,Z,H,P,N,C
3064 ;----------------------------------------------------------------
3065 ;|Mnemonic |SZHPNC|Description |Notes |
3066 ;----------------------------------------------------------------
3067 ;|ADD HL,ss |--?-0*|Add |HL=HL+ss |
3068 ;|----------|SZHP C|---------- 8080 ----------------------------|
3069 ;|ADD HL,ss |---- *|Add |HL=HL+ss |
3076 bmov z_flags,ZFL_H, temp,AVR_H
3077 bmov z_flags,ZFL_C, temp,AVR_C
3078 do_z80_flags_clear_N
3081 ;----------------------------------------------------------------
3082 ;|Mnemonic |SZHPNC|Description |Notes |
3083 ;----------------------------------------------------------------
3084 ;|LD dst,src|------|Load |dst=src |
3087 do_op_sthl: ;store hl to mem loc in opl:h
3104 ;----------------------------------------------------------------
3105 ;|Mnemonic |SZHPNC|Description |Notes |
3106 ;----------------------------------------------------------------
3107 ;|LD dst,src|------|Load |dst=src |
3123 ;----------------------------------------------------------------
3124 ;|Mnemonic |SZHPNC|Description |Notes |
3125 ;----------------------------------------------------------------
3126 ;|LD dst,src|------|Load |dst=src |
3136 ;----------------------------------------------------------------
3137 ;|Mnemonic |SZHPNC|Description |Notes |
3138 ;----------------------------------------------------------------
3139 ;|DAA |***P-*|Decimal Adjust Acc. | |
3140 ;|----------|SZHP C|---------- 8080 ----------------------------|
3144 ; Description (http://www.z80.info/z80syntx.htm#DAA):
3145 ; This instruction conditionally adjusts the accumulator for BCD addition
3146 ; and subtraction operations. For addition (ADD, ADC, INC) or subtraction
3147 ; (SUB, SBC, DEC, NEC), the following table indicates the operation performed:
3149 ; -------------------------------------------------------------------------------
3150 ; | | C Flag | HEX value in | H Flag | HEX value in | Number | C flag|
3151 ; | Operation| Before | upper digit | Before | lower digit | added | After |
3152 ; | | DAA | (bit 7-4) | DAA | (bit 3-0) | to byte | DAA |
3153 ; |-----------------------------------------------------------------------------|
3154 ; | | 0 | 0-9 | 0 | 0-9 | 00 | 0 |
3155 ; | ADD | 0 | 0-8 | 0 | A-F | 06 | 0 |
3156 ; | | 0 | 0-9 | 1 | 0-3 | 06 | 0 |
3157 ; | ADC | 0 | A-F | 0 | 0-9 | 60 | 1 |
3158 ; | | 0 | 9-F | 0 | A-F | 66 | 1 |
3159 ; | INC | 0 | A-F | 1 | 0-3 | 66 | 1 |
3160 ; | | 1 | 0-2 | 0 | 0-9 | 60 | 1 |
3161 ; | | 1 | 0-2 | 0 | A-F | 66 | 1 |
3162 ; | | 1 | 0-3 | 1 | 0-3 | 66 | 1 |
3163 ; |-----------------------------------------------------------------------------|
3164 ; | SUB | 0 | 0-9 | 0 | 0-9 | 00 | 0 |
3165 ; | SBC | 0 | 0-8 | 1 | 6-F | FA | 0 |
3166 ; | DEC | 1 | 7-F | 0 | 0-9 | A0 | 1 |
3167 ; | NEG | 1 | 6-F | 1 | 6-F | 9A | 1 |
3168 ; |-----------------------------------------------------------------------------|
3171 ; C: See instruction.
3173 ; P/V: Set if Acc. is even parity after operation, reset otherwise.
3174 ; H: See instruction.
3175 ; Z: Set if Acc. is Zero after operation, reset otherwise.
3176 ; S: Set if most significant bit of Acc. is 1 after operation, reset otherwise.
3182 ldi oph,0 ; what to add
3183 sbrc z_flags,ZFL_H ; if H-Flag
3186 andi temp,0x0f ; ... or lower digit > 9
3192 sbrc z_flags,(1<<ZFL_C)
3201 ori z_flags,(1<<ZFL_C); set C
3203 sbrs z_flags,ZFL_N ; if sub-op
3204 rjmp op_da_add ; then
3207 op_da_add: ; else add-op
3220 ori z_flags,(1<<ZFL_C)
3221 andi z_flags,(1<<ZFL_N)|(1<<ZFL_C) ; preserve C,N
3222 ldpmx temp2, sz53p_tab, opl ; get S,Z,P
3224 bmov z_flags,ZFL_H, temp,AVR_H ; H (?)
3229 sbrc z_flags,ZFL_N ; if add-op
3230 rjmp do_op_da_sub ; then
3234 cpi temp,0x0a ; if lower digit > 9
3236 ori temp2,0x06 ; add 6 to lower digit
3238 sbrc z_flags,ZFL_H ; ... or H-Flag
3248 do_op_da_c: ; else sub-op
3249 sbrc z_flags,ZFL_C ;
3251 andi z_flags, ~( (1<<ZFL_S) | (1<<ZFL_Z) | (1<<ZFL_H) )
3254 bst temp,AVR_Z ;Z-Flag
3256 bst temp,AVR_N ;S-Flag
3258 sbrc temp2,5 ;C-Flag, set if 0x06 added
3259 ori z_flags,(1<<ZFL_C) ;
3263 do_op_da_sub: ;TODO:
3268 ;----------------------------------------------------------------
3269 ;|Mnemonic |SZHPNC|Description |Notes |
3270 ;----------------------------------------------------------------
3271 ;|SCF |--0-01|Set Carry Flag |CY=1 |
3272 ;|----------|SZHP C|---------- 8080 ----------------------------|
3276 andi z_flags,~((1<<ZFL_H)|(1<<ZFL_N))
3277 ori z_flags,(1<<ZFL_C)
3280 ;----------------------------------------------------------------
3281 ;|Mnemonic |SZHPNC|Description |Notes |
3282 ;----------------------------------------------------------------
3283 ;|CCF |--?-0*|Complement Carry Flag|CY=~CY |
3284 ;|----------|SZHP C|---------- 8080 ----------------------------|
3285 ;|SCF |---- 1|Set Carry Flag |CY=1 |
3289 do_z80_flags_clear_N
3294 ;----------------------------------------------------------------
3295 ;|Mnemonic |SZHPNC|Description |Notes |
3296 ;----------------------------------------------------------------
3297 ;|CPL |--1-1-|Complement |A=~A |
3298 ;|----------|SZHP C|---------- 8080 ----------------------------|
3299 ;|CPL |---- -|Complement |A=~A |
3308 ;----------------------------------------------------------------
3309 ;|Mnemonic |SZHPNC|Description |Notes |
3310 ;----------------------------------------------------------------
3311 ;|PUSH xx |------|Push |-[SP]=xx |
3312 ;|PUSH qq |------|Push |-[SP]=qq |
3362 .db ", SP is now ",0
3373 ;----------------------------------------------------------------
3374 ;|Mnemonic |SZHPNC|Description |Notes |
3375 ;----------------------------------------------------------------
3376 ;|POP xx |------|Pop |xx=[SP]+ |
3377 ;|POP qq |------|Pop |qq=[SP]+ |
3403 .db "Stack pop: val ",0
3419 ;----------------------------------------------------------------
3420 ;|Mnemonic |SZHPNC|Description |Notes |
3421 ;----------------------------------------------------------------
3422 ;|EX [SP],HL|------|Exchange |[SP]<->HL |
3423 ;|EX DE,HL |------|Exchange |DE<->HL |
3435 ;----------------------------------------------------------------
3436 ;|Mnemonic |SZHPNC|Description |Notes |
3437 ;----------------------------------------------------------------
3439 ; TODO: Implement IFF1, IFF2
3443 ;----------------------------------------------------------------
3444 ;|Mnemonic |SZHPNC|Description |Notes |
3445 ;----------------------------------------------------------------
3447 ; TODO: Implement IFF1, IFF2
3451 ;----------------------------------------------------------------
3452 ;|Mnemonic |SZHPNC|Description |Notes |
3453 ;----------------------------------------------------------------
3454 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3455 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3456 ;|RET cc |------|Conditional Return |If cc RET |
3466 ;----------------------------------------------------------------
3467 ;|Mnemonic |SZHPNC|Description |Notes |
3468 ;----------------------------------------------------------------
3469 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3470 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3471 ;|RET cc |------|Conditional Return |If cc RET |
3481 ;----------------------------------------------------------------
3482 ;|Mnemonic |SZHPNC|Description |Notes |
3483 ;----------------------------------------------------------------
3484 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3485 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3486 ;|RET cc |------|Conditional Return |If cc RET |
3496 ;----------------------------------------------------------------
3497 ;|Mnemonic |SZHPNC|Description |Notes |
3498 ;----------------------------------------------------------------
3499 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3500 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3501 ;|RET cc |------|Conditional Return |If cc RET |
3511 ;----------------------------------------------------------------
3512 ;|Mnemonic |SZHPNC|Description |Notes |
3513 ;----------------------------------------------------------------
3514 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3515 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3516 ;|RET cc |------|Conditional Return |If cc RET |
3526 ;----------------------------------------------------------------
3527 ;|Mnemonic |SZHPNC|Description |Notes |
3528 ;----------------------------------------------------------------
3529 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3530 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3531 ;|RET cc |------|Conditional Return |If cc RET |
3541 ;----------------------------------------------------------------
3542 ;|Mnemonic |SZHPNC|Description |Notes |
3543 ;----------------------------------------------------------------
3544 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3545 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3546 ;|RET cc |------|Conditional Return |If cc RET |
3549 do_op_ifp: ;sign positive, aka s=0
3556 ;----------------------------------------------------------------
3557 ;|Mnemonic |SZHPNC|Description |Notes |
3558 ;----------------------------------------------------------------
3559 ;|CALL cc,nn|------|Conditional Call |If cc CALL |
3560 ;|JP cc,nn |------|Conditional Jump |If cc JP |
3561 ;|RET cc |------|Conditional Return |If cc RET |
3564 do_op_ifm: ;sign negative, aka s=1
3571 ;----------------------------------------------------------------
3572 ;|Mnemonic |SZHPNC|Description |Notes |
3573 ;----------------------------------------------------------------
3574 ;|OUT [n],A |------|Output |[n]=A |
3577 ;Interface with peripherials goes here :)
3578 do_op_outa: ; out (opl),a
3581 .db 13,"Port write: ",0
3596 ;----------------------------------------------------------------
3597 ;|Mnemonic |SZHPNC|Description |Notes |
3598 ;----------------------------------------------------------------
3599 ;|IN A,[n] |------|Input |A=[n] |
3602 do_op_in: ; in a,(opl)
3605 .db 13,"Port read: (",0
3623 ;----------------------------------------------------------------
3648 ;----------------------------------------------------------------
3651 .db "Invalid opcode @ PC=",0,0
3657 ;----------------------------------------------------------------
3661 ;----------------------------------------------------------------
3662 ; Lookup table, stolen from z80ex, Z80 emulation library.
3663 ; http://z80ex.sourceforge.net/
3665 ; The S, Z, 5 and 3 bits and the parity of the lookup value
3667 .db 0x44,0x00,0x00,0x04,0x00,0x04,0x04,0x00
3668 .db 0x08,0x0c,0x0c,0x08,0x0c,0x08,0x08,0x0c
3669 .db 0x00,0x04,0x04,0x00,0x04,0x00,0x00,0x04
3670 .db 0x0c,0x08,0x08,0x0c,0x08,0x0c,0x0c,0x08
3671 .db 0x20,0x24,0x24,0x20,0x24,0x20,0x20,0x24
3672 .db 0x2c,0x28,0x28,0x2c,0x28,0x2c,0x2c,0x28
3673 .db 0x24,0x20,0x20,0x24,0x20,0x24,0x24,0x20
3674 .db 0x28,0x2c,0x2c,0x28,0x2c,0x28,0x28,0x2c
3675 .db 0x00,0x04,0x04,0x00,0x04,0x00,0x00,0x04
3676 .db 0x0c,0x08,0x08,0x0c,0x08,0x0c,0x0c,0x08
3677 .db 0x04,0x00,0x00,0x04,0x00,0x04,0x04,0x00
3678 .db 0x08,0x0c,0x0c,0x08,0x0c,0x08,0x08,0x0c
3679 .db 0x24,0x20,0x20,0x24,0x20,0x24,0x24,0x20
3680 .db 0x28,0x2c,0x2c,0x28,0x2c,0x28,0x28,0x2c
3681 .db 0x20,0x24,0x24,0x20,0x24,0x20,0x20,0x24
3682 .db 0x2c,0x28,0x28,0x2c,0x28,0x2c,0x2c,0x28
3683 .db 0x80,0x84,0x84,0x80,0x84,0x80,0x80,0x84
3684 .db 0x8c,0x88,0x88,0x8c,0x88,0x8c,0x8c,0x88
3685 .db 0x84,0x80,0x80,0x84,0x80,0x84,0x84,0x80
3686 .db 0x88,0x8c,0x8c,0x88,0x8c,0x88,0x88,0x8c
3687 .db 0xa4,0xa0,0xa0,0xa4,0xa0,0xa4,0xa4,0xa0
3688 .db 0xa8,0xac,0xac,0xa8,0xac,0xa8,0xa8,0xac
3689 .db 0xa0,0xa4,0xa4,0xa0,0xa4,0xa0,0xa0,0xa4
3690 .db 0xac,0xa8,0xa8,0xac,0xa8,0xac,0xac,0xa8
3691 .db 0x84,0x80,0x80,0x84,0x80,0x84,0x84,0x80
3692 .db 0x88,0x8c,0x8c,0x88,0x8c,0x88,0x88,0x8c
3693 .db 0x80,0x84,0x84,0x80,0x84,0x80,0x80,0x84
3694 .db 0x8c,0x88,0x88,0x8c,0x88,0x8c,0x8c,0x88
3695 .db 0xa0,0xa4,0xa4,0xa0,0xa4,0xa0,0xa0,0xa4
3696 .db 0xac,0xa8,0xa8,0xac,0xa8,0xac,0xac,0xa8
3697 .db 0xa4,0xa0,0xa0,0xa4,0xa0,0xa4,0xa4,0xa0
3698 .db 0xa8,0xac,0xac,0xa8,0xac,0xa8,0xa8,0xac
3701 ; ----------------------- Opcode decoding -------------------------
3703 ; Lookup table for Z80 opcodes. Translates the first byte of the instruction word into three
3704 ; operations: fetch, do something, store.
3705 ; The table is made of 256 words. These 16-bit words consist of
3706 ; the fetch operation (bit 0-4), the processing operation (bit 10-16) and the store
3707 ; operation (bit 5-9).
3710 .dw (FETCH_NOP | OP_NOP | STORE_NOP) ; 00 NOP
3711 .dw (FETCH_DIR16| OP_NOP | STORE_BC ) ; 01 nn nn LD BC,nn
3712 .dw (FETCH_A | OP_NOP | STORE_MBC ) ; 02 LD (BC),A
3713 .dw (FETCH_BC | OP_INC16 | STORE_BC ) ; 03 INC BC
3714 .dw (FETCH_B | OP_INC | STORE_B ) ; 04 INC B
3715 .dw (FETCH_B | OP_DEC | STORE_B ) ; 05 DEC B
3716 .dw (FETCH_DIR8 | OP_NOP | STORE_B ) ; 06 nn LD B,n
3717 .dw (FETCH_A | OP_RLC | STORE_A ) ; 07 RLCA
3718 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 08 EX AF,AF' (Z80)
3719 .dw (FETCH_BC | OP_ADDHL | STORE_HL ) ; 09 ADD HL,BC
3720 .dw (FETCH_MBC | OP_NOP | STORE_A ) ; 0A LD A,(BC)
3721 .dw (FETCH_BC | OP_DEC16 | STORE_BC ) ; 0B DEC BC
3722 .dw (FETCH_C | OP_INC | STORE_C ) ; 0C INC C
3723 .dw (FETCH_C | OP_DEC | STORE_C ) ; 0D DEC C
3724 .dw (FETCH_DIR8 | OP_NOP | STORE_C ) ; 0E nn LD C,n
3725 .dw (FETCH_A | OP_RRC | STORE_A ) ; 0F RRCA
3726 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 10 oo DJNZ o (Z80)
3727 .dw (FETCH_DIR16| OP_NOP | STORE_DE ) ; 11 nn nn LD DE,nn
3728 .dw (FETCH_A | OP_NOP | STORE_MDE) ; 12 LD (DE),A
3729 .dw (FETCH_DE | OP_INC16 | STORE_DE ) ; 13 INC DE
3730 .dw (FETCH_D | OP_INC | STORE_D ) ; 14 INC D
3731 .dw (FETCH_D | OP_DEC | STORE_D ) ; 15 DEC D
3732 .dw (FETCH_DIR8 | OP_NOP | STORE_D ) ; 16 nn LD D,n
3733 .dw (FETCH_A | OP_RL | STORE_A ) ; 17 RLA
3734 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 18 oo JR o (Z80)
3735 .dw (FETCH_DE | OP_ADDHL | STORE_HL ) ; 19 ADD HL,DE
3736 .dw (FETCH_MDE | OP_NOP | STORE_A ) ; 1A LD A,(DE)
3737 .dw (FETCH_DE | OP_DEC16 | STORE_DE ) ; 1B DEC DE
3738 .dw (FETCH_E | OP_INC | STORE_E ) ; 1C INC E
3739 .dw (FETCH_E | OP_DEC | STORE_E ) ; 1D DEC E
3740 .dw (FETCH_DIR8 | OP_NOP | STORE_E ) ; 1E nn LD E,n
3741 .dw (FETCH_A | OP_RR | STORE_A ) ; 1F RRA
3742 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 20 oo JR NZ,o (Z80)
3743 .dw (FETCH_DIR16| OP_NOP | STORE_HL ) ; 21 nn nn LD HL,nn
3744 .dw (FETCH_DIR16| OP_STHL | STORE_NOP) ; 22 nn nn LD (nn),HL
3745 .dw (FETCH_HL | OP_INC16 | STORE_HL ) ; 23 INC HL
3746 .dw (FETCH_H | OP_INC | STORE_H ) ; 24 INC H
3747 .dw (FETCH_H | OP_DEC | STORE_H ) ; 25 DEC H
3748 .dw (FETCH_DIR8 | OP_NOP | STORE_H ) ; 26 nn LD H,n
3749 .dw (FETCH_A | OP_DA | STORE_A ) ; 27 DAA
3750 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 28 oo JR Z,o (Z80)
3751 .dw (FETCH_HL | OP_ADDHL | STORE_HL ) ; 29 ADD HL,HL
3752 .dw (FETCH_DIR16| OP_RMEM16 | STORE_HL ) ; 2A nn nn LD HL,(nn)
3753 .dw (FETCH_HL | OP_DEC16 | STORE_HL ) ; 2B DEC HL
3754 .dw (FETCH_L | OP_INC | STORE_L ) ; 2C INC L
3755 .dw (FETCH_L | OP_DEC | STORE_L ) ; 2D DEC L
3756 .dw (FETCH_DIR8 | OP_NOP | STORE_L ) ; 2E nn LD L,n
3757 .dw (FETCH_A | OP_CPL | STORE_A ) ; 2F CPL
3758 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 30 oo JR NC,o (Z80)
3759 .dw (FETCH_DIR16| OP_NOP | STORE_SP ) ; 31 nn nn LD SP,nn
3760 .dw (FETCH_DIR16| OP_NOP | STORE_AM ) ; 32 nn nn LD (nn),A
3761 .dw (FETCH_SP | OP_INC16 | STORE_SP ) ; 33 INC SP
3762 .dw (FETCH_MHL | OP_INC | STORE_MHL) ; 34 INC (HL)
3763 .dw (FETCH_MHL | OP_DEC | STORE_MHL) ; 35 DEC (HL)
3764 .dw (FETCH_DIR8 | OP_NOP | STORE_MHL) ; 36 nn LD (HL),n
3765 .dw (FETCH_NOP | OP_SCF | STORE_NOP) ; 37 SCF
3766 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; 38 oo JR C,o (Z80)
3767 .dw (FETCH_SP | OP_ADDHL | STORE_HL ) ; 39 ADD HL,SP
3768 .dw (FETCH_DIR16| OP_RMEM8 | STORE_A ) ; 3A nn nn LD A,(nn)
3769 .dw (FETCH_SP | OP_DEC16 | STORE_SP ) ; 3B DEC SP
3770 .dw (FETCH_A | OP_INC | STORE_A ) ; 3C INC A
3771 .dw (FETCH_A | OP_DEC | STORE_A ) ; 3D DEC A
3772 .dw (FETCH_DIR8 | OP_NOP | STORE_A ) ; 3E nn LD A,n
3773 .dw (FETCH_NOP | OP_CCF | STORE_NOP) ; 3F CCF (Complement Carry Flag, gvd)
3774 .dw (FETCH_B | OP_NOP | STORE_B ) ; 40 LD B,r
3775 .dw (FETCH_C | OP_NOP | STORE_B ) ; 41 LD B,r
3776 .dw (FETCH_D | OP_NOP | STORE_B ) ; 42 LD B,r
3777 .dw (FETCH_E | OP_NOP | STORE_B ) ; 43 LD B,r
3778 .dw (FETCH_H | OP_NOP | STORE_B ) ; 44 LD B,r
3779 .dw (FETCH_L | OP_NOP | STORE_B ) ; 45 LD B,r
3780 .dw (FETCH_MHL | OP_NOP | STORE_B ) ; 46 LD B,r
3781 .dw (FETCH_A | OP_NOP | STORE_B ) ; 47 LD B,r
3782 .dw (FETCH_B | OP_NOP | STORE_C ) ; 48 LD C,r
3783 .dw (FETCH_C | OP_NOP | STORE_C ) ; 49 LD C,r
3784 .dw (FETCH_D | OP_NOP | STORE_C ) ; 4A LD C,r
3785 .dw (FETCH_E | OP_NOP | STORE_C ) ; 4B LD C,r
3786 .dw (FETCH_H | OP_NOP | STORE_C ) ; 4C LD C,r
3787 .dw (FETCH_L | OP_NOP | STORE_C ) ; 4D LD C,r
3788 .dw (FETCH_MHL | OP_NOP | STORE_C ) ; 4E LD C,r
3789 .dw (FETCH_A | OP_NOP | STORE_C ) ; 4F LD C,r
3790 .dw (FETCH_B | OP_NOP | STORE_D ) ; 50 LD D,r
3791 .dw (FETCH_C | OP_NOP | STORE_D ) ; 51 LD D,r
3792 .dw (FETCH_D | OP_NOP | STORE_D ) ; 52 LD D,r
3793 .dw (FETCH_E | OP_NOP | STORE_D ) ; 53 LD D,r
3794 .dw (FETCH_H | OP_NOP | STORE_D ) ; 54 LD D,r
3795 .dw (FETCH_L | OP_NOP | STORE_D ) ; 55 LD D,r
3796 .dw (FETCH_MHL | OP_NOP | STORE_D ) ; 56 LD D,r
3797 .dw (FETCH_A | OP_NOP | STORE_D ) ; 57 LD D,r
3798 .dw (FETCH_B | OP_NOP | STORE_E ) ; 58 LD E,r
3799 .dw (FETCH_C | OP_NOP | STORE_E ) ; 59 LD E,r
3800 .dw (FETCH_D | OP_NOP | STORE_E ) ; 5A LD E,r
3801 .dw (FETCH_E | OP_NOP | STORE_E ) ; 5B LD E,r
3802 .dw (FETCH_H | OP_NOP | STORE_E ) ; 5C LD E,r
3803 .dw (FETCH_L | OP_NOP | STORE_E ) ; 5D LD E,r
3804 .dw (FETCH_MHL | OP_NOP | STORE_E ) ; 5E LD E,r
3805 .dw (FETCH_A | OP_NOP | STORE_E ) ; 5F LD E,r
3806 .dw (FETCH_B | OP_NOP | STORE_H ) ; 60 LD H,r
3807 .dw (FETCH_C | OP_NOP | STORE_H ) ; 61 LD H,r
3808 .dw (FETCH_D | OP_NOP | STORE_H ) ; 62 LD H,r
3809 .dw (FETCH_E | OP_NOP | STORE_H ) ; 63 LD H,r
3810 .dw (FETCH_H | OP_NOP | STORE_H ) ; 64 LD H,r
3811 .dw (FETCH_L | OP_NOP | STORE_H ) ; 65 LD H,r
3812 .dw (FETCH_MHL | OP_NOP | STORE_H ) ; 66 LD H,r
3813 .dw (FETCH_A | OP_NOP | STORE_H ) ; 67 LD H,r
3814 .dw (FETCH_B | OP_NOP | STORE_L ) ; 68 LD L,r
3815 .dw (FETCH_C | OP_NOP | STORE_L ) ; 69 LD L,r
3816 .dw (FETCH_D | OP_NOP | STORE_L ) ; 6A LD L,r
3817 .dw (FETCH_E | OP_NOP | STORE_L ) ; 6B LD L,r
3818 .dw (FETCH_H | OP_NOP | STORE_L ) ; 6C LD L,r
3819 .dw (FETCH_L | OP_NOP | STORE_L ) ; 6D LD L,r
3820 .dw (FETCH_MHL | OP_NOP | STORE_L ) ; 6E LD L,r
3821 .dw (FETCH_A | OP_NOP | STORE_L ) ; 6F LD L,r
3822 .dw (FETCH_B | OP_NOP | STORE_MHL) ; 70 LD (HL),r
3823 .dw (FETCH_C | OP_NOP | STORE_MHL) ; 71 LD (HL),r
3824 .dw (FETCH_D | OP_NOP | STORE_MHL) ; 72 LD (HL),r
3825 .dw (FETCH_E | OP_NOP | STORE_MHL) ; 73 LD (HL),r
3826 .dw (FETCH_H | OP_NOP | STORE_MHL) ; 74 LD (HL),r
3827 .dw (FETCH_L | OP_NOP | STORE_MHL) ; 75 LD (HL),r
3828 .dw (FETCH_NOP | OP_NOP | STORE_NOP) ; 76 HALT
3829 .dw (FETCH_A | OP_NOP | STORE_MHL) ; 77 LD (HL),r
3830 .dw (FETCH_B | OP_NOP | STORE_A ) ; 78 LD A,r
3831 .dw (FETCH_C | OP_NOP | STORE_A ) ; 79 LD A,r
3832 .dw (FETCH_D | OP_NOP | STORE_A ) ; 7A LD A,r
3833 .dw (FETCH_E | OP_NOP | STORE_A ) ; 7B LD A,r
3834 .dw (FETCH_H | OP_NOP | STORE_A ) ; 7C LD A,r
3835 .dw (FETCH_L | OP_NOP | STORE_A ) ; 7D LD A,r
3836 .dw (FETCH_MHL | OP_NOP | STORE_A ) ; 7E LD A,r
3837 .dw (FETCH_A | OP_NOP | STORE_A ) ; 7F LD A,r
3838 .dw (FETCH_B | OP_ADDA | STORE_A ) ; 80 ADD A,r
3839 .dw (FETCH_C | OP_ADDA | STORE_A ) ; 81 ADD A,r
3840 .dw (FETCH_D | OP_ADDA | STORE_A ) ; 82 ADD A,r
3841 .dw (FETCH_E | OP_ADDA | STORE_A ) ; 83 ADD A,r
3842 .dw (FETCH_H | OP_ADDA | STORE_A ) ; 84 ADD A,r
3843 .dw (FETCH_L | OP_ADDA | STORE_A ) ; 85 ADD A,r
3844 .dw (FETCH_MHL | OP_ADDA | STORE_A ) ; 86 ADD A,r
3845 .dw (FETCH_A | OP_ADDA | STORE_A ) ; 87 ADD A,r
3846 .dw (FETCH_B | OP_ADCA | STORE_A ) ; 88 ADC A,r
3847 .dw (FETCH_C | OP_ADCA | STORE_A ) ; 89 ADC A,r
3848 .dw (FETCH_D | OP_ADCA | STORE_A ) ; 8A ADC A,r
3849 .dw (FETCH_E | OP_ADCA | STORE_A ) ; 8B ADC A,r
3850 .dw (FETCH_H | OP_ADCA | STORE_A ) ; 8C ADC A,r
3851 .dw (FETCH_L | OP_ADCA | STORE_A ) ; 8D ADC A,r
3852 .dw (FETCH_MHL | OP_ADCA | STORE_A ) ; 8E ADC A,r
3853 .dw (FETCH_A | OP_ADCA | STORE_A ) ; 8F ADC A,r
3854 .dw (FETCH_B | OP_SUBFA | STORE_A ) ; 90 SUB A,r
3855 .dw (FETCH_C | OP_SUBFA | STORE_A ) ; 91 SUB A,r
3856 .dw (FETCH_D | OP_SUBFA | STORE_A ) ; 92 SUB A,r
3857 .dw (FETCH_E | OP_SUBFA | STORE_A ) ; 93 SUB A,r
3858 .dw (FETCH_H | OP_SUBFA | STORE_A ) ; 94 SUB A,r
3859 .dw (FETCH_L | OP_SUBFA | STORE_A ) ; 95 SUB A,r
3860 .dw (FETCH_MHL | OP_SUBFA | STORE_A ) ; 96 SUB A,r
3861 .dw (FETCH_A | OP_SUBFA | STORE_A ) ; 97 SUB A,r
3862 .dw (FETCH_B | OP_SBCFA | STORE_A ) ; 98 SBC A,r
3863 .dw (FETCH_C | OP_SBCFA | STORE_A ) ; 99 SBC A,r
3864 .dw (FETCH_D | OP_SBCFA | STORE_A ) ; 9A SBC A,r
3865 .dw (FETCH_E | OP_SBCFA | STORE_A ) ; 9B SBC A,r
3866 .dw (FETCH_H | OP_SBCFA | STORE_A ) ; 9C SBC A,r
3867 .dw (FETCH_L | OP_SBCFA | STORE_A ) ; 9D SBC A,r
3868 .dw (FETCH_MHL | OP_SBCFA | STORE_A ) ; 9E SBC A,r
3869 .dw (FETCH_A | OP_SBCFA | STORE_A ) ; 9F SBC A,r
3870 .dw (FETCH_B | OP_ANDA | STORE_A ) ; A0 AND A,r
3871 .dw (FETCH_C | OP_ANDA | STORE_A ) ; A1 AND A,r
3872 .dw (FETCH_D | OP_ANDA | STORE_A ) ; A2 AND A,r
3873 .dw (FETCH_E | OP_ANDA | STORE_A ) ; A3 AND A,r
3874 .dw (FETCH_H | OP_ANDA | STORE_A ) ; A4 AND A,r
3875 .dw (FETCH_L | OP_ANDA | STORE_A ) ; A5 AND A,r
3876 .dw (FETCH_MHL | OP_ANDA | STORE_A ) ; A6 AND A,r
3877 .dw (FETCH_A | OP_ANDA | STORE_A ) ; A7 AND A,r
3878 .dw (FETCH_B | OP_XORA | STORE_A ) ; A8 XOR A,r
3879 .dw (FETCH_C | OP_XORA | STORE_A ) ; A9 XOR A,r
3880 .dw (FETCH_D | OP_XORA | STORE_A ) ; AA XOR A,r
3881 .dw (FETCH_E | OP_XORA | STORE_A ) ; AB XOR A,r
3882 .dw (FETCH_H | OP_XORA | STORE_A ) ; AC XOR A,r
3883 .dw (FETCH_L | OP_XORA | STORE_A ) ; AD XOR A,r
3884 .dw (FETCH_MHL | OP_XORA | STORE_A ) ; AE XOR A,r
3885 .dw (FETCH_A | OP_XORA | STORE_A ) ; AF XOR A,r
3886 .dw (FETCH_B | OP_ORA | STORE_A ) ; B0 OR A,r
3887 .dw (FETCH_C | OP_ORA | STORE_A ) ; B1 OR A,r
3888 .dw (FETCH_D | OP_ORA | STORE_A ) ; B2 OR A,r
3889 .dw (FETCH_E | OP_ORA | STORE_A ) ; B3 OR A,r
3890 .dw (FETCH_H | OP_ORA | STORE_A ) ; B4 OR A,r
3891 .dw (FETCH_L | OP_ORA | STORE_A ) ; B5 OR A,r
3892 .dw (FETCH_MHL | OP_ORA | STORE_A ) ; B6 OR A,r
3893 .dw (FETCH_A | OP_ORA | STORE_A ) ; B7 OR A,r
3894 .dw (FETCH_B | OP_SUBFA | STORE_NOP) ; B8 CP A,r
3895 .dw (FETCH_C | OP_SUBFA | STORE_NOP) ; B9 CP A,r
3896 .dw (FETCH_D | OP_SUBFA | STORE_NOP) ; BA CP A,r
3897 .dw (FETCH_E | OP_SUBFA | STORE_NOP) ; BB CP A,r
3898 .dw (FETCH_H | OP_SUBFA | STORE_NOP) ; BC CP A,r
3899 .dw (FETCH_L | OP_SUBFA | STORE_NOP) ; BD CP A,r
3900 .dw (FETCH_MHL | OP_SUBFA | STORE_NOP) ; BE CP A,r
3901 .dw (FETCH_A | OP_SUBFA | STORE_NOP) ; BF CP A,r
3902 .dw (FETCH_NOP | OP_IFNZ | STORE_RET) ; C0 RET NZ
3903 .dw (FETCH_NOP | OP_POP16 | STORE_BC ) ; C1 POP BC
3904 .dw (FETCH_DIR16| OP_IFNZ | STORE_PC ) ; C2 nn nn JP NZ,nn
3905 .dw (FETCH_DIR16| OP_NOP | STORE_PC ) ; C3 nn nn JP nn
3906 .dw (FETCH_DIR16| OP_IFNZ | STORE_CALL) ; C4 nn nn CALL NZ,nn
3907 .dw (FETCH_BC | OP_PUSH16 | STORE_NOP) ; C5 PUSH BC
3908 .dw (FETCH_DIR8 | OP_ADDA | STORE_A ) ; C6 nn ADD A,n
3909 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; C7 RST 0
3910 .dw (FETCH_NOP | OP_IFZ | STORE_RET) ; C8 RET Z
3911 .dw (FETCH_NOP | OP_NOP | STORE_RET) ; C9 RET
3912 .dw (FETCH_DIR16| OP_IFZ | STORE_PC ) ; CA nn nn JP Z,nn
3913 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; CB (Z80 specific)
3914 .dw (FETCH_DIR16| OP_IFZ | STORE_CALL) ; CC nn nn CALL Z,nn
3915 .dw (FETCH_DIR16| OP_NOP | STORE_CALL) ; CD nn nn CALL nn
3916 .dw (FETCH_DIR8 | OP_ADCA | STORE_A ) ; CE nn ADC A,n
3917 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; CF RST 8H
3918 .dw (FETCH_NOP | OP_IFNC | STORE_RET) ; D0 RET NC
3919 .dw (FETCH_NOP | OP_POP16 | STORE_DE ) ; D1 POP DE
3920 .dw (FETCH_DIR16| OP_IFNC | STORE_PC ) ; D2 nn nn JP NC,nn
3921 .dw (FETCH_DIR8 | OP_OUTA | STORE_NOP) ; D3 nn OUT (n),A
3922 .dw (FETCH_DIR16| OP_IFNC | STORE_CALL) ; D4 nn nn CALL NC,nn
3923 .dw (FETCH_DE | OP_PUSH16 | STORE_NOP) ; D5 PUSH DE
3924 .dw (FETCH_DIR8 | OP_SUBFA | STORE_A ) ; D6 nn SUB n
3925 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; D7 RST 10H
3926 .dw (FETCH_NOP | OP_IFC | STORE_RET) ; D8 RET C
3927 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; D9 EXX (Z80)
3928 .dw (FETCH_DIR16| OP_IFC | STORE_PC ) ; DA nn nn JP C,nn
3929 .dw (FETCH_DIR8 | OP_IN | STORE_A ) ; DB nn IN A,(n)
3930 .dw (FETCH_DIR16| OP_IFC | STORE_CALL) ; DC nn nn CALL C,nn
3931 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; DD (Z80)
3932 .dw (FETCH_DIR8 | OP_SBCFA | STORE_A ) ; DE nn SBC A,n
3933 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; DF RST 18H
3934 .dw (FETCH_NOP | OP_IFPO | STORE_RET) ; E0 RET PO
3935 .dw (FETCH_NOP | OP_POP16 | STORE_HL ) ; E1 POP HL
3936 .dw (FETCH_DIR16| OP_IFPO | STORE_PC ) ; E2 nn nn JP PO,nn
3937 .dw (FETCH_MSP | OP_EXHL | STORE_MSP) ; E3 EX (SP),HL
3938 .dw (FETCH_DIR16| OP_IFPO | STORE_CALL) ; E4 nn nn CALL PO,nn
3939 .dw (FETCH_HL | OP_PUSH16 | STORE_NOP) ; E5 PUSH HL
3940 .dw (FETCH_DIR8 | OP_ANDA | STORE_A ) ; E6 nn AND n
3941 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; E7 RST 20H
3942 .dw (FETCH_NOP | OP_IFPE | STORE_RET) ; E8 RET PE
3943 .dw (FETCH_HL | OP_NOP | STORE_PC ) ; E9 JP (HL)
3944 .dw (FETCH_DIR16| OP_IFPE | STORE_PC ) ; EA nn nn JP PE,nn
3945 .dw (FETCH_DE | OP_EXHL | STORE_DE ) ; EB EX DE,HL
3946 .dw (FETCH_DIR16| OP_IFPE | STORE_CALL) ; EC nn nn CALL PE,nn
3947 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; ED (Z80 specific)
3948 .dw (FETCH_DIR8 | OP_XORA | STORE_A ) ; EE nn XOR n
3949 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; EF RST 28H
3950 .dw (FETCH_NOP | OP_IFP | STORE_RET) ; F0 RET P
3951 .dw (FETCH_NOP | OP_POP16 | STORE_AF ) ; F1 POP AF
3952 .dw (FETCH_DIR16| OP_IFP | STORE_PC ) ; F2 nn nn JP P,nn
3953 .dw (FETCH_NOP | OP_DI | STORE_NOP) ; F3 DI
3954 .dw (FETCH_DIR16| OP_IFP | STORE_CALL) ; F4 nn nn CALL P,nn
3955 .dw (FETCH_AF | OP_PUSH16 | STORE_NOP) ; F5 PUSH AF
3956 .dw (FETCH_DIR8 | OP_ORA | STORE_A ) ; F6 nn OR n
3957 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; F7 RST 30H
3958 .dw (FETCH_NOP | OP_IFM | STORE_RET) ; F8 RET M
3959 .dw (FETCH_HL | OP_NOP | STORE_SP ) ; F9 LD SP,HL
3960 .dw (FETCH_DIR16| OP_IFM | STORE_PC ) ; FA nn nn JP M,nn
3961 .dw (FETCH_NOP | OP_EI | STORE_NOP) ; FB EI
3962 .dw (FETCH_DIR16| OP_IFM | STORE_CALL) ; FC nn nn CALL M,nn
3963 .dw (FETCH_NOP | OP_INV | STORE_NOP) ; FD (Z80 specific)
3964 .dw (FETCH_DIR8 | OP_SUBFA | STORE_NOP) ; FE nn CP n
3965 .dw (FETCH_RST | OP_NOP | STORE_CALL) ; FF RST 38H
3967 ; vim:set ts=8 noet nowrap