Professional Documents
Culture Documents
Verilog Review: ECE 5745 Complex Digital ASIC Design Christopher Batten
Verilog Review: ECE 5745 Complex Digital ASIC Design Christopher Batten
Verilog Review: ECE 5745 Complex Digital ASIC Design Christopher Batten
• Behavioral Verilog
– Gate level module adder( input [3:0] A, B,
output cout,
– Register transfer level output [3:0] S );
wire c0, c1, c2;
• Parameterized Static
FA fa3( A[3], B[3], c2, cout, S[3] );
endmodule
Elaboration
• Greatest Common
Divisor
Value Meaning
0 Logic zero
1 Logic one
X Unknown logic value
Z High impedance, floating
An X bit might be a 0, 1, Z, or in transition. We can
set bits to be X in situations where we don’t care
what the value is. This can help catch bugs and
improve synthesis quality.
?
memory_req
instruction
instruction
small_net
ECE 5745 Complex Digital ASIC Design • Verilog Review • 4
Verilog includes ways to specify
bit literals in various bases
• Binary literals
– 8’b0000_0000
4’b10_11 – 8’b0xx0_1xx1
• Hexadecimal literals
Underscores
are ignored – 32’h0a34_def1
Base format
– 16’haxxx
(d,b,o,h) • Decimal literals
Decimal number – 32’d42
representing size in bits
We’ll learn how to
actually assign literals to
nets a little later
• Behavioral Verilog
– Gate level module adder( input [3:0] A, B,
output cout,
– Register transfer level output [3:0] S );
wire c0, c1, c2;
• Parameterized Static
FA fa3( A[3], B[3], c2, cout, S[3] );
endmodule
Elaboration
• Greatest Common
Divisor
endmodule
cout sum
Note the
Ports must have semicolon at the
a direction (or end of the port list!
be bidirectional)
and a bitwidth ECE 5745 Complex Digital ASIC Design • Verilog Review • 7
A Verilog module includes a module
name and a port list
Traditional Verilog-1995 Syntax
A B
module adder( A, B, cout, sum );
4 4
input [3:0] A;
input [3:0] B;
output cout;
adder output [3:0] sum;
endmodule
c
adder FA FA FA FA
cout S
adder FA FA FA FA
cout S
FA FA FA FA
FA FA FA FA
... ); [3:0] A, B,
module adder( input
output cout,
output [3:0] S );
wire c0, c1, c2;
FA fa0( A[0],
... );B[0], 1’b0, c0, S[0] );
FA fa1( A[1],
... );B[1], c0, c1, S[1] );
FA fa2( A[2],
... );B[2], c1, c2, S[2] );
FA fa3( A[3],
... );B[3], c2, cout, S[3] );
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 14
Verilog Review
• Data types
• Structural Verilog FA FA FA FA
• Behavioral Verilog
– Gate level module adder( input [3:0] A, B,
output cout,
– Register transfer level output [3:0] S );
wire c0, c1, c2;
• Parameterized Static
FA fa3( A[3], B[3], c2, cout, S[3] );
endmodule
Elaboration
• Greatest Common
Divisor
Manual
Low-level netlist
Gate Level V of primitive gates
Auto Place + Route
wire t0,
out,t1;
t0, t1;
assign t0
out = ~( (sel[1]
(t0 | sel[0])
& c) |&(~sel[1]
(t1 | ~sel[0])
& a) ););
assign t1 = ~( (sel[1] & d) | (~sel[1] & b) );
assign out
t0 = ~( (t0
(sel[1]
| sel[0])
& c) |&(~sel[1]
(t1 | ~sel[0])
& a) ););
endmodule
always @( a or b or c or d or sel )
begin
t0 = ~( (sel[1] & c) | (~sel[1] & a) );
t1 = ~( (sel[1] & d) | (~sel[1] & b) );
out = ~( (t0 | sel[0]) & (t1 | ~sel[0]) );
end
endmodule
The always block is reevaluated
whenever a signal in its
sensitivity list changes
always @( a or b or c or d or sel )
begin
t0 = ~( (sel[1] & c) | (~sel[1] & a) );
t1 = ~( (sel[1] & d) | (~sel[1] & b) );
out = ~( (t0 | sel[0]) & (t1 | ~sel[0]) );
end
endmodule
The order of these procedural
assignment statements does matter.
They essentially happen in sequentially!
always @( a or b or c or d or sel )
begin
t0 = ~( (sel[1] & c) | (~sel[1] & a) );
t1 = ~( (sel[1] & d) | (~sel[1] & b) );
out = ~( (t0 | sel[0]) & (t1 | ~sel[0]) );
end
endmodule
LHS of procedural assignments must be
declared as a reg type. Verilog reg is not
necessarily a hardware register!
always @( a or b or c or d or sel )
begin
t0 = ~( (sel[1] & c) | (~sel[1] & a) );
t1 = ~( (sel[1] & d) | (~sel[1] & b) );
out = ~( (t0 | sel[0]) & (t1 | ~sel[0]) );
end
endmodule
What happens if we accidentally
forget a signal on the sensitivity list?
always @( * )
begin
t0 = ~( (sel[1] & c) | (~sel[1] & a) );
t1 = ~( (sel[1] & d) | (~sel[1] & b) );
out = ~( (t0 | sel[0]) & (t1 | ~sel[0]) );
end
endmodule
Verilog-2001 provides special syntax to
automatically create a sensitivity list for
all signals read in the always block
endmodule
integer num_calls;
initial num_calls = 0; Initial statement
integer multiplier;
integer result; Variables of
always @(*)
begin
type integer
multiplier = in;
result = 1;
while ( multiplier > 0 )
begin
result = result * multiplier;
multiplier = multiplier - 1; Data dependent
end
while loop
out = result;
num_calls = num_calls + 1;
end
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 48
Delay statements should only be
used in test harnesses
module mux4
(
input a,
input b, Although this will add a delay for
input c, simulation, these are ignored in
input d, synthesis
input [1:0] sel,
output out
);
endmodule
assign out +
= ( fn == 2'd0 ) ? ( in0 + in1 )
: ( fn == 2'd1 ) ? ( in0 - in1 )
: ( fn == 2'd9 ) ? ( in1 >> in0 )
: ( fn == 2'd10 ) ? ( in1 >>> in0 ) –
: 32'bx;
endmodule >>
>>>
initial
begin
// This gets the program to load into memory from the command line
if ( $value$plusargs( "exe=%s", exe_filename ) )
$readmemh( exe_filename, mem.m );
else
begin
$display( "ERROR: No executable specified! (use +exe=<filename>)" );
$finish;
end
// Stobe reset
#0 reset = 1;
#38 reset = 0;
end
High-Level Behavioral
Designers usually use a mix
of all three! Early on in the
design process they might
use mostly behavioral
models. As the design is
Register Transfer Level refined, the behavioral
models begin to be replaced
by dataflow models. Finally,
the designers use automatic
Gate Level tools to synthesize a low-
level gate-level model.
• Behavioral Verilog
– Gate level module adder( input [3:0] A, B,
output cout,
– Register transfer level output [3:0] S );
wire c0, c1, c2;
• Parameterized
FA fa3( A[3], B[3], c2, cout, S[3] );
endmodule
Static Elaboration
• Greatest Common
Divisor
always @(*)
begin
case ( sel )
1’d0 : out = in0;
1’d1 : out = in1;
default : out = {WIDTH{1’bx}};
endcase
end
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 55
Parameters are bound during static
elaboration creating flexible modules
module vcERDFF_pf
#( parameter WIDTH = 1, Instantiation Syntax
parameter RESET_VALUE = 0 ) vcERDFF_pf#(32,32’h10) pc_pf
( (
input clk, .clk (clk),
.reset (reset),
input reset, .en (pc_enable),
input [WIDTH-1:0] d, .d (pc_mux_out),
input en, .q (pc)
output reg [WIDTH-1:0] q );
);
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 56
Generate blocks can execute loops and
conditionals during static elaboration
module adder ( input [3:0] op1,op2,
output cout,
output [3:0] sum );
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 57
Combining parameters + generate blocks
enables more powerful elaboration
module adder#( parameter WIDTH = 1 )
(
input [WIDTH-1:0] op1,op2,
output cout,
output [WIDTH-1:0] sum
); Use parameter for
wire [WIDTH:0] carry; loop bounds
assign carry[0] = 1’b0;
assign cout = carry[WIDTH];
genvar i;
generate
for ( i = 0; i < WIDTH; i = i+1 )
begin : ripple
FA fa( op1[i], op2[i], carry[i], carry[i+1] );
end
endgenerate
endmodule ECE 5745 Complex Digital ASIC Design • Verilog Review • 58
Generate statements are useful
for more than just module instantiation
module adder#( parameter WIDTH = 1 )
(
input [WIDTH-1:0] op1,op2,
output cout,
output [WIDTH-1:0] sum
);
Statically elaborating
wire [WIDTH:0] carry; many continuous
assign carry[0] = 1’b0;
assign cout = carry[WIDTH];
assignments
genvar i;
generate
for ( i = 0; i < WIDTH; i = i+1 )
begin : ripple
assign {carry[i+1],sum[i]} = op1[i] + op2[i] + carry[i];
end
endgenerate
endmodule
• Behavioral Verilog
– Gate level module adder( input [3:0] A, B,
output cout,
– Register transfer level output [3:0] S );
wire c0, c1, c2;
• Parameterized Static
FA fa3( A[3], B[3], c2, cout, S[3] );
endmodule
Elaboration
• Greatest Common
Divisor
initial
begin
// 3 = GCD( 27, 15 )
inA = 27;
inB = 15;
#10;
if ( out == 3 )
$display( "Test ( gcd(27,15) ) succeeded, [ %x == %x ]", out, 3 );
else
$display( "Test ( gcd(27,15) ) failed, [ %x != %x ]", out, 3 );
$finish;
end
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 63
Behavioral GCD model is written within a
single always block with C like structure
module gcdGCDUnit_behav#( parameter W = 16 )
(
input [W-1:0] inA, inB,
output [W-1:0] Y Our goal now is to design an RTL
);
hardware block which implements
reg [W-1:0] A, B, Y, swap;
integer done; this high-level behavior. What does
always @(*) the RTL implementation need?
begin
done = 0;
A = inA; B = inB;
State
while ( !done )
begin
if ( A < B )
swap = A;
Less-Than Comparator
A = B;
B = swap;
else if ( B != 0 ) Equal Comparator
A = A - B;
else
done = 1; Subtractor
end
Y = A;
end
endmodule
ECE 5745 Complex Digital ASIC Design • Verilog Review • 64
The first step is to carefully
design an appropriate port interface
operands_val result_val
operands_rdy result_rdy
operands_bits_A result_bits_data
operands_bits_B
clk reset
zero? lt
A = inA; B = inB;
A
while ( !done )
begin
if ( A < B )
swap = A;
A = B;
B B = swap;
else if ( B != 0 )
A = A - B;
else
done = 1;
end
Y = A;
zero? lt
A = inA; B = inB;
A
while ( !done )
begin
if ( A < B )
swap = A;
A = B;
B B = swap;
else if ( B != 0 )
A = A - B;
else
done = 1;
end
Y = A;
zero? lt
A = inA; B = inB;
A
while ( !done )
sub begin
if ( A < B )
swap = A;
A = B;
B B = swap;
else if ( B != 0 )
A = A - B;
else
done = 1;
end
Y = A;
A A B B
mux reg mux reg
sel en sel en B=0 A<B
zero? lt
A = inA; B = inB;
A
while ( !done )
sub begin
if ( A < B )
swap = A;
A = B;
B B = swap;
else if ( B != 0 )
A = A - B;
else
done = 1;
end
Y = A;
input clk, A A B B
sel en sel en B=0 A<B
// Data signals
input [W-1:0] operands_bits_A,
input [W-1:0] operands_bits_B, zero? lt
output [W-1:0] result_bits_data, A
sub
// Control signals (ctrl->dpath)
input A_en, B
input B_en,
input [1:0] A_mux_sel,
input B_mux_sel,
);
vcEDFF_pf#(W) A_pf
(
.clk (clk),
.en_p (A_en),
.d_p (A_mux_out),
.q_np (A)
);
operands_val
!( A < B ) & ( B = 0 )
WAIT :
if ( operands_val ) CALC
state_next = CALC;
endcase
end
A A B B
sel en sel en B=0 A<B
zero? lt Generic
Generic A Test
Test Source sub
Sink
B
Functional RTL
Model Model
Identical?