[FPGA] Verilog: Sequential Circuit Design | Binary Counter | Counter | Frequency Divider | Timing Constraints

Preface: The content of this chapter is mainly to demonstrate the circuit design, simulation, synthesis and download using Verilog language under Vivado

Example: Counters and Dividers

 ​​

  • Features: Using Xilinx Artix-7 XC7A35T chip 
  • Configuration method: USB-JTAG/SPI Flash
  • Up to 100MHz internal clock speed 
  • Memory: 2Mbit SRAM N25Q064A SPI Flash (the old model of the sample picture is N25Q032A)
  • General IO: Switch: x8LED: x16Button: x5DIP: x8 General expansion IO: 32pin
  • Audio and video/display: 7-segment digital tube: x8 VGA video output interface Audio audio interface 
  • Communication interface: UART: USB to UART Bluetooth: Bluetooth module 
  • Analog interface: DAC: 8-bit resolution XADC: 2-way 12bit 1Msps ADC

Table of contents

Ⅰ. Pre-requisite knowledge

0x00 binary counter

0x01 Use the IP core to construct a counter 

Ⅱ. Verilog implementation

0x00 divider

0x01 Timing constraints


Ⅰ. Pre-requisite knowledge

0x00 binary counter

A simple binary counter counts by repeatedly cycling through a binary sequence. Taking the two-bit addition counting as an example, each time the clock pulse signal clk is a rising edge, the counter will add 1 to the count value. Therefore, the count value (composed of Q1Q0) is 00, 01, 10, 11, 00, 11..., and repeats itself. In the waveform diagram in the figure, the following information is revealed:

[i] A two-bit counter, the range it can count is 0~3 (ie 22-1). Similarly, the range that an n bits counter can count is 0~2n-1.

[ii] If Q0 and Q1 are drawn out as separate signal lines, the waveform frequency obtained by Q0 and Q1 is 1/2 and 1/4 of the clock pulse signal clk, that is, the clk frequency of the clock pulse signal is divided by 2, divided 4. Therefore, the graphic counter is often called a divide-by-4 counter.

[iii] From the discussion above, it can be seen that the number of signals that can be obtained by an n bits counter is the result of dividing the frequency by 2n.

 Referring to the following source program, try to analyze its frequency division coefficient:

1.

module addcounter(clk,Q) ; 
input clk ;
output[1:0] Q ;
reg[1:0] Q ;
always @(posedge clk)begin
Q<=Q+1 ;
end
endmodule

2.

module counter3(clr,clk,Q)
input wire clr; input wire clk;
output reg[2:0] Q;
input wire [2:0] D;
assign D[2] = ~Q[2] & Q[1] & Q[0] | Q[2] & ~Q[1] | Q[2] & ~Q[0]
assign D[1] = ~Q[1] & Q[0] | Q[1] & ~Q[0]
assign D[0] = ~Q[0]
always @ (posedge clk or posedge clr) begin
  if(clr==1)  Q<=0;
  else   Q <=D
end
endmodule

General-purpose binary counters generally have more functions, such as up/down counting, preset initial value, synchronous clearing, pause, etc. 74LS161 is a commonly used preset 4-bit binary synchronous addition counter. Its function table is as follows:

enter

output

P

T

CP

D0

D1

D2

D3

Q0

Q1

Q2

Q3

0

0

0

0

0

1

0

D0

D1

D2

D3

D0

D1

D2

D3

1

1

1

1

count

1

1

0

Keep

1

1

0

Keep

0x01 Use the IP core to construct a counter 

(1) According to the principle and reference code of the above 74LS161, design the counting circuit in vivado:

module CNT161( input CR, input CP, input [3:0] D , input LD, input EP, input ET, output wire [3:0] Q);
wire [3:0] Din;
reg [3:0] Dout;
assign Din=D;
assign Q=Dout;
always@(posedge CP or negedge CR)  begin
if (CR==0)  Dout<=0;
else if  (LD==0)  Dout<=Din;
else if  (LD==1 && EP==0 && ET==0)  Dout<=Dout;
else if  (LD==1 && EP==0 && ET==1)  Dout<=Dout;
else if  (LD==1 && EP==1 && ET==0)  Dout<=Dout;
else if  (LD==1 && EP==1 && ET==1)  Dout<=Dout+1;
end
endmodule  

(2) The clock of the experimental board is 100MHZ, and the counter is used to construct the frequency division output 1H:

module slowClock(clk, reset, clk_1Hz);
input clk, reset;
output clk_1Hz;
reg clk_1Hz = 1'b0;  // provide initial condition for this register.
reg [27:0] counter;
// counter size calculation according to input and output frequencies
parameter sys_clk = 100000000;  // 50 MHz system clock
parameter clk_out = 1;  // 1 Hz clock output
parameter max = sys_clk / (2*clk_out); // max-counter size
always@(posedge reset or posedge clk)  begin
    if (reset == 1'b1)  begin
       clk_1Hz <= 0;
       counter <= 0;
    end
    else  begin
       counter <= counter + 1;
       if ( counter == max)  begin
          counter <= 0;
          clk_1Hz <= ~clk_1Hz;
       end
     end
end
endmodule   

Ⅱ. Verilog implementation

0x00 divider

Design code:


module slowClock(clk, reset,Q);
    input clk, reset;
    output [3:0] Q;
    reg [3:0] Q = 4'b0000;
    // provide initial condition for this register.
    reg [27:0] counter;
    // counter size calculation according to input and output frequencies
parameter sys_clk = 1;  
parameter clk_out = 1;  
parameter max = sys_clk / (2*clk_out); // max-counter size

    always@(posedge reset or posedge clk)  begin
        if (reset == 1'b1)  begin
        Q <= 0;
        counter <= 0;
        end
        else  begin
            counter <= counter + 1;
            if (counter == max)  begin
                counter <= 0;
                Q<=Q+4'b0001;
            end
        end
    end
endmodule

❗Note:

parameter sys_clk = 1;  
parameter clk_out = 1;  
parameter max = sys_clk / (2*clk_out); // max-counter size

It is written according to the frequency of the EGO1 board, and different boards can be set with different frequency divisions

Simulation code:

module sim_slowClock();
    reg clk ,reset;
    wire [3:0] Q;
    slowClock test(.clk(clk),.reset(reset),.Q(Q));
    initial clk=0;
    initial reset=1;
    always begin
        #10;
        clk=~clk;
        reset=0;
        end
endmodule

 Click "RTL ANALYSIS->Open Elaborated Design" in Vivado to view the synthesized logic circuit, as shown in the figure:

Simulation code:

  • It can be seen from the figure that the rising edge is valid and is an asynchronous circuit;
  • reset is active at high level, it is 1 at the beginning, and it is set to 0000;
  • It can be seen from the waveform diagram that it is divided by sixteen;

0x01 Timing constraints

Since a clock signal is required, timing constraints are also required.

[a] Select Synthesis > Synthesized Design > Edit Timing Constraints in the Flow Navigator.

 【b】Open the Timing Constraint interface and start timing constraints.

 【c】Double-click Clock->Create Clock on the left to enter the Create Clock interface, and enter clk_pin in the Clock name. Select the button on the right in Source objects.

 [d] Select I/O Ports in Find names of type in Specify Clock Source Object, click Find, and select the found cp, as shown in the figure:

Click Set when you're done making your selections. The dialog box switches to as shown in the figure:

Click ok to complete the clock creation, the results refer to the following figure:

 【e】Set Input Setup Delay, double-click Input->Input Setup Delay on the left, as shown in the figure:

Enter Set Input Delay and configure it as shown in the figure below: select clk_pin for Clock, rst for Objects, and 0 ns for Delay. Click OK after completing the settings.

[f] Next, set the Delay value specifies <min/max> delay, double-click Input->Input Setup Delay on the left.

Select Clock as clk_pin, Objects select rst, Delays value select -0.5 ns, and select Delay value specifies,

Delay is set to min. After completing the settings, click ok.

 [g] Next, set Output Delay, double-click Output->Set Output Delay on the left. Clock selects clk_pin, Objects selects all outputs, and the Delay value is set to 0ns.

 [h] After completing the above constraints, you can see the following constraint results in All Constraints. Select File->Save Constraints to save the set constraints.

 At this time, if you open the constraints in the Sources interface, you can see that constraints have been added to the XDC file.

 [i] Select Synthesized Design -> Report Timing Summary in Flow Navigator. And set the Path delay type to min_max in the Options tab.

 After synthesizing again, check the timing report. If you see red in some places in the report, it means that the requirements have not been met after the timing constraints. Then during Implementation, Vivado will automatically optimize the routing path to meet the constraint time set by the user. If it still cannot be satisfied in Implementation, you need to analyze the circuit for further constraints.

Guess you like

Origin blog.csdn.net/m0_66307842/article/details/128922249