The EDSAC Debugger uses a tracing simulator that operates by: fetching the simulated instruction; decoding it to save trace information; checking to see if the instruction is a branch, and updating the simulated program counter if it is; else placing the instruction in the middle of the simulator loop and executing it directly; and then returning to the top of the simulator loop.

As an aside, the 1951 paper on the EDSAC debugger contains a pretty complete description of a modern debugger...



From instruction-set simulation and tracing