Procedural Assignment

LRM §9.2.

A procedural assignment updates the value of register data types.

Syntax:

[ delay ] register_name = [ delay ] expression;     // blocking
[ delay ] register_name <= [ delay ] expression;    // non-blocking

Description:

Procedural assignments are used for updating register data types and memory data types.

The expression in a blocking procedural assignment is evaluated and assigned when the statement is encountered. In a begin-end sequential statement group, execution of the next statement is blocked until the assignment is complete.

In a non-blocking procedural assignment, the expression is evaluated when the statement is encountered, and assignment is postponed until the end of the time-step. In a begin-end sequential statement group, execution of the next statement is not blocked and may be evaluated before the assignment is complete. A group of statements with a non-blocking assignment has similar functionality as a group of statements within a fork-join block.

The left-hand side of a procedural assignment should be one of the following:

When the right-hand side evaluates to a fewer bits than the left-hand side, the assignment to a reg does not sign-extend.

The evaluation of the assignment is delayed by the delay when the delay is specified before the register name. When the delay is specified before the expression, the expression is evaluated when the statement is encountered, and assigned in the time-step specified by the delay.

Example:

begin
  a = 0;
  #10 a = 1;
  #5 a = 2;
end             // time 0: a=0; time 10: a=1; time 15 (#10+#5): a=2;

begin
  a <= 0;
  #10 a <= 1;
  #5 a <= 2;
end            // time 0: a=0; time 5: a=2; time 10: a=1;

begin
  a <= b;
  b <= a;
end            // both assignments are evaluated before a or b changes

See also:

Continuous assignment, Expression, Net data type