This article does not cite any sources. (September 2011) (Learn how and when to remove this template message)
When a system is instructed to single-step, it will execute one instruction and then stop. The contents of registers and memory locations can be examined; if they are correct, the system can be told to go on and execute the next instruction. The Intel 8086 Trap Flag and type-1 interrupt response make it quite easy to implement a single-step feature in an 8086-based system. If the Trap Flag is set, the 8086 will automatically do a type-1 interrupt after each instruction executes. When this happens, the CPU pushes the flag register on the stack then does a type-1 interrupt.
The 8086 has no instruction to directly set or clear the trap flag. Instead, the entire status register (known as the 16-bit Flags Register in Real Mode, the 32-bit EFlags Register in Protected Mode, or the 64-bit RFlags Register in Long Mode) must be addressed by pushing it on the stack, changing the Trap Flag bit as desired, and then popping the value off the stack and back into the Flag Register. The easiest way to do this is:
PUSHF ; Push flags on stack MOV BP, SP ; Copy SP to BP for use as index OR WORD PTR[BP+0], 0100H ; Set bit 8, the Trap flag POPF ; Copy the newly modified value back to the Flags Register
The Trap Flag is usually used in conjunction with a type-1 interrupt handler which will allow viewing of the register values and memory addresses of the program being single-stepped. That Interrupt Service Routine might look something like:
Int1ServiceRoutine: ; Stack: Ret, Flags PUSHA ; Stack: Ret, Flags, AX, CX, DX, BX, SP, BP, SI, DI PUSH DS ; Stack: Ret, Flags, AX, CX, DX, BX, SP, BP, SI, DI, DS PUSH ES ; Stack: Ret, Flags, AX, CX, DX, BX, SP, BP, SI, DI, DS, ES ... the rest of the ISR code would go here, and should only use general purpose registers to avoid having to save and restore the FPU state MOV BP, SP ; Stack: Ret, Flags, AX, CX, DX, BX, SP, BP, SI, DI, DS, ES MOV BP, [BP+10] ; Copy the value of SP on the stack to the BP register for use as an index OR WORD PTR[BP+0], 0100H ; Set the Trap flag in the stored Flag register POP ES ; Stack: Ret, Flags, AX, CX, DX, BX, SP, BP, SI, DI, DS POP DS ; Stack: Ret, Flags, AX, CX, DX, BX, SP, BP, SI, DI POPA ; Stack: Ret, Flags IRET ; continue execution for ONE instruction, after which this ISR gets called again
To set the trap flag, simply replace the OR instruction in the preceding sequence with the instruction:
- AND WORD PTR[BP+0], 0FEFFH
The trap flag is automatically cleared by the 8086 when a type-1 interrupt occurs so that the interrupt handler itself will not be single-stepped. The initial value of the flags register which contains the trap flag is preserved on the stack and restored upon exiting the handler so that another type-1 interrupt will be generated upon completion of the next instruction.