Skip to content
VLSI Mentor

VHDL · Chapter 9.8 · Finite State Machines

Safe FSMs and Illegal-State Recovery

An FSM has a finite set of legal states, but its state register can hold more bit patterns than that, the illegal states such as unused binary codes or any non-one-hot pattern in a one-hot machine. In normal operation the FSM never enters them, yet a single-event upset, a glitch, a metastable capture, or a reset problem can drive it into one, and a naive machine may then sit there forever. A safe FSM guarantees recovery, so from any state, including illegal ones, it returns to a known legal state. This lesson shows how to add that recovery for every unlisted state, why one-hot encodings have especially many illegal patterns, what the safe-FSM synthesis attribute does, and how to keep the synthesiser from optimising the recovery logic away as unreachable.

Foundation14 min readVHDLFSMSafe StateIllegal StateRecoveryReliability

1. Engineering intuition — plan for the state you should never be in

You design an FSM to move among its legal states, but the hardware can end up elsewhere: a cosmic-ray upset flips a state bit, a glitch or metastable capture lands the register on an unused code, or a reset issue leaves it undefined. If your transition logic only describes the legal states, the machine has no defined move from an illegal one — so it can freeze. A safe FSM anticipates this: it makes every possible state, legal or not, lead back to a known state (usually idle/reset). It is cheap insurance, and for anything that must not hang — safety, long-running, or radiation-exposed systems — it is mandatory.

2. Formal explanation — recovery for every state

safe_recovery.vhd
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
library ieee; use ieee.std_logic_1164.all;
type state_t is (IDLE, RUN, PAUSE, DONE);       -- 4 legal states
signal state, next_state : state_t;
 
nlogic : process (all)
begin
  next_state <= state;                          -- default: stay
  case state is
    when IDLE  => if go = '1' then next_state <= RUN; end if;
    when RUN   => if fin = '1' then next_state <= DONE; end if;
    when PAUSE => next_state <= RUN;
    when DONE  => next_state <= IDLE;
    when others => next_state <= IDLE;          -- SAFE RECOVERY: any illegal state → IDLE
  end case;
end process;

The when others => next_state <= IDLE; is the recovery: it defines a transition from any state the case did not explicitly list — which, for an enum that the tool may encode with spare codes, includes the illegal patterns. From any illegal state the machine returns to IDLE within a clock. Without it, an illegal state has no defined exit and the FSM can hang.

3. Production RTL — safe one-hot and the synthesis attribute

safe_fsm_controls.vhd
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
library ieee; use ieee.std_logic_1164.all;
-- (A) Tell the tool to build a SAFE FSM (recover from illegal states) via an attribute.
attribute fsm_safe_state : string;
attribute fsm_safe_state of state : signal is "reset_state";   -- recover illegal → reset state
-- (vendor attribute names vary; "safe_fsm"/"fsm_safe_state" select a safe implementation)
 
-- (B) For one-hot, an explicit check: a legal one-hot has exactly one bit set.
--     If 'state_oh' is ever NOT one-hot (zero or multiple bits), force recovery.
-- if (number of set bits in state_oh) /= 1 then next_state <= IDLE; end if;

What hardware does this become? With the safe-FSM attribute (or explicit when others), the synthesiser adds logic so any out-of-range or non-one-hot pattern transitions to the reset/idle state. For one-hot machines this matters most — a one-hot register has 2^N patterns but only N legal ones, so almost every pattern is illegal, and an upset is likely to produce an illegal (multi-hot or zero-hot) pattern that needs recovery.

4. Hardware interpretation — every state leads home

safe FSM recovering from illegal states to a known statelegal statesIDLE, RUN, PAUSE, DONEillegal statesunused codes / non-one-hotsafe recovery (whenothers)any illegal → IDLEknown state (IDLE)machine never hangsupset / glitchrecover12
A safe FSM gives every state, legal or illegal, a path back to a known state. Normal transitions move among the legal states; the safe recovery (when others, or the safe-FSM attribute) adds transitions from any illegal state — an unused binary code, or a non-one-hot pattern after an upset — to the reset/idle state. Without recovery, an illegal state has no defined exit and the machine can hang there. One-hot encodings have many illegal patterns, so they especially need recovery; the cost is a little extra next-state logic for guaranteed liveness.

5. Simulation interpretation — upset, then recover

An upset drives the FSM to an illegal state; safe recovery returns it to IDLE

8 cycles
An upset drives the FSM to an illegal state; safe recovery returns it to IDLEan upset forces the register to an ILLEGAL state (fault flagged)an upset forces theregister to an ILLEGALstate (fault flagged)safe recovery (when others → IDLE) returns the FSM to a known state next clocksafe recovery (when others→ IDLE) returns the FSM toa known state next clockclkstateRUNRUNILLEGALILLEGALIDLEIDLERUNRUNfault00110000t0t1t2t3t4t5t6t7
Something (an upset, glitch, or metastable capture) drives the state register into an illegal pattern. Because the FSM has safe recovery (when others => IDLE), the next clock returns it to IDLE rather than leaving it stuck. Without recovery, the machine could sit in the illegal state indefinitely — a hang that a safe FSM prevents by construction.

6. Debugging example — the recovery the tool deleted

Expected: the FSM recovers from illegal states. Observed: in the gate-level netlist the recovery is gone — the when others branch was optimised away — so an injected upset hangs the FSM. Root cause: the synthesiser proved the illegal states are unreachable in normal operation and removed the recovery logic as dead code; it does not know you want it for upset tolerance. Fix: use the vendor safe-FSM attribute (which tells the tool to keep/insert recovery) rather than relying on a when others it may delete; for critical FSMs, verify the recovery survives to the netlist (and consider explicit one-hot checks). Engineering takeaway: a when others recovery can be optimised away because it looks unreachable — enable the safe-FSM attribute to make the tool preserve illegal-state recovery, and confirm it in the netlist.

keep_the_recovery.vhd
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
-- The 'when others' may be removed as unreachable; the safe-FSM attribute tells the tool to keep recovery.
attribute fsm_safe_state of state : signal is "reset_state";
-- ... and still write the explicit recovery for simulation/intent:
when others => next_state <= IDLE;

7. Common mistakes & what to watch for

  • No illegal-state recovery. An upset can hang the FSM; add when others => <known state> (and the safe-FSM attribute).
  • Relying only on when others. The tool may delete it as unreachable; use the safe-FSM attribute to preserve recovery, and verify in the netlist.
  • Ignoring one-hot's many illegal states. One-hot registers have far more illegal than legal patterns; recovery (or a one-hot check) is especially important.
  • Recovering to a busy/unsafe state. Recover to idle/reset (a benign known state), not into the middle of an operation.
  • Assuming reset alone is enough. Reset fixes power-up, not a mid-operation upset; recovery handles illegal states that arise during running.

8. Engineering insight & continuity

A safe FSM treats illegal states as inevitable, not impossible: from any state, legal or not, it returns to a known one, guaranteeing the machine can never hang. The mechanism is a when others recovery plus the safe-FSM synthesis attribute that keeps the tool from optimising it away — essential for one-hot encodings and for any system that must not freeze. This is the reliability capstone of FSM design. The module's final lesson pulls together everything that can go wrong — the Common FSM Bugs — into a single catalog with fixes, before the curriculum moves to Packages and Reuse.

Standards & specifications

Governing standard
IEEE Std 1076 (VHDL)(opens IEEE in a new tab)

Defines the VHDL language — types, the simulation cycle, and the semantics a conforming analyser and simulator must implement. Synthesis restrictions and vendor coding rules are tool behaviour, not language rules.

This page also covers RTL structure, verification approach and debugging technique. Those are engineering practice built on the standard, not requirements the standard itself imposes.

Where this fits

Part of the VHDL curriculum.