012. Refactorización de los flags Zero y Negative

Extraer las actualizaciones compartidas de los flags Zero y Negative.

Lección 12 de 356 · tests/chapter_01_cpu/test_012_refactor_zero_and_negative_flags.py

Archivo a actualizar

emulator/cpu/cpu.py

Ubicaciones

CPU._update_zero_and_negative_flags
CPU.step, existing $A9 and $AD branches

Por qué existe este paso

Actualmente, la LDA inmediata y la absoluta repiten mutaciones idénticas de flags. Una única función auxiliar hace que el invariante sea ejecutable una sola vez y recibe el valor resultante de forma explícita, de modo que las instrucciones posteriores puedan reutilizarlo sin depender del acumulador A.

Implementación de ejemplo completa

ZERO_FLAG = 1 << 1
NEGATIVE_FLAG = 1 << 7


class CPU:
    def _update_zero_and_negative_flags(self, value: int) -> None:
        if value == 0:
            self.p |= ZERO_FLAG
        else:
            self.p &= ~ZERO_FLAG

        if value & NEGATIVE_FLAG:
            self.p |= NEGATIVE_FLAG
        else:
            self.p &= ~NEGATIVE_FLAG

    def step(self) -> None:
        opcode = self.fetch_byte()

        if opcode == 0xA9:
            self.a = self.fetch_byte()
        elif opcode == 0xAD:
            address = self.fetch_word()
            self.a = self.bus.read(address)
        else:
            raise NotImplementedError(
                f"Opcode {opcode:02X} not implemented"
            )

        self._update_zero_and_negative_flags(self.a)

Invariantes importantes

  • los flags se derivan del valor recibido, no implícitamente de cpu.a
  • solo cambian Z y N
  • el comportamiento existente de LDA permanece sin cambios tras la refactorización

Error común

Una refactorización no da permiso para cambiar el comportamiento. Los Tests 010–011 siguen siendo el contrato de comportamiento; este paso solo centraliza su mecanismo.

Fuera de alcance

  • sacar la lógica de direccionamiento de CPU.step
  • mover el comportamiento de LDA a instructions.py

Ejecutar esta lección

uv run pytest tests/chapter_01_cpu/test_012_refactor_zero_and_negative_flags.py -v