Verilog for Combinational Circuits
Verilog includes ways to specify bit lit l i various bases literals in i b
Binary literals
4b10_11
Underscores are ignored Base format (d,b,o,h) Decimal number representing size in bits
8b0000_0000 8b0xx0_1xx1
Hexadecimal literals
32h0a34_def1 16haxxx 16 haxxx
Decimal literals
32d42
Well learn how to actually assign literals to nets a little later
Verilog Basics
History of hardware design languages y g g g Data types Structural Verilog Functional Verilog
Gate level Register transfer level High-level behavioral
FA FA FA FA
module adder( input [3:0] A B A, B, output cout, output [3:0] S ); wire c0, c1, c2; FA fa0( A[0], B[0], FA fa1( A[1], B[1], FA fa2( A[2], B[2], FA fa3( A[3], B[3], endmodule 1b0, c0, c1, c2, c0, c1, c2, cout, S[0] S[1] S[2] S[3] ); ); ); );
A Verilog module includes a module name and a port list d t li t
A
4
B
4
adder
4
module adder( A, B, cout, sum ); input [3:0] A; input [3:0] B; output p cout; ; output [3:0] sum; // HDL modeling of // adder f dd functionality ti lit endmodule
cout
sum
Ports must have ( a direction (or be bidirectional) and a bitwidth
Note the semicolon at the end of the port list!
A Verilog module includes a module name and a port list d t li t
A
4
B
4
Traditional Verilog-1995 Syntax
module adder( A, B, cout, sum ); input [3:0] A; input [3:0] B; output cout; output [3:0] sum;
adder
4
ANSI C Style Verilog-2001 Syntax
module adder( input [3:0] A, input [ p [3:0] B, ] , output cout, output [3:0] sum );
cout
sum
A module can instantiate other modules creating a module hierarchy ti d l hi h
a cout b cin
module FA( input a, b, cin output cout, sum ); // HDL modeling of 1 bit // adder functionality endmodule
FA
c
A module can instantiate other modules creating a module hierarchy ti d l hi h
A B
adder
cout S
FA
FA
FA
FA
module adder( input [3:0] A, B, output cout, output [3:0] S ); wire c0, c1, c2; FA fa0( ... ); FA fa1( ... ); FA fa2( ... ); FA fa3( ... ); endmodule
A module can instantiate other modules creating a module hierarchy ti d l hi h
A B
adder
cout S
FA
FA
FA
FA
module adder( input [3:0] A, B, output cout, output [3:0] S ); wire c0, c1, c2; FA fa0( A[0] B[0] A[0], B[0], FA fa1( A[1], B[1], FA fa2( A[2], B[2], FA fa3( A[3], B[3], endmodule 1b0 1b0, c0, c1, c2, c0 c0, c1, c2, cout, S[0] S[1] S[2] S[3] ); ); ); );
Carry Chain
Verilog supports connecting ports by position and by name iti db
Connecting ports by ordered list gp y
FA fa0( A[0], B[0], 1b0, c0, S[0] );
Connecting ports by name (compact) gp y ( p )
FA fa0( .a(A[0]), .b(B[0]), .cin(1b0), .cout(c0), .sum(S[0]) );
Connecting ports by name
FA fa0 ( .a .b .cin .cout t .sum );
(A[0]), (B[0]), (1b0), (c0), ( 0) (S[0])
For all but the smallest modules, connecting ports by name yields clearer and less buggy code code.
Lets review how to turn our schematic diagram into structural Verilog di i t t t l V il
FA
FA
FA
FA
Lets review how to turn our schematic diagram into structural Verilog di i t t t l V il
FA
FA
FA
FA
input module adder( ... ); [3:0] A, B, output cout, output [3:0] S ); wire c0, c1, c2; FA f 0( A[0]) B[0] fa0( ... );B[0], A[0], FA fa1( ... );B[1], A[1], FA fa2( ... );B[2], A[2], FA fa3( ... );B[3], A[3], endmodule 1b0 1b0, c0, c1, c2, c0, 0 c1, c2, cout, S[0] S[1] S[2] S[3] ) ); ); ); );
Verilog Fundamentals
History of hardware design languages y g g g Data types Structural Verilog Functional Verilog
Gate level Register transfer level High-level behavioral
FA FA FA FA
module adder( input [3:0] A B A, B, output cout, output [3:0] S ); wire c0, c1, c2; FA fa0( A[0], B[0], FA fa1( A[1], B[1], FA fa2( A[2], B[2], FA fa3( A[3], B[3], endmodule 1b0, c0, c1, c2, c0, c1, c2, cout, S[0] S[1] S[2] S[3] ); ); ); );
Gate-level Verilog uses structural Verilog t V il to connect primitive gates t i iti t
module mux4( input a, b, c, d, input [1:0] sel, output out ); b d a c sel[1] sel[0] wire [1:0] sel_b; not not0( sel_b[0], sel[0] ); not not1( sel_b[1], sel[1] ); wire n0 n1, n2 n0, n1 n2, and and0( n0, c, and and1( n1, a, and and2( n2, d, and and3( n3, b, n3 b n3; sel[1] sel_b[1] sel[1] sel_b[1] sel b[1] ); ); ); );
wire x0, x1; nor nor0( x0, n0, n1 ); nor nor1( x1, n2, n3 ); wire y0, y1; or or0( y0, x0, sel[0] ); or or1( y1, x1, sel_b[0] ); nand nand0( out, y0, y1 ); out y0 endmodule out
So is this how we make latches d fli fl l t h and flip-flops? ?
module latch ( input clk, input d, output reg q ); always @( clk ) begin if ( clk ) d = q; end endmodule module flipflop ( input clk, input d, output q ); always @( posedge clk ) begin d = q; end endmodule
Edge-triggered always block