diff --git a/src/index.html.ejs b/src/index.html.ejs
index a108dbe..e971be0 100644
--- a/src/index.html.ejs
+++ b/src/index.html.ejs
@@ -18,6 +18,7 @@
can input registers and memory as hex, unsigned decimal, or signed decimal by using the dropdowns in the editors. Use the
"Examples" dropdown to select a pre-made assembly program to run. While the demo is running, you can use the side pane
to view the current memory and registers. Labels and tooltips on the diagram will show the state of each wire and component.
+ You can use the ebreak
instruction to insert a breakpoint in the simulation.
You can view the source or contribute on GitHub. diff --git a/src/ui/SimulatorUI.tsx b/src/ui/SimulatorUI.tsx index 6457d20..8fe64ad 100644 --- a/src/ui/SimulatorUI.tsx +++ b/src/ui/SimulatorUI.tsx @@ -119,23 +119,31 @@ export default function SimulatorUI() { let nextState = state if (nextState == "unstarted") { // try to start if we are unstarted const started = start() // try to start, updates state to paused if success - if (started) nextState = (mode == "play" ? 'playing' : 'paused') + if (started) { + nextState = (mode == "play" ? 'playing' : 'paused') + } } if (["paused", "playing"].includes(nextState)) { // don't do anything if we are "done" or if start failed try { // step the simulation `count` times. We step multiple at once when playing at full speed to avoid rendering each tick - const done = updateSim(sim => { + nextState = updateSim(sim => { for (let i = 0; i < count && !sim.isDone(); i++) { sim.tick() + if (sim.isBreak()) break + } + + if (sim.isDone()) { + return "done" + } else if (sim.isBreak()) { + clearPlayInterval() + return "paused" + } else if (mode == "play") { + return "playing" + } else { + return "paused" } - return sim.isDone() }) - if (done) { - nextState = "done" - } else { - nextState = (mode == "play" ? 'playing' : 'paused') - } } catch (e: any) { // this shouldn't happen. nextState = "done" error(`Error in simulation:\n${e.message}`) @@ -190,7 +198,9 @@ export default function SimulatorUI() { link.remove(); } - useInterval(() => step("play", speed == 0 ? 1000 : 1), (state == "playing") ? speed : null) + const clearPlayInterval = useInterval(() => { + step("play", speed == 0 ? 1000 : 1) + }, (state == "playing") ? speed : null) return (