Important if you need your designs to cleanly reset every time.
Apologies, but many folks are still post "I use exactly this template of three top procedures in every new design entity:
begin -- process template if reset = '1' then init_all_regs; -- no port init required elsif rising_edge(clock) then update_process_regs; end if; update_output_ports; -- wires ok for reset or clk end process template; " This is only the most recent example, and seeing this asynchronous reset code over and over again is starting to worry me, particulary considering that some FPGA's may be in critical environments, where cleanly coming out of reset is vital.
Xilinx[Ken Chapman] suggests this is not the most efficient strategy for LUT utilization in
"The tools do not automatically analyze asynchronous set/reset paths." (I assume tools means Map/Place/Route)
This bears repeating. "The tools do not automatically analyze asynchronous set/reset paths."
Following that scary statement is a reference to the "Enable" and "Disable" constraints, which control timing checks over these two paths (among others):
"Asynchronous Set/Reset to output propagation delay" and "Synchronous Set/Reset to clock setup and hold checks"
But lo and behold! There is NO checking (according to cgd above) of the path:
"Asynchronous Set/Reset to clock setup and hold checks"
(I like the convention of calling "async reset" clear, and calling "async set" preset, leaving set/reset for the sync functions, and will try to stick with that for the rest of this discussion)
The clear pin may be released at various registers in a process with uncertain timing relative to clock, _even_ if the clear signal started out synchronous. This has the same potential for trouble as any other async input to a synchronous state machine, because clear is just another input after all. A one-hot state machine can go no-hot or many-hot; a binary coded (non-Gray) SM may enter an illegal state; or see Ray's counter example (which is _not_ a counter-example) at
I've modified my style to ALWAYS reset synchronously, using a sync reset (with considered exceptions for certain unique circuits):
process(clock) begin if RISING_EDGE(clock) then if reset = '1' then init_regs; -- the ones that need it. else [elsif enable = '1' then] -- I like this form, it's free update_process_regs; end if; end if; end process;
Sure, it means that reset has to be synchronized somewhere, and (egad, worse yet!) typing an extra "end if" and indenting a level deeper, but this is a small price to pay for designs that start up first time, every time.
To quote Ray: " Generally speaking, asynchronous resets are a very bad idea in FPGAs." Because this might be mis-interpreted, I'd clarify that and say even synchronous resets, if used as a clear function, are a bad idea. Write code to reset synchronously. Keep clear of that clear pin.
Regards to all, John