Verilog module cannot calculate a&b and a|b - verilog

I am creating the verilog module that calculate either one of a+b, a-b, a & b or a | b.
The problem is that it does calculate for a+b and a-b.
but it cannot calculate a & b and a | b and return nothing.
input [31:0] a, b;
input [2:0] op;
output [31:0] z;
output ex;
wire[31:0]a0,a1,a2,a3;
assign a0 = a & b;
assign a1 = a | b;
assign a2 = a + b;
assign a3 = a - b;
assign z=a0;
//assign z=a1;
//assign z=a2;
//assign z=a3;
endmodule
the module basically calculate a+b, a-b, a&b, and a|b and assign its calculated value to z.
And it does successfully calculate for a+b and a-b and put calculated value to z.
But for a&b and a|b, it doesn't assign anything to z.
How can I solve this?
Thank you very much if you can help me.

I'm sure it does assign something to z. The problem is that you are trying to assign too much to z.
Each assign statement represents some hardware, which in this case drives the wire z. So, you are driving z 4 times in parallel from 4 separate lumps of hardware. If you like, you have a short circuit. (Remember Verilog is a hardware description language. You are designing hardware here, not writing software. If you assign to a wire from more than one place, you have shorted the outputs of some lumps of hardware together.)
I notice there is an input [2:0] op. This looks like homework to me and I guess you have been asked to design an ALU. An ALU is a lump of hardware (combinational logic in this case) that can perform various operations on it's inputs (its operands), which in this case are a and b. Which operation it performs needs to be selected by some other control input, which in this case is almost certainly supposed to be op.
So, you need some code that tests op and drives z with either a+b, a-b, a&b or a|b. The obvious construct to me for this job is a case statement:
case (op)
3'b000:
z = // some expression, eg a + b, it depends on what op code 000 is supposed to mean
3'b001:
z = // some other expression here
// etc etc
default: // perhaps...
z = // ...something to drive z if none of the other branches are used
endcase
A case statement should go inside an always block. As I suspect this is homework, I won't feed you the answer, I'll let you work out how to do that.
Finally, I see that op is 3 bits wide. This suggests that you ALU has more than 4 different operations to carry out. I also see there is an ex output, which presumably needs to do something.

There's some confusion here. Your original posted code is fine; z will be assigned as you want. The other answer is incorrect - there are no multiple drivers; they're commented out. The delay suggestion is also incorrect - a delay will make no difference whatever to your logic.

Related

What exactly do x and z values represent in Verilog?

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:
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?
Since z represents an undriven net, can a reg type have a z bit? If so, what does it mean?
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.

Comparing two numbers without comparison operators in verilog

Two 8-bit inputs are fed to the comparator, and if first one is greater than second, they are supposed to be subtracted, else they are supposed to be added. But, > and < operators aren't supposed to be used to compare them.
So, I have written my logic as:
input[7:0] in1,in2;
output select;
assign select=(in1-in2)?0:1;
It is always subtracting, unless difference equals 0. If I use division, 0 cannot be an input or my program can crash. Any suggestions on how to solve this problem?
Thanks a lot for your time.
Remember that the leftmost bit of a negative number is aways 1. So you can use it to check the sign of the difference.
input[7:0] in1,in2;
output select;
wire [7:0] difference = in1-in2;
wire sign_of_difference = difference[7];
assign select = sign_of_difference? 0:1;

What are the uses of force - release statements?

From a hardware point of view, what do force and release statements model? What are the uses of these statements?
The force/release statements are generally used to aid in simulations.
One scenario is to avoid X-propagation in gate simulations. The RTL code sometimes contains registers without asynchronous resets. Although the RTL simulations will run cleanly, gate simulations often do not. Either the X's never get resolved, or they take so many cycles to resolve so as to make simulations take an impractical amount of time to run. By forcing and releasing a random known value into the register during reset, the simulation is allowed to proceed cleanly and complete in a timely manner.
Another scenario involves large counters. For example, to see a 32-bit counter roll over, it requires 4 billion cycles. Typically, you want it to roll over several times in one simulation. Again, this could take an impractically long time to simulate. The force/release can be used to deposit a random value into the counter close to the roll-over value.
Another scenario involves boosting code coverage results. It can be difficult to achieve 100% coverage on all metrics, especially when using IP which can not be modified. The force can be used to toggle an unused signal.
The force/release should be used sparingly and only when you are convinced it is valid to do so.
Based on IEEE Std 1364-2005, the force procedural continuous assignment statement shall override all procedural assignments to a variable or net. The release procedural statement shall end a procedural continuous assignment to a variable or net. The value of the variable shall remain the same until the variable is assigned a new value through a procedural assignment or a procedural continuous assignment.
For example:
module test;
reg a, b, c, d;
wire e;
and and1 (e, a, b, c);
initial begin
$monitor("%d d=%b,e=%b", $stime, d, e);
assign d = a & b & c;
a = 1;
b = 0;
c = 1;
#10;
force d = (a | b | c);
force e = (a | b | c);
#10;
release d;
release e;
#10 $finish;
end
endmodule
In the example above and gate and1 is patched to work as or gate. If you simulate it, you'd get following results:
Results:
00 d=0,e=0
10 d=1,e=1
20 d=0,e=0
Without force statement, for t = 10, e should be equal to 0 (since 1 & 0 & 1 = 0). Using force statement overrides result of and1 and force e = 1. But as soon as release is applied to e, the value is change to 0 (the functionality of and gate is restored).
In the example above you can also see that force/release can be applied both to regs (d) and wires (e). This statements are used in testbenches, when you want to force determined value in reg or wire.

Assigning values in Verilog: difference between assign, <= and =

I have just started learning Verilog and I've seen these three lines from different sources. I am confused about the difference between the three:
c <= a&b;
assign c = ~a;
c = 1'b0;
These lines seem to assign a value to c but what's the difference? Thanks.
1) <=non-blocking and is performed on every positive edge of clock. these are evaluated in parallel so no guarantee of order. An example of this would be a register.
2) assign =continual assignment to wire outside an always statement. value of LHS is updated when RHS changes.
3) =blocking assignment, inside always statements enforces sequential order.

How to implement a special selector

Is it possible to write a module with 3 wires a,b,c that would output either :
z (disconnected) if a=b=c=z
a if a=(0 or 1) and b=c=z
b if b=(0 or 1) and a=c=z
c if c=(0 or 1) and a=b=z
x (dont care) otherwise
In verilog?
If you have three nets all driving the same wire then this will get what you want in simulation:
module three_drive(
input a,
input b,
input c,
output d);
assign d=a;
assign d=b;
assign d=c;
endmodule
However, I don't know what the synthesis would do with that.
It sounds to me like what you really want is to take these three signals and short them together on the input to your FPGA.
If you don't care what the result is if no one is driving it, then nguthrie has the correct answer. If it needs to be x if it's not driven, then you can do:
module three_drive(
input a,
input b,
input c,
output d);
wire temp;
assign temp=a;
assign temp=b;
assign temp=c;
assign d = (temp === 1'bz) ? 1'bx : temp;
endmodule
The above is not synthesizable, but it would get the simulation behavior you are looking for.

Resources