A Verilog race condition occurs when two or more statements that are scheduled to execute in the same simulation time-step, would give different results when the order of statement execution is changed.
module race (out1, out2, clk, rst);
output out1, out2;
input clk, rst;
reg out1, out2;
always @(posedge clk or posedge rst)
if (rst) out1 = 0;
else out1 = out2;
always @(posedge clk or posedge rst)
if (rst) out2 = 1;
else out2 = out1;
endmodule
If the first always block executes first after a reset, both out1 and out2 will take on the value of 1. If the second always block executes first after a reset, both out1 and out2 will take on the value 0. This clearly represents a Verilog race condition.
Making multiple assignments to the same variable from more than one always block is a Verilog race condition, even when using nonblocking assignments.
One of the recommendations is to avoid driving variables from multiple sources.
The deadlock situation is one in which one process is waiting for the other process to enable it, which in turn will enable the source process. The code could be a syntactically correct implementation, and still have a deadlock situation. The scenario can happen in both synchronous and asynchronous designs. A simple asynchronous example has been illustrated in the following, to demonstrate how deadlock occurs.
module deadlock;
reg reg1, reg2;
initial
begin
reg1 = 1'b0;
wait @ (reg2==1'b1)
end
always @(reg1)
begin
if (reg1==1'b1)
reg2 = 1'b1;
end
endmodule
The above example is an illustration of the deadlock scenario, which can be difficult to capture in a larger implementation.
What is the difference between a vectored and a scalared net?
Both scalared and vectored are Verilog constructs used on multi-bit nets to specify whether or not specifying bit and part select of the nets is permitted. For example,
wire scalared [3:0] a;
wire vectored [3:0] b;
wire c, d;
// Syntax error to use a bit select of vectored net
assign b[1] = 1'b1;
// OK
assign a[1] = 1'b0;
Difference b/w assign, de-assign and force, release.
The procedural assign-deassign construct is intended to be used for modeling hardware behavior, but the construct is not synthesizable by most logic synthesis tools. The force-release construct is intended for design verification, and is not synthesizable.
What does it mean to “short-circuit” the evaluation of an expression?
Verilog supports numerous operators that have rules of associativity and precedence. In some of the expressions, the result of the expression can be evaluated early on, due to the precedence and influence to override the rest of the expression. In that case, the entire expression need not be evaluated. This is called short-circuiting and expression evaluation.
For example,
assign out = ((a>b) & (c|d));
If the result of (a>b) is false (1'b0), then tools can already determine that the result of the AND operation will be 0. Thus, there is no need to evaluate (c|d) and rest of the equation is short-circuited.
What are the pros and cons of using hierarchical names to refer to Verilog objects?
The top-level module is called the root module because it is not instantiated anywhere. It is the starting point. To assign a unique name to an identifier, start from the top-level module and trace the path along the design hierarchy to the desired identifier.
assign status = top.hub_top.hpie.status_reg;
Adv:
- It is easy to debug the internal signals of a design, especially if they are not a part of the top level pin out.
- Sometimes, during synthesis, these hierarchical names get renamed, depending upon the synthesis strategy and switches used, and hence, will cease to exist. In that case, special switches need to be added to the synthesis compiler commands, in order to maintain the hierarchical naming.
- If the Verilog code needs to be translated into VHDL, the hierarchical names are not translatable.
Yes. Verilog supports the operation by using two astrices, back to back like,
assign out = (in ** 5);