1.顶层数码管显示模块
`timescale 1ns / 1ps ////////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 18:57:45 08/18/2019 // Design Name: // Module Name: dynamic_seg_top // Project Name: // Target Devices: // Tool versions: // Description: //实现简易时钟计数功能 // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // module dynamc_seg_top //---------------------<端口声明>--------------------------------------- ( input clk_50MHZ , //时钟,50Mhz input rst_n , //复位,低电平有效 output reg [ 7:0] seg_sel , //数码管位选 output reg [ 7:0] seg_data //数码管段选,即内容显示 ); //---------------------<信号定义>--------------------------------------- wire clk_1KHZ ; reg [3:0] data_tmp ; reg [7:0] cnt ; wire [23:0] data ; //---------------------------------------------------------------------- // 1k分频例化,扫描一个数码管时间为1ms //---------------------------------------------------------------------- CLK_DIV # ( .width(16), .cnt(50_000) ) uut( .clk_50MHZ(clk_50MHZ), .rst_n(rst_n), .clk_out(clk_1KHZ) ); //====================================================================== // //时,分,秒计数例化 // //====================================================================== clock_cnt clk_cnt_uut( .clk_50MHZ(clk_50MHZ), .rst_n(rst_n), .data(data) ); //---------------------------------------------------------------------- // 数码管扫描,8位循环扫描,频率为1k //---------------------------------------------------------------------- always @(posedge clk_1KHZ or negedge rst_n) begin if(!rst_n) seg_sel <= 8'b0111_1111; else if(seg_sel==8'b1111_1110) seg_sel <= 8'b0111_1111; else seg_sel <= ~(~seg_sel>>1); end //---------------------------------------------------------------------- // 位选,不同计数对应不同位选编码,也对应分割的不同数据 //---------------------------------------------------------------------- always @(*) begin case(seg_sel) 8'b0111_1111: data_tmp = data[ 3: 0] ; // 位1 8'b1011_1111: data_tmp = data[ 7: 4] ; // 位2 8'b1101_1111: data_tmp = 4'ha ; // 位3 8'b1110_1111: data_tmp = data[11:8] ; // 位4 8'b1111_0111: data_tmp = data[15:12] ; // 位5 8'b1111_1011: data_tmp = 4'hb ; // 位6 8'b1111_1101: data_tmp = data[19:16] ; // 位7 8'b1111_1110: data_tmp = data[23:20] ; // 位8 default: data_tmp = 4'b0000 ; endcase end //---------------------------------------------------------------------- // 段选,将不同分割数据进行段选编码,实验平台为2个4位一体共阳数码管 //---------------------------------------------------------------------- always @(*) begin case(data_tmp) 4'h0: seg_data = 9'hc0; 4'h1: seg_data = 9'hf9; 4'h2: seg_data = 9'ha4; 4'h3: seg_data = 9'hb0; 4'h4: seg_data = 9'h99; 4'h5: seg_data = 9'h92; 4'h6: seg_data = 9'h82; 4'h7: seg_data = 9'hf8; 4'h8: seg_data = 9'h80; 4'h9: seg_data = 9'h90; 4'ha: seg_data = 9'hbf;// 4'hb: seg_data = 9'hbf;//第三位和第六位显示时钟的分隔线 default:seg_data = 9'hc0; endcase end endmodule
2.时分秒计数模块
`timescale 1ns / 1ps ////////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 19:51:36 02/25/2020 // Design Name: // Module Name: clock_cnt // Project Name: // Target Devices: // Tool versions: // Description: // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // ////////////////////////////////////////////////////////////////////////////////// module clock_cnt ( input clk_50MHZ, input rst_n, output [23:0]data ); reg [7:0] second ;//时钟“秒” reg [7:0] minute ;//时钟“分” reg [7:0] hour ;//时钟“小时” wire clk_1HZ ; //---------------------------------------------------------------------- //-- 例化计数分频产生1HZ时钟 //---------------------------------------------------------------------- CLK_DIV # ( .width(28), .cnt(50_000_000) ) uut( .clk_50MHZ(clk_50MHZ), .rst_n(rst_n), .clk_out(clk_1HZ) ); //---------------------------------------------------------------------- //-- 秒计数,从0-59计数,1秒加一,到59清零 //---------------------------------------------------------------------- always @(posedge clk_1HZ or negedge rst_n) begin if(!rst_n) second<=8'd0; else if (second[3:0]==4'd9) begin second[3:0]<=8'd0; if(second[7:4]==4'd5) second[7:4]<=4'd0; else second[7:4]<=second[7:4]+4'd1; end else second[3:0]<=second[3:0]+4'd1; end //---------------------------------------------------------------------- //-- 分计数,从0-59计数,1分钟加一,到59清零 //---------------------------------------------------------------------- always @(posedge clk_1HZ or negedge rst_n) begin if(!rst_n) minute<=8'd0; else if ((second[3:0]==4'd9)&(second[7:4]==4'd5)) begin if(minute[3:0]==4'd9) begin minute[3:0] <=4'd0; if(minute[7:4]==4'd5) minute[7:4] <=4'd0; else minute[7:4] <=minute[7:4]+4'd1; end else begin minute[3:0]<=minute[3:0]+4'd1; end end else minute<=minute; end //---------------------------------------------------------------------- //-- 小时计数,从0-23计数,1小时加一,到23清零 //---------------------------------------------------------------------- always @(posedge clk_1HZ or negedge rst_n) begin if(!rst_n) hour<=8'd0; else if ((second[3:0]==4'd9)&(second[7:4]==4'd5)&(minute[3:0]==4'd9)&(minute[7:4]==4'd5)) begin if(hour[7:4]==4'd2) begin if(hour[3:0]==4'd3) begin hour[3:0] <=4'd0; hour[7:4]<=4'd0; end else begin hour[7:4]<=hour[7:4]; hour[3:0] <=hour[3:0]+4'd1; end end else begin if(hour[3:0]==4'd9) begin hour[3:0] <=4'd0; hour[7:4] <=hour[7:4]+4'd1; end else begin hour[3:0] <=hour[3:0]+4'd1; hour[7:4] <=hour[7:4]; end end end else hour<=hour; end assign data[3:0] =second [3:0];//将“秒”的个位数送到数码管第一位 assign data[7:4] =second [7:4];//将“秒”的十位数送到数码管第二位 assign data[11:8] =minute [3:0];//将“分“的个位数送到数码管第四位 assign data[15:12] =minute [7:4];//将”分”的十位数送到数码管第五位 assign data[19:16] =hour [3:0];//将“时“的个位数送到数码管第七位 assign data[23:20] =hour [7:4];//将”时”的个位数送到数码管第八位 endmodule
3.任意时钟分频模块
`timescale 1ns / 1ps ////////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 18:54:40 02/25/2020 // Design Name: // Module Name: CLK_DIV // Project Name: // Target Devices: // Tool versions: // Description: //任意时钟分频模块 // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // ////////////////////////////////////////////////////////////////////////////////// module CLK_DIV # ( parameter width = 28, parameter cnt = 50_000_000 ) ( input clk_50MHZ, input rst_n , output clk_out ); reg [width-1:0] cnt_p; reg cnt_n; reg clk_p; reg clk_n; //上升沿计数器,实现0-49_999_999计数 always@(posedge clk_50MHZ or negedge rst_n) begin if(!rst_n) cnt_p <= 1'b0; else if(cnt_p == (cnt-1)) cnt_p <= 1'b0; else cnt_p <= cnt_p + 1'b1; end //上升沿触发时钟分频,实现1HZ时钟输出 always@(posedge clk_50MHZ or negedge rst_n) begin if(!rst_n) clk_p<=1'b0; else if(cnt_p<(cnt>>1)) clk_p<=1'b0; else clk_p<=1'b1; end always@(negedge clk_50MHZ or negedge rst_n) begin if(!rst_n) cnt_n <= 1'b0; else if(cnt_n == (cnt-1)) cnt_n <= 1'b0; else cnt_n <= cnt_n + 1'b1; end always@(negedge clk_50MHZ or negedge rst_n) begin if(!rst_n) clk_n<=1'b0; else if(cnt_n<(cnt>>1)) clk_n<=1'b0; else clk_n<=1'b1; end wire clk1=clk_50MHZ; //当分频系数为1时,输出时钟 wire clk2=clk_p; //当分频系数为偶数时,输出等于clk_p wire clk3=clk_p&clk_n;//当分频系数为奇数时,输出等于clk_p&clk_n assign clk_out=(cnt==1)?clk1:(cnt[0]? clk2:clk3); endmodule
4.时分秒仿真testbench文件
`timescale 100ps / 1ps //////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 22:18:22 02/25/2020 // Design Name: clock_cnt // Module Name: C:/mydesign/dybamic_seg1/clk_tb.v // Project Name: dybamic_seg // Target Device: // Tool versions: // Description: // // Verilog Test Fixture created by ISE for module: clock_cnt // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // //////////////////////////////////////////////////////////////////////////////// module clk_tb; // Inputs reg clk_50MHZ; reg rst_n; // Outputs wire [23:0] data; // Instantiate the Unit Under Test (UUT) clock_cnt uut ( .clk_50MHZ(clk_50MHZ), .rst_n(rst_n), .data(data) ); initial begin // Initialize Inputs clk_50MHZ = 0; rst_n = 0; // Wait 100 ns for global reset to finish #10; rst_n = 1; #10; // Add stimulus here end always #1 clk_50MHZ=~clk_50MHZ; endmodule
5.显示模块仿真testbench文件
`timescale 1ns / 1ps //////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 15:11:16 02/26/2020 // Design Name: dynamc_seg_top // Module Name: C:/mydesign/dybamic_seg1/dy_segtb.v // Project Name: dybamic_seg // Target Device: // Tool versions: // Description: // // Verilog Test Fixture created by ISE for module: dynamc_seg_top // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // //////////////////////////////////////////////////////////////////////////////// module dy_segtb; // Inputs reg clk_50MHZ; reg rst_n; // Outputs wire [7:0] seg_sel; wire [7:0] seg_data; // Instantiate the Unit Under Test (UUT) dynamc_seg_top uut ( .clk_50MHZ(clk_50MHZ), .rst_n(rst_n), .seg_sel(seg_sel), .seg_data(seg_data) ); initial begin // Initialize Inputs clk_50MHZ = 0; rst_n = 0; // Wait 100 ns for global reset to finish #10; rst_n = 1; #10; // Add stimulus here end always #1 clk_50MHZ=~clk_50MHZ; endmodule