当前位置:   article > 正文

【FPGA】用Verilog语言实现流水灯实验

【FPGA】用Verilog语言实现流水灯实验

一、模块框图

在这里插入图片描述
包含两个输入信号:系统时钟(sys_clk)以及复位信号(sys_rst_n)。
一个输出信号:led_out (因有4个led灯组成流水灯,故位宽为4,每一个比特位控制一个led灯)

二、波形图

1、时钟与复位信号

在这里插入图片描述

2、计数器

因每一个流水灯点亮的时间为0.5s,板子频率为50Mhz(20ns)
0.5s = 5X10^8ns
故计数个数为 (5X10^8)/ 20 = 2.5x10^7
在这里插入图片描述

3、脉冲信号

当计数器计数到最大值减一时,保持一个时钟周期的高脉冲,其余时刻保持低电平
在这里插入图片描述

4、输出信号

当复位信号有效时,对其赋初值为 4’b1110 (第一个灯亮,其余三个灭),并在第一个周期内保持
检测到脉冲标志信号时,值变为4’b1101(第二个灯亮,其余三个灭),并在这一周期内保持
后面同理
在这里插入图片描述

5、理想结果

与led_out波形相对应,间隔为0.5s
在这里插入图片描述

三、代码部分

1、Verilog代码

(1)法1:拼接运算符

在这里插入图片描述

module water_led
#(
  parameter CNT_MAX = 25'd24_999_999   //声明计数最大值参数,24999999二进制为25位
)
(
input wire       sys_clk,
input wire       sys_rst_n,

output reg [3:0] led_out   //端口列表
);
reg [24:0] cnt;
reg cnt_flag;      //声明寄存器

always@(posedge sys_clk or negedge sys_rst_n)     //计数器赋值
    if(sys_rst_n == 1'b0)
	    cnt <= 25'd0;
	 else if (cnt == CNT_MAX)
	    cnt <= 25'd0;
	 else
	    cnt <= cnt + 25'd1;
		 
always@(posedge sys_clk or negedge sys_rst_n)    //脉冲标志信号赋值
    if(sys_rst_n == 1'b0)
	     cnt_flag <= 1'b0;
	 else if (cnt == (CNT_MAX - 25'd1 ))
	     cnt_flag <= 1'b1;
	 else
	     cnt_flag <= 1'b0;
		  
always@(posedge sys_clk or negedge sys_rst_n)  //输出信号赋值
    if(sys_rst_n == 1'b0)
	     led_out <= 4'b1110
	 else if(cnt_flag == 1'b1)
	 led_out <= {led_out[2:0],led_out[3]};   //拼接运算符(例如上一状态为1110,现状态为1101,将上一状态的后三位110放在现状态的前三位,
	 else                                    //上一状态的第一位1放在现状态的最后一位,再将110与1进行拼接运算,即可得到现状态1101)
	     led_out <=  led_out;
		 
endmodule
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38

其中拼接运算符详情见下:
在这里插入图片描述

(2)法2:移位运算符,再取反

先添加led_out_reg [3:0]寄存器
在这里插入图片描述
将输出信号赋值部分的代码进行如下修改,再进行取反
在这里插入图片描述

2、tb仿真代码

在这里插入图片描述

`timescale 1ns/1ns
module tb_water_led();  //端口列表
reg sys_clk;
reg sys_rst_n;

wire [3:0] led_out;     //变量声明

initial
    begin
	    sys_clk = 1'b1;              //赋初值
		 sys_rst_n <= 1'b0;
		 #20
		 sys_rst_n <= 1'b1;
	 end
	 
always #10 sys_clk = ~sys_clk;       //生成时钟

water_led                 //实例化
#(
     .CNT_MAX(25'd24)
)
water_led_inst
(
     .sys_clk(sys_clk),
	  .sys_rst_n(sys_rst_n),
	  
	  .led_out(led_out)
);

endmodule
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30

四、仿真波形

在这里插入图片描述
经分析,与开始手动绘制的波形图吻合,结果正确,此处不再上传上版验证结果。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/weixin_40725706/article/detail/630120
推荐阅读
相关标签
  

闽ICP备14008679号