What exactly do x and z values represent in Verilog?

Viewed 1364

The Verilog standard defines four types of bit values: 0, 1, x, and z where 0 means low, 1 means high, x means unknown, and z means an undriven net.

A couple of questions:

  1. Does x mean that we don't know if the value is 0 or 1? 0 or 1 or z? or that the value is just unknown and can be something else than 0, 1, or z?
  2. Since z represents an undriven net, can a reg type have a z bit? If so, what does it mean?
2 Answers

The value X means a number of things depending on what kind of signal you are referring to and how it got that value.

For a variable with a 4-state data data type, X is the default initial state, meaning its value is unknown and has the potential to be any value. This is a symbolic state as real hardware will be in a particular state 0 or 1 at any specific point in time. You can also assign variable to the value X because of some operation that you either don't-care what its value is, or want to consider that operation illegal. Synthesis tools use that don't-care information when optimizing your logic and it will produce deterministic logic.

Nets have values that are a resolution functions of one or more drivers or continuous assignments. The built-in net types resolves multiple drivers by looking at their drive strengths, highest strengths wins. When there is a conflict between equal strengths driving 0 and 1, a wire resolves the conflict with an X value. The absence of any strength is called the Z state.

It's possible for a variable to be assigned the X or Z state and have that value drive a net through a continuous assignment. If the wire is being driven with a stronger strength, that strong strength's value prevails.

Typically, x means that we don't know if the value is 0 or 1. I suppose it could also include z. I don't think it ever means anything other than 0/1/z.

x in simulation often means that the signal was not initialized to a 0 or a 1. This common if you are modeling a flip-flop without a reset.

Another common reason for an x is when a net is driven by multiple drivers (contention). If one is driving a 0 and the other a 1, the result is x.

Yes, a reg can have the value z. It is common to use procedural assignments to a reg. Here is a simple example of a tri-state driver:

module tb;

reg en = 0;
reg out;

always @* out = en ? 1 : 'z;

initial begin
    $monitor($time, " en=%b out=%b", en, out);
    #5 en = 1;
    #5 en = 0;
    #5 $finish;
end

endmodule

Prints:

               0 en=0 out=x
               5 en=1 out=1
              10 en=0 out=z

This could also be modeled using a continous assignment:

wire out = en ? 1 : 'z;

In both cases (reg and wire), the z means the same thing.

Related