HDL for Sequential Circuits ENEL211 Digital Technology Lecture Outline • Latches and Flip-flops • Behavioural Control • Counters and Registers Gated D Latch module D_latch (Q,D,control); output Q; input D,control; reg Q; always @ (control or D) if (control) Q = D; //Same as: if (control = 1) endmodule D Flip-flop module D_FF (Q,D,CLK); output Q; input D,CLK; reg Q; always @ (posedge CLK) Q = D; endmodule Testing Flip-flops • Need to have flip-flop in known state at start of test – Add reset input module DFF (Q,D,CLK,RST); output Q; input D,CLK,RST; reg Q; always @(posedge CLK or negedge RST) if (~RST) Q = 1'b0; // Same as: if (RST = 0) else Q = D; endmodule Async vs Sync Reset • Reset can occur immediately (asynchronous) or at the next clock edge (synchronous). • Async is faster but synchronous often has advantages for system stability Asynchronous: always @(posedge CLK or negedge RST) if (RST) Q = 1'b0; // Same as: if (RST = 1) Synchronous: always @(posedge CLK) if (RST) Q = 1'b0; // Same as: if (RST = 1) T Flip-flop from D type • Characteristic Equation Q( n 1) Q( n ) T module TFF (Q,T,CLK,RST); output Q; input T,CLK,RST; wire DT; assign DT = Q ^ T ; //Instantiate the D flip-flop DFF TF1 (Q,DT,CLK,RST); endmodule JK Flip-flop from D type • Characteristic Equation Q( n 1) J .Q( n ) K .Q( n ) module JKFF (Q,J,K,CLK,RST); output Q; input J,K,CLK,RST; wire JK; assign JK = (J & ~Q) | (~K & Q); //Instantiate D flipflop DFF JK1 (Q,JK,CLK,RST); endmodule Behavioural Modelling • Represents circuits at functional and algorithmic level. • Use procedural statements similar in concept to procedural programming languages (e.g. C, Java), • Behavioural modelling is mostly used to represent sequential circuits. Procedural Blocks • Behavioural models place procedural statements in a block after the initial or always keywords. • The initial block executes once at the start of the simulation. • The always keyword takes a list of variables. The block of statements is executed whenever one of the variables changes in a continuous loop. Parallelism • Electronic circuits are inherently parallel. • Separate initial or always blocks are executed in parallel. • Some things must be done sequentially in order to have a deterministic result. • It is possible to control which statements within a block execute sequentially or in parallel. Multiple Statement Blocks • If there are multiple statements in a block they must be enclosed by begin .. end or by fork .. join. • Statements inside begin .. end are executed sequentially. • Statements inside fork .. join are executed in parallel. begin .. end is Sequential module initial_begin_end(); reg clk,reset,enable,data; initial begin $monitor("%g clk=%b reset=%b enable=%b data=%b", $time, clk, reset, enable, data); #1 clk = 0; #10 reset = 0; #5 enable = 0; #3 data = 0; Simulator Output #1 $finish; 0 clk=x reset=x enable=x data=x end 1 clk=0 reset=x enable=x data=x endmodule 11 clk=0 reset=0 enable=x data=x 16 clk=0 reset=0 enable=0 data=x 19 clk=0 reset=0 enable=0 data=0 fork .. join is Parallel module initial_fork_join(); reg clk,reset,enable,data; initial begin $monitor("%g clk=%b reset=%b enable=%b data=%b", $time, clk, reset, enable, data); fork #1 clk = 0; #10 reset = 0; #5 enable = 0; #3 data = 0; join #1 $display ("%g Terminating simulation", $time); $finish; Simulator Output end 0 clk=x reset=x enable=x data=x endmodule 1 clk=0 reset=x enable=x data=x 3 clk=0 reset=x enable=x data=0 5 clk=0 reset=x enable=0 data=0 10 clk=0 reset=0 enable=0 data=0 11 Terminating simulation Blocking and Nonblocking Assignment • Assignment using = is blocking: the next statement is blocked till it completes. – therefore sequential. • Assignment using <= is non-blocking: the next statement can start at the same time. – therefore parallel with the next statement. Race Conditions • With parallel execution it is easy to generate logic with race conditions and nondeterministic behaviour module race_condition(); reg b; initial begin b = 0; end initial begin b = 1; end endmodule Conditional Statements • if else • case if (reset) dff <= 0; else begin dff <= din; yy <=0; end always @ (a or b or c or sel) case (sel) 0 : y = a; 1 : y = b; 2,3 : y = c; default : $display("Error in SEL"); endcase Looping statement • forever – The forever statement needs to contain some timing statement(s) as it executed continuously. • repeat repeat (8) begin data = data << 1; data[0] = temp; end Looping statements • while while (data[0] == 0) begin loc = loc + 1; data = data >> 1; end • for for (i = 0; i < 256; i = i + 1) begin #1 $display(" Address = %g Data = %h",i,ram[i]); ram[i] <= 0; // Initialize the RAM with 0 end Universal Shift Register module shftreg (s1,s0,Pin,lfin,rtin,A,CLK,Clr); input s1,s0; //Select inputs input lfin, rtin; //Serial inputs input CLK,Clr; //Clock and Clear input [3:0] Pin; //Parallel input output [3:0] A; //Register output reg [3:0] A; always @ (posedge CLK or negedge Clr) if (~Clr) A = 4'b0000; else case ({s1,s0}) 2'b00: A = A; //No change 2'b01: A = {rtin,A[3:1]}; //Shift right 2'b10: A = {A[2:0],lfin}; //Shift left 2'b11: A = Pin; //Parallel load input endcase endmodule Ripple Counter module ripplecounter(count, reset, A0, A1, A2, A3); input count; input reset; output A0, A1, A2, A3; TFF T0(count, reset, A0); TFF T1(A0, reset, A1); TFF T2(A1, reset, A2); TFF T3(A2, reset, A3); endmodule T Flip-flop module TFF (T,RST,Q); input T, RST; output Q; reg Q; always @(negedge T or posedge RST) begin if (RST) begin Q = 1'b0; end else begin #2 Q = ~Q; end end endmodule Binary Counter module counter (Count,Load,IN,CLK,Clr,A,CO); input Count,Load,CLK,Clr; input [3:0] IN; //Data input output CO; //Output carry output [3:0] A; //Data output reg [3:0] A; assign CO = Count & ~Load & (A == 4'b1111); always @ (posedge CLK or negedge Clr) if (~Clr) A = 4'b0000; else if (Load) A = IN; else if (Count) A = A + 1'b1; else A = A; // no change endmodule