Z80 Assembly Instruction Set
31 May 2023
As I am refreshing my Z80 assembly skills I realized that I don’t have a good understanding of some of the less popular instructions. To make sure that I understand how everything works I’ve gone through all of the instructions and made notes on how they work.
This will be a living document that I will update as I find errors or ommisions. It is intended to be a quick reference. Each of the instructions has the information that I find useful, not a full explanation. I hope that others find it valuable too.
Data Load
Instruction | Destination | Source |
---|---|---|
LD | A | A B C D E H L (HL) (BC) (DE) (IX+index) (IY+index) (word) byte |
LD | B C D E H L | A B C D E H L (HL) (IX+index) (IY+index) byte |
LD | (HL) (IX+index) (IY+index) | A B C D E H L byte |
LD | (BC) (DE) (word) | A |
LD | BC DE HL SP IX IY | word (word) |
LD | (word) | BC DE HL SP IX IY |
LD | SP | HL IX IY |
Register Exchange
Instruction | Operation | Description |
---|---|---|
EX | DE,HL | HL <-> DE |
EX | (SP),HL | H <-> (SP+1); L <-> (SP) |
EX | (SP),IX | IXh <-> (SP+1); IXl <-> (SP) |
EX | (SP),IY | IYh <-> (SP+1); IYl <-> (SP) |
EX | AF,AF’ | AF <-> AF’ |
EXX | BC/DE/HL <-> BC’/DE’/HL’ |
Addition and Subtraction
Instruction | Destination | Source | Description |
---|---|---|---|
ADD | A | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A + SOURCE |
ADC | A | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A + SOURCE + Carry |
SUB | A | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A - SOURCE |
SBC | A | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A - SOURCE - Carry |
ADD | HL IX IY | BC DE HL SP | DEST = DEST + SOURCE |
ADC | HL | BC DE HL SP | HL = HL + SOURCE + Carry |
SUB | HL | BC DE HL SP | HL = HL - SOURCE |
SBC | HL | BC DE HL SP | HL = HL - SOURCE - Carry |
Interrupts and Control
Instruction | Operation | Description |
---|---|---|
DI | Disable interrupts | |
EI | Enable interrupts | |
IM | 0 | Interrupt mode 0. Interrupting devices place data on the bus for the CPU to execute |
IM | 1 | Interrupt mode 1. Interrupts execute RST 38H |
IM | 2 | Interrupt mode 2. Interrupts perform a call to a location in memory |
LD | I,A | Interrupt Page = A |
LD | A,I | A = Interrupt Page |
LD | R,A | Refresh Register = A |
LD | A,R | A = Refresh Register |
NOP | No Operation | |
HALT | NOP and loop |
Increment and Decrement
Instruction | Targets |
---|---|
INC | A B C D E H L (HL) (IX+index) (IY+index) |
DEC | A B C D E H L (HL) (IX+index) (IY+index) |
INC | BC DE HL SP IX IY |
DEC | BC DE HL SP IX IY |
Special Accumulator and Flags
Instruction | Description |
---|---|
DAA | Convert A to BCD. Used after adding or subtracting two BCD numbers |
CPL | Complement A = NOT A |
SCF | Set the Carry Flag to 1 |
CCF | Complement the Carry Flag |
NEG | Negate A |
Rotate
Instruction | Targets | Description |
---|---|---|
RLCA | Rotate A left circular | |
RRCA | Rotate A right circular | |
RLA | Rotate A left through carry | |
RRA | Rotate A right through carry | |
RLD | For BCD. Move low nibble of (HL) to high nibble, move high nibble to A and move A to low nibble | |
RRD | For BCD. Move low nibble of (HL) to A, high nibble to low and A to high nibble | |
RLC | A B C D E H L (HL) (IX+index) (IY+index) | Rotate left circular |
RL | A B C D E H L (HL) (IX+index) (IY+index) | Rotate left through carry |
RRC | A B C D E H L (HL) (IX+index) (IY+index) | Rotate right circular |
RR | A B C D E H L (HL) (IX+index) (IY+index) | Rotate right through carry |
SLA | A B C D E H L (HL) (IX+index) (IY+index) | Shift left arithmetic, sets LSB to 0, MSB goes to Carry |
SRA | A B C D E H L (HL) (IX+index) (IY+index) | Shift right arithmetic, MSB unchanged, LSB goes to Carry |
SRL | A B C D E H L (HL) (IX+index) (IY+index) | Shift right logical, sets MSB to 0, LSB goes to Carry |
Logical Byte Operations
Instruction | Targets | Description |
---|---|---|
AND | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A AND Target |
XOR | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A XOR Target |
OR | A B C D E H L (HL) (IX+index) (IY+index) byte | A = A OR Target |
CP | A B C D E H L (HL) (IX+index) (IY+index) byte | Compare A to Target |
CPI | Compare A to (HL) then increment HL and decrement BC | |
CPIR | Same as CPI except repeat until a match is found or BC == 0 | |
CPD | Compare A to (HL) then decrement HL and BC | |
CPDR | Same as CPD except repeat until a match is found or BC == 0 |
Branch Control/Program Counter Load
Instruction | Operation | Description |
---|---|---|
JP | address | Jump to address or label |
JP | NZ,address | Jump if A != CP |
JP | Z,address | Jump if A = CP |
JP | NC,address | Jump if A >= CP |
JP | C,address | Jump if A < CP |
JP | PO,address | Jump if odd number of bits in CP |
JP | PE,address | Jump if even number of bits in CP |
JP | P,address | Jump if positive (first bit of A is 0) |
JP | M,address | Jump if negative (first bit of A is 1) |
JP | (HL) (IX) (IY) | Jump to what is stored at HL, IX, IY |
JR | index | Relative jump to address or label |
JR | NZ,index | Relative Jump if A != CP |
JR | Z,index | Relative Jump if A = CP |
JR | NC,index | Relative Jump if A >= CP |
JR | C,index | Relative Jump if A < CP |
DJNZ | index | Decreases B and Jumps if B is NotZero |
CALL | address | Call address or label pushing PC to the stack |
CALL | NZ Z NC C PO PE P M | Call on condition |
RET | Pull PC from the stack and return from CALL | |
RET | NZ Z NC C PO PE P M | Return on condition |
RETI | Return from Interrupt | |
RETN | Return from non-maskable Interrupt | |
RST | 0H 8H 10H 18H 20H 28H 30H 38H | CALL 0H except 1 byte long instead of 3 |
Stack
Instruction | Targets | Description |
---|---|---|
PUSH | BC DE HL AF IX IY | Push target to the stack and decrement stack by 2 |
POP | BC DE HL AF IX IY | Pop target from the stack and increment stack by 2 |
Input/Output
Instruction | Operation | Description |
---|---|---|
IN | A,(byte) | A = [byte] |
IN | A,(port) | A = [port] |
IN | B,(port) | B = [port] |
IN | C,(port) | C = [port] |
IN | D,(port) | D = [port] |
IN | E,(port) | E = [port] |
IN | H,(port) | H = [port] |
IN | L,(port) | L = [port] |
INI | Set (HL) = [port], decrement B and increment HL | |
INIR | Same as INI, repeat until B = 0 | |
IND | Set (HL) = [port], decrement B and HL | |
INDR | Same as IND, repeat until B = 0 | |
OUT | (byte),A | [byte] = A |
OUT | (port),A | [port] = A |
OUT | (port),B | [port] = B |
OUT | (port),C | [port] = C |
OUT | (port),D | [port] = D |
OUT | (port),E | [port] = E |
OUT | (port),H | [port] = H |
OUT | (port),L | [port] = L |
OUTI | Set [port] = (HL), decrement B and increment HL | |
OTIR | Same as OUTI, repeat until B = 0 | |
OUTD | Set [port] = (HL), decrement B and HL | |
OTDR | Same as OUTD, repeat until B = 0 |
Data Transfer
Instruction | Description |
---|---|
LDI | Sets (DE) = (HL), increment HL and DE, decrement BC |
LDIR | Same as LDI but repeats until B = 0 |
LDD | Sets (DE) = (HL), decrement HL, DE and BC |
LDDR | Same as LDD but repeats until B = 0 |
Bit Manipulation
Instruction | Bits | Registers | Description |
---|---|---|---|
BIT | 0-7 | A B C D E H L (HL) (IX+index) (IY+index) | Set Z flag to NOT bit in register |
RES | 0-7 | A B C D E H L (HL) (IX+index) (IY+index) | Set bit in register to 0 |
SET | 0-7 | A B C D E H L (HL) (IX+index) (IY+index) | Set bit in register to 1 |