What is the assembly language command HALT used for ?

This stops the CPU until an interrupt occurs. Nintendo recommends using this command in your main game loop in order to save battery power while the CPU has nothing else to do.

When an interrupt occurs while in HALT, the CPU starts back up and pushes the Program Counter onto the stack before servicing the interrupt(s). Except it doesn't push the address after HALT as one might expect but rather the address of HALT itself.

HALT operates differently depending on whether the Interrupt Master Enable (IME) is set or reset. Assembly command EI sets IME to 1. Assembly command DI resets IME to 0.

IME = 1 -



     HALT stops the CPU until the register IF ($ff0f) &

    register IE ($ffff) when logically ANDed together

    have a non-zero result.



     HALT will only start the CPU upon a 0 to 1 transition

    of one of the bits of the non-zero result. (i.e. Pending

    interrupts that occurred before HALT was executed will

    not terminate HALT.)





IME = 0 -



    [$ff0f].AND.[$ffff] = 0 :



        HALT is aborted. Next instruction is executed normally.



         If IME is set to 1 at a later time then a halt condition

        will occur one instruction after IME is set to 1 to complete

        the halt that was not allowed to finish earlier.



    [$ff0f].AND.[$ffff] > 0 :



         HALT is aborted. The first byte of the next instruction

        after HALT is read. The Program Counter (PC) fails to

        increment to the next memory location. As a results, the

        first byte after HALT is read again. From this point on

        the Program Counter once again operates normally.



         If IME is set to 1 at a later time then a halt condition

        will occur one instruction after IME is set to 1 to complete

        the halt that was not allowed to finish earlier.


Nintendo also recommends that you put a NOP after HALT commands. The reason for this is that the Program Counter will not increment properly (CPU bug) if you try to do a HALT while IME = 0 and an interrupt is pending. A single-byte instruction immediately following HALT will get executed twice if IME = 0 and an interrupt is pending. If the instruction following HALT is a multi-byte instruction then the game could hang or registers could get scrambled.

IME is set to 1 even if the assembly instruction EI is executed immediately before the HALT instruction.

Later versions of the RGBASM compiler automatically add a NOP after HALT.