Electronic – Usage of “initial” in Verilog module description

fpgatestbenchverilog

I'm writting a code and I have 2 dumb questions:

1- Is it a bad practice to use "initial" in the module description?

I'm asking this because I have a frequency divider with 2 signals (clk_in and clk_out). If I want to see the behaviour in simulation, I have to give an initial value to clk_out, otherwise clk_out will always keep as X.
Then, I used "initial" instead of using a reset signal.

2- Why the code without initializing the output works fine in the FPGA but it doesn't in simulation?

My code basically do this: Clk_out <= ~Clk_out;

Thanks in advance.

Best Answer

It is a common misconception that initial blocks cannot ever be synthesised.

In fact, for FPGAs, they can in most cases be synthesised. In fact the use of initial blocks is quite common. You can use them to set the power-on value of structures such as RAMs, ROMs, and registers.

This is not bad practice at all, and helps with both simulation and synthesis code.

In many cases with registers however, you are better off using a reset signal to control the value of the register. This is because it gives you the option to put the register in a known state at any point. If you only reset a partial group of registers in a circuit, you can end up with weird states existing.

In free-running circuitry such as your clock <= ~clock example, it is probably not necessary to include a reset, and using an initial value will help ensure that the simulation and synthesis behaviour match.


In terms of why your code doesn't work in simulation, it is because the simulation actually has four states, whereas synthesis really only has three.

The x (unknown) state is the default for signals which are not initialised in simulation. Unknown represents a condition where the simulator doesn't know what the value is, it could be a 1, or it could be a 0.

If you take an unknown value and invert it, you end up with another unknown value. As such your simulation will end up always showing x for the value, because it never knows where to start.

In synthesis code, this will not stop it running (*) - it will either be a 1 or a 0, and the FPGA will simply calculate the output based on whatever that value may be.


(*) The issue lies actually in the fact that you don't know how it will start. This is not a problem if you have simulated it to find out, but if your simulation fails, it can be hard to predict behaviours.

There are cases when having no initial value is not an issue - for example a data bus which has a valid signal. As long as the valid signal initialises to low to indicate the data bus is invalid, then it doesn't matter what value the data bus starts in. However for registers like the "launchMissile" variable, leaving it to chance whether that starts high or low is dangerous.