/// Represents all official 6502 CPU instructions.
#[derive(Clone, Copy, Debug, PartialEq)]
pub enum Operation {
    /// Add with Carry
    ///
    /// Affects flags: N, V, Z, C
    ///
    /// Addressing Modes: Immediate (2/2), ZeroPage (2/3), ZeroPageX (2/4), Absolute (3/4),
    /// AbsoluteX (3/4), AbsoluteY (3/4), IndirectX (2/6), IndirectY (2/5)
    ADC,

    /// Logical AND with Accumulator
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Immediate (2/2), ZeroPage (2/3), ZeroPageX (2/4), Absolute (3/4),
    /// AbsoluteX (3/4), AbsoluteY (3/4), IndirectX (2/6), IndirectY (2/5)
    AND,

    /// Arithmetic Shift Left
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Accumulator (1/2), ZeroPage (2/5), ZeroPageX (2/6), Absolute (3/6),
    /// AbsoluteX (3/7)
    ASL,

    /// Branch if Carry Clear
    ///
    /// Addressing Modes: Relative (2/2)
    BCC,

    /// Branch if Carry Set
    ///
    /// Addressing Modes: Relative (2/2)
    BCS,

    /// Branch if Equal (Zero Set)
    ///
    /// Addressing Modes: Relative (2/2)
    BEQ,

    /// Bit Test
    ///
    /// Affects flags: N, V, Z
    ///
    /// Addressing Modes: ZeroPage (2/3), Absolute (3/4)
    BIT,

    /// Branch if Minus (Negative Set)
    ///
    /// Addressing Modes: Relative (2/2)
    BMI,

    /// Branch if Not Equal (Zero Clear)
    ///
    /// Addressing Modes: Relative (2/2)
    BNE,

    /// Branch if Positive (Negative Clear)
    ///
    /// Addressing Modes: Relative (2/2)
    BPL,

    /// Force Interrupt
    ///
    /// Affects flags: B
    ///
    /// Addressing Modes: Implied (1/7)
    BRK,

    /// Branch if Overflow Clear
    ///
    /// Addressing Modes: Relative (2/2)
    BVC,

    /// Branch if Overflow Set
    ///
    /// Addressing Modes: Relative (2/2)
    BVS,

    /// Clear Carry Flag
    ///
    /// Affects flags: C
    ///
    /// Addressing Modes: Implied (1/2)
    CLC,

    /// Clear Decimal Mode
    ///
    /// Affects flags: D
    ///
    /// Addressing Modes: Implied (1/2)
    CLD,

    /// Clear Interrupt Disable
    ///
    /// Affects flags: I
    ///
    /// Addressing Modes: Implied (1/2)
    CLI,

    /// Clear Overflow Flag
    ///
    /// Affects flags: V
    ///
    /// Addressing Modes: Implied (2/2)
    CLV,

    /// Compare Accumulator
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Immediate (2/2), ZeroPage (2/3), ZeroPageX (2/4), Absolute (3/4),
    /// AbsoluteX (3/4), AbsoluteY (3/4), IndirectX (2/6), IndirectY (2/5)
    CMP,

    /// Compare X Register
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Immediate (2/2), ZeroPage (2/3), Absolute (3/4)
    CPX,

    /// Compare Y Register
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Immediate, ZeroPage, Absolute
    CPY,

    /// Decrement Memory
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: ZeroPage, ZeroPageX, Absolute, AbsoluteX
    DEC,

    /// Decrement X Register
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    DEX,

    /// Decrement Y Register
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    DEY,

    /// Exclusive OR with Accumulator
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Immediate, ZeroPage, ZeroPageX, Absolute, AbsoluteX, AbsoluteY, IndirectX, IndirectY
    EOR,

    /// Increment Memory
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: ZeroPage, ZeroPageX, Absolute, AbsoluteX
    INC,

    /// Increment X Register
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    INX,

    /// Increment Y Register
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    INY,

    /// Jump to Address
    ///
    /// Addressing Modes: Absolute, Indirect
    JMP,

    /// Jump to Subroutine
    ///
    /// Addressing Modes: Absolute
    JSR,

    /// Load Accumulator
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Immediate, ZeroPage, ZeroPageX, Absolute, AbsoluteX, AbsoluteY, IndirectX, IndirectY
    LDA,

    /// Load X Register
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Immediate, ZeroPage, ZeroPageY, Absolute, AbsoluteY
    LDX,

    /// Load Y Register
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Immediate, ZeroPage, ZeroPageX, Absolute, AbsoluteX
    LDY,

    /// Logical Shift Right
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Accumulator, ZeroPage, ZeroPageX, Absolute, AbsoluteX
    LSR,

    /// No Operation
    ///
    /// Addressing Modes: Implied
    NOP,

    /// Logical Inclusive OR with Accumulator
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Immediate, ZeroPage, ZeroPageX, Absolute, AbsoluteX, AbsoluteY, IndirectX, IndirectY
    ORA,

    /// Push Accumulator on Stack
    ///
    /// Addressing Modes: Implied
    PHA,

    /// Push Processor Status on Stack
    ///
    /// Addressing Modes: Implied
    PHP,

    /// Pull Accumulator from Stack
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    PLA,

    /// Pull Processor Status from Stack
    ///
    /// Addressing Modes: Implied
    PLP,

    /// Rotate Left
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Accumulator, ZeroPage, ZeroPageX, Absolute, AbsoluteX
    ROL,

    /// Rotate Right
    ///
    /// Affects flags: N, Z, C
    ///
    /// Addressing Modes: Accumulator, ZeroPage, ZeroPageX, Absolute, AbsoluteX
    ROR,

    /// Return from Interrupt
    ///
    /// Addressing Modes: Implied
    RTI,

    /// Return from Subroutine
    ///
    /// Addressing Modes: Implied
    RTS,

    /// Subtract with Carry
    ///
    /// Affects flags: N, V, Z, C
    ///
    /// Addressing Modes: Immediate, ZeroPage, ZeroPageX, Absolute, AbsoluteX, AbsoluteY, IndirectX, IndirectY
    SBC,

    /// Set Carry Flag
    ///
    /// Affects flags: C
    ///
    /// Addressing Modes: Implied
    SEC,

    /// Set Decimal Flag
    ///
    /// Affects flags: D
    ///
    /// Addressing Modes: Implied
    SED,

    /// Set Interrupt Disable
    ///
    /// Affects flags: I
    ///
    /// Addressing Modes: Implied
    SEI,

    /// Store Accumulator
    ///
    /// Addressing Modes: ZeroPage, ZeroPageX, Absolute, AbsoluteX, AbsoluteY, IndirectX, IndirectY
    STA,

    /// Store X Register
    ///
    /// Addressing Modes: ZeroPage, ZeroPageY, Absolute
    STX,

    /// Store Y Register
    ///
    /// Addressing Modes: ZeroPage, ZeroPageX, Absolute
    STY,

    /// Transfer Accumulator to X
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    TAX,

    /// Transfer Accumulator to Y
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    TAY,

    /// Transfer Stack Pointer to X
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    TSX,

    /// Transfer X to Accumulator
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    TXA,

    /// Transfer X to Stack Pointer
    ///
    /// Addressing Modes: Implied
    TXS,

    /// Transfer Y to Accumulator
    ///
    /// Affects flags: N, Z
    ///
    /// Addressing Modes: Implied
    TYA,
}
