i6502/opcodes.go

407 lines
8.4 KiB
Go

package i6502
// Addressing modes
const (
_ = iota
absolute
absoluteX
absoluteY
accumulator
immediate
implied
indirect
indirectX
indirectY
relative
zeropage
zeropageX
zeropageY
)
var addressingNames = [...]string{
"",
"absolute",
"absoluteX",
"absoluteY",
"accumulator",
"immediate",
"implied",
"(indirect)",
"(indirect,X)",
"(indirect),Y",
"relative",
"zeropage",
"zeropageX",
"zeropageY",
}
// OpCode table
const (
_ = iota
adc
and
asl
bcc
bcs
beq
bit
bmi
bne
bpl
brk
bvc
bvs
clc
cld
cli
clv
cmp
cpx
cpy
dec
dex
dey
eor
inc
inx
iny
jmp
jsr
lda
ldx
ldy
lsr
nop
ora
pha
php
pla
plp
rol
ror
rti
rts
sbc
sec
sed
sei
sta
stx
sty
tax
tay
tsx
txa
txs
tya
)
var instructionNames = [...]string{
"",
"ADC",
"AND",
"ASL",
"BCC",
"BCS",
"BEQ",
"BIT",
"BMI",
"BNE",
"BPL",
"BRK",
"BVC",
"BVS",
"CLC",
"CLD",
"CLI",
"CLV",
"CMP",
"CPX",
"CPY",
"DEC",
"DEX",
"DEY",
"EOR",
"INC",
"INX",
"INY",
"JMP",
"JSR",
"LDA",
"LDX",
"LDY",
"LSR",
"NOP",
"ORA",
"PHA",
"PHP",
"PLA",
"PLP",
"ROL",
"ROR",
"RTI",
"RTS",
"SBC",
"SEC",
"SED",
"SEI",
"STA",
"STX",
"STY",
"TAX",
"TAY",
"TSX",
"TXA",
"TXS",
"TYA",
}
// OpType is the operation type, it includes the instruction and
// addressing mode. It also includes some extra information for the
// emulator, like number of cycles
type OpType struct {
Opcode byte // 65(C)02 Opcode, this includes an instruction and addressing mode
opcodeId uint8 // Decoded opcode Id,
addressingId uint8 // Decoded address mode Id
Size uint8 // Size of the entire instruction in bytes
Cycles uint8 // Number of clock cycles required to complete this instruction
}
var opTypes = map[uint8]OpType{
0xEA: OpType{0xEA, nop, implied, 1, 2},
// Set instruction
0x38: OpType{0x38, sec, implied, 1, 2},
0xF8: OpType{0xF8, sed, implied, 1, 2},
0x78: OpType{0x78, sei, implied, 1, 2},
// Clear instructions
0x18: OpType{0x18, clc, implied, 1, 2},
0xD8: OpType{0xD8, cld, implied, 1, 2},
0x58: OpType{0x58, cli, implied, 1, 2},
0xB8: OpType{0xB8, clv, implied, 1, 2},
// ADC
0x69: OpType{0x69, adc, immediate, 2, 2},
0x65: OpType{0x65, adc, zeropage, 2, 3},
0x75: OpType{0x75, adc, zeropageX, 2, 4},
0x6D: OpType{0x6D, adc, absolute, 3, 4},
0x7D: OpType{0x7D, adc, absoluteX, 3, 4},
0x79: OpType{0x79, adc, absoluteY, 3, 4},
0x61: OpType{0x61, adc, indirectX, 2, 6},
0x71: OpType{0x71, adc, indirectY, 2, 5},
// SBC
0xE9: OpType{0xE9, sbc, immediate, 2, 2},
0xE5: OpType{0xE5, sbc, zeropage, 2, 3},
0xF5: OpType{0xF5, sbc, zeropageX, 2, 4},
0xED: OpType{0xED, sbc, absolute, 3, 4},
0xFD: OpType{0xFD, sbc, absoluteX, 3, 4},
0xF9: OpType{0xF9, sbc, absoluteY, 3, 4},
0xE1: OpType{0xE1, sbc, indirectX, 2, 6},
0xF1: OpType{0xF1, sbc, indirectY, 2, 5},
// Increments
0xE8: OpType{0xE8, inx, implied, 1, 2},
0xC8: OpType{0xC8, iny, implied, 1, 2},
0xE6: OpType{0xE6, inc, zeropage, 2, 5},
0xF6: OpType{0xF6, inc, zeropageX, 2, 6},
0xEE: OpType{0xEE, inc, absolute, 3, 6},
0xFE: OpType{0xFE, inc, absoluteX, 3, 7},
// Decrements
0xCA: OpType{0xCA, dex, implied, 1, 2},
0x88: OpType{0x88, dey, implied, 1, 2},
0xC6: OpType{0xC6, dec, zeropage, 2, 5},
0xD6: OpType{0xD6, dec, zeropageX, 2, 6},
0xCE: OpType{0xCE, dec, absolute, 3, 6},
0xDE: OpType{0xDE, dec, absoluteX, 3, 7},
// LDA
0xA9: OpType{0xA9, lda, immediate, 2, 2},
0xA5: OpType{0xA5, lda, zeropage, 2, 3},
0xB5: OpType{0xB5, lda, zeropageX, 2, 4},
0xAD: OpType{0xAD, lda, absolute, 3, 4},
0xBD: OpType{0xBD, lda, absoluteX, 3, 4},
0xB9: OpType{0xB9, lda, absoluteY, 3, 4},
0xA1: OpType{0xA1, lda, indirectX, 2, 6},
0xB1: OpType{0xB1, lda, indirectY, 2, 5},
// LDX
0xA2: OpType{0xA2, ldx, immediate, 2, 2},
0xA6: OpType{0xA6, ldx, zeropage, 2, 3},
0xB6: OpType{0xB6, ldx, zeropageY, 2, 4},
0xAE: OpType{0xAE, ldx, absolute, 3, 4},
0xBE: OpType{0xBE, ldx, absoluteY, 3, 4},
// LDY
0xA0: OpType{0xA0, ldy, immediate, 2, 2},
0xA4: OpType{0xA4, ldy, zeropage, 2, 3},
0xB4: OpType{0xB4, ldy, zeropageX, 2, 4},
0xAC: OpType{0xAC, ldy, absolute, 3, 4},
0xBC: OpType{0xBC, ldy, absoluteX, 3, 4},
// ORA
0x09: OpType{0x09, ora, immediate, 2, 2},
0x05: OpType{0x05, ora, zeropage, 2, 3},
0x15: OpType{0x15, ora, zeropageX, 2, 4},
0x0D: OpType{0x0D, ora, absolute, 3, 4},
0x1D: OpType{0x1D, ora, absoluteX, 3, 4},
0x19: OpType{0x19, ora, absoluteY, 3, 4},
0x01: OpType{0x01, ora, indirectX, 2, 6},
0x11: OpType{0x11, ora, indirectY, 2, 5},
// AND
0x29: OpType{0x29, and, immediate, 2, 2},
0x25: OpType{0x25, and, zeropage, 2, 3},
0x35: OpType{0x35, and, zeropageX, 2, 4},
0x2D: OpType{0x2D, and, absolute, 3, 4},
0x3D: OpType{0x3D, and, absoluteX, 3, 4},
0x39: OpType{0x39, and, absoluteY, 3, 4},
0x21: OpType{0x21, and, indirectX, 2, 6},
0x31: OpType{0x31, and, indirectY, 2, 5},
// EOR
0x49: OpType{0x49, eor, immediate, 2, 2},
0x45: OpType{0x45, eor, zeropage, 2, 3},
0x55: OpType{0x55, eor, zeropageX, 2, 4},
0x4D: OpType{0x4D, eor, absolute, 3, 4},
0x5D: OpType{0x5D, eor, absoluteX, 3, 4},
0x59: OpType{0x59, eor, absoluteY, 3, 4},
0x41: OpType{0x41, eor, indirectX, 2, 6},
0x51: OpType{0x51, eor, indirectY, 2, 5},
// STA
0x85: OpType{0x85, sta, zeropage, 2, 3},
0x95: OpType{0x95, sta, zeropageX, 2, 4},
0x8D: OpType{0x8D, sta, absolute, 3, 4},
0x9D: OpType{0x9D, sta, absoluteX, 3, 5},
0x99: OpType{0x99, sta, absoluteY, 3, 5},
0x81: OpType{0x81, sta, indirectX, 2, 6},
0x91: OpType{0x91, sta, indirectY, 2, 6},
// STX
0x86: OpType{0x86, stx, zeropage, 2, 3},
0x96: OpType{0x96, stx, zeropageY, 2, 4},
0x8E: OpType{0x8E, stx, absolute, 3, 4},
// STY
0x84: OpType{0x84, sty, zeropage, 2, 3},
0x94: OpType{0x94, sty, zeropageX, 2, 4},
0x8C: OpType{0x8C, sty, absolute, 3, 4},
// TAX
0xAA: OpType{0xAA, tax, implied, 1, 2},
// TAY
0xA8: OpType{0xA8, tay, implied, 1, 2},
// TXA
0x8A: OpType{0x8A, txa, implied, 1, 2},
// TXA
0x98: OpType{0x98, tya, implied, 1, 2},
// TSX
0xBA: OpType{0xBA, tsx, implied, 1, 2},
// TXS
0x9A: OpType{0x9A, txs, implied, 1, 2},
// ASL
0x0A: OpType{0x0A, asl, accumulator, 1, 2},
0x06: OpType{0x06, asl, zeropage, 2, 5},
0x16: OpType{0x16, asl, zeropageX, 2, 6},
0x0E: OpType{0x0E, asl, absolute, 3, 6},
0x1E: OpType{0x1E, asl, absoluteX, 3, 7},
// LSR
0x4A: OpType{0x4A, lsr, accumulator, 1, 2},
0x46: OpType{0x46, lsr, zeropage, 2, 5},
0x56: OpType{0x56, lsr, zeropageX, 2, 6},
0x4E: OpType{0x4E, lsr, absolute, 3, 6},
0x5E: OpType{0x5E, lsr, absoluteX, 3, 7},
// ROL
0x2A: OpType{0x2A, rol, accumulator, 1, 2},
0x26: OpType{0x26, rol, zeropage, 2, 5},
0x36: OpType{0x36, rol, zeropageX, 2, 6},
0x2E: OpType{0x2E, rol, absolute, 3, 6},
0x3E: OpType{0x3E, rol, absoluteX, 3, 7},
// ROR
0x6A: OpType{0x6A, ror, accumulator, 1, 2},
0x66: OpType{0x66, ror, zeropage, 2, 5},
0x76: OpType{0x76, ror, zeropageX, 2, 6},
0x6E: OpType{0x6E, ror, absolute, 3, 6},
0x7E: OpType{0x7E, ror, absoluteX, 3, 7},
// CMP
0xC9: OpType{0xC9, cmp, immediate, 2, 2},
0xC5: OpType{0xC5, cmp, zeropage, 2, 3},
0xD5: OpType{0xD5, cmp, zeropageX, 2, 4},
0xCD: OpType{0xCD, cmp, absolute, 3, 4},
0xDD: OpType{0xDD, cmp, absoluteX, 3, 4},
0xD9: OpType{0xD9, cmp, absoluteY, 3, 4},
0xC1: OpType{0xC1, cmp, indirectX, 2, 6},
0xD1: OpType{0xD1, cmp, indirectY, 2, 5},
// CPX
0xE0: OpType{0xE0, cpx, immediate, 2, 2},
0xE4: OpType{0xE4, cpx, zeropage, 2, 3},
0xEC: OpType{0xEC, cpx, absolute, 3, 4},
// CPY
0xC0: OpType{0xC0, cpy, immediate, 2, 2},
0xC4: OpType{0xC4, cpy, zeropage, 2, 3},
0xCC: OpType{0xCC, cpy, absolute, 3, 4},
// BRK
0x00: OpType{0x00, brk, implied, 1, 7},
// BCC / BCS
0x90: OpType{0x90, bcc, relative, 2, 2},
0xB0: OpType{0xB0, bcs, relative, 2, 2},
// BNE / BEQ
0xD0: OpType{0xD0, bne, relative, 2, 2},
0xF0: OpType{0xF0, beq, relative, 2, 2},
// BPL / BMI
0x10: OpType{0x10, bpl, relative, 2, 2},
0x30: OpType{0x30, bmi, relative, 2, 2},
// BVC / BCS
0x50: OpType{0x50, bvc, relative, 2, 2},
0x70: OpType{0x70, bvs, relative, 2, 2},
// BIT
0x24: OpType{0x24, bit, zeropage, 2, 3},
0x2C: OpType{0x2C, bit, absolute, 3, 4},
// PHP / PLP
0x08: OpType{0x08, php, implied, 1, 3},
0x28: OpType{0x28, plp, implied, 1, 4},
// PHA / PLA
0x48: OpType{0x48, pha, implied, 1, 3},
0x68: OpType{0x68, pla, implied, 1, 4},
// JMP
0x4C: OpType{0x4C, jmp, absolute, 3, 3},
0x6C: OpType{0x6C, jmp, indirect, 3, 5},
// JSR
0x20: OpType{0x20, jsr, absolute, 3, 6},
// RTS
0x60: OpType{0x60, rts, implied, 1, 6},
// RTI
0x40: OpType{0x40, rti, implied, 1, 6},
}