Return to previous page Advance to next page
Verilog Reference Guide
Chapter 3: Structural Descriptions

Module Statements and Constructs

Foundation Express recognizes the following Verilog statements and constructs when they are used in a Verilog module.

Data declarations and assignments are described in this section. Module and gate instantiations are described in the “Module Instantiations” section of this chapter. Function definitions, task statements, and always blocks are described in the “Functional Descriptions” chapter.

Structural Data Types

Verilog structural data types include wire, wand, wor, tri, supply0, and supply1. Although parameter does not fall into the category of structural data types, it is presented here because it is used with structural data types.

You can define an optional range for all the data types presented in this section. The range provides a means for creating a bit vector. The syntax for a range specification follows.

[msb : lsb]

Expressions for most significant bit (msb) and least significant bit (lsb) must be non-negative constant-valued expressions. Constant-valued expressions are composed only of constants, Verilog parameters, and operators.

parameter

You can customize each instantiation of a module by using Verilog parameters. By setting different values for the parameter when you instantiate the module, you can cause constructions of different logic. For more information, see the “Parameterized Designs” section of this chapter.

A parameter symbolically represents constant values. The definition for a parameter consists of the parameter name and the value assigned to it. The value can be any constant-valued integer or Boolean expression. If you do not set the size of the parameter with a range definition or a sized constant, the parameter is unsized and defaults to a 32-bit quantity. Refer to the “Constant-Valued Expressions” section of the “Expressions” chapter for information about constant formats.

You can use a parameter wherever a number is allowed, except when you declare the number of bits in an assignment statement, which will generate a syntax error as shown in the following example.

parameter size = 4;
assign out = in ? 4'b000 :size'b0101; //syntax error

You can define a parameter anywhere within a module definition. However, the Verilog language requires that you define the parameter before you use it.

The following example shows two parameter declarations. Parameters TRUE and FALSE are unsized and have values of 1 and 0, respectively. Parameters S0, S1, S2, and S3 have values of 3, 1, 0, and 2, respectively, and are stored as 2-bit quantities.

parameter TRUE=1, FALSE=0;
parameter [1:0]S0=3,S1=1,S2=0,S3=2;

wire

A wire data type in a Verilog description represents the physical wires in a circuit. A wire connects gate-level instantiations and module instantiations. With the Verilog language, you can read a value from a wire from within a function or a begin...end block, but you cannot assign a value to a wire within a function or a begin...end block. (An always block is a specific type of begin...end block).

A wire does not store its value. It must be driven in one of two ways.

In the Verilog language, an undriven wire defaults to a value of Z (high impedance). However, Foundation Express leaves undriven wires unconnected. Multiple connections or assignments to a wire short the wires together.

In the following example, two wires are declared; a is a single-bit wire, and b is a 3-bit vector of wires. Its most significant bit (msb) has an index of 2, and its least significant bit (lsb) has an index of 0.

wire a;
wire [2:0] b;

You can assign a delay value in a wire declaration, and you can use the Verilog keywords scalared and vectored for simulation. Foundation Express accepts the syntax of these constructs, but they are ignored when the circuit is synthesized.

Note: You can use delay information for modeling, but Foundation Express ignores this delay information. If the functionality of your circuit depends on the delay information, Foundation Express might create logic with behavior that does not agree with the behavior of the simulated circuit.

wand

The wand (wired AND) data type is a specific type of wire.

In the following example, two variables drive the variable c. The value of c is determined by the logical AND of a and b.

module wand_test(a,b,c);
   input a,b;
   output c;

   wand c;

   assign c = a;
   assign c = b;

endmodule

You can assign a delay value in a wand declaration, and you can use the Verilog keywords scalared and vectored for simulation. Foundation Express accepts the syntax of these constructs, but they are ignored when the circuit is synthesized.

wor

The wor (wired OR) data type is a specific type of wire.

In the following example, two variables drive the variable c. The value of c is determined by the logical OR of a and b.

module wor_test(a, b, c);
   input a, b;
   output c;

   wor c;

   assign c = a;
   assign c = b;
endmodule

tri

The tri (three-state) data type is a specific type of wire. All variables that drive the tri must have a value of Z (high-impedance), except one. This single variable determines the value of the tri.

Note: Foundation Express does not enforce the previous condition. You must ensure that no more than one variable driving a tri has a value other than Z.

In the following example, three variables drive the variable out.

module tri_test (out,condition);
   input [1:0] condition;
   output out;

   reg a,b,c;
   tri out;

   always @ (condition) begin
    a = 1'bz; //set all variables to Z
    b = 1'bz;
    c = 1'bz;
     case (condition) //set only one variable to non-Z
      2'b00 : a = 1'b1;
      2'b01 : b = 1'b0;
      2'b10 : c = 1'b1;
     endcase
   end

   assign out = a; // make the tri connection
   assign out = b;
   assign out = c;
endmodule

supply0 and supply1

The supply0 and supply1 data types define wires tied to logic 0 (ground) and logic 1 (power). Using supply0 and supply1 is the same as declaring a wire and assigning a 0 or a 1 to it. In the following example, power is tied to logic 1 and gnd (ground) is tied to logic 0.

supply0 gnd;
supply1 power;

reg

A reg represents a variable in Verilog. A reg can be a 1-bit quantity or a vector of bits. For a vector of bits, the range indicates the most significant bit (msb) and least significant bit (lsb) of the vector. Both regs must be non-negative constants, parameters, or constant-valued expressions. The following example shows reg declarations.

reg x; // single bit
reg a,b,c; // 3 1-bit quantities
reg [7:0] q; // an 8-bit vector

Port Declarations

You must explicitly declare the direction (input, output, or bidirectional) of each port that appears in the port list of a port definition. Use the input, output, and inout statements, as described in the following sections.

input

An input is a type of wire and is governed by the syntax of wire. You declare all input ports of a module with an input statement. You can use a range specification to declare an input that is a vector of signals, as for input b in the following example. The input statements can appear in any order in the description but must be declared before they are used. The following is an example.

input a;
input [2:0] b;

output

Unless otherwise defined by a reg, wand, wor, or tri declaration, an output is a type of wire and is governed by the syntax of wire. You declare all output ports of a module with an output statement. An output statement can appear in any order in the description, but you must declare the output before you use it.

You can use a range specification to declare an output that is a vector of signals. If you use a reg declaration for an output, the reg must have the same range as the vector of signals. The following declaration is an example.

output a;
output [2:0]b;
reg [2:0] b;

inout

You can declare bidirectional ports with the inout statement. An inout is a type of wire and is governed by the syntax of wire. With Foundation Express, you can connect only inout ports to module or gate instantiations. You must declare an inout before you use it. The following declaration is an example.

inout a;
inout [2:0]b;

Continuous Assignment

If you want to drive a value onto a wire, wand, wor, or tri, use a continuous assignment to specify an expression for the wire value. You can specify a continuous assignment in two ways.

The following example shows two equivalent continuous assignments for wire a.

wire a;              // declare 
assign a = b & c;    // assign
wire a = b & c;      // declare and assign

The left side of a continuous assignment can be any of the following.

The right side of the continuous assignment statement can be any supported Verilog operator or any arbitrary expression that uses previously declared variables and functions. You cannot assign a value to a reg in a continuous assignment.

With Verilog, you can assign drive strength for each continuous assignment statement. Foundation Express accepts drive strength, but it does not affect the synthesis of the circuit. Keep this in mind when you use drive strength in your Verilog source.

Assignments are performed bit-wise, with the low bit on the right side assigned to the low bit on the left side.