一、按键按下实现LED点亮
当LED引脚输出低电平时LED点亮,
(1)代码实现如下
`timescale 1ns / 1ps
module myled(clk,rst_n,led);
input clk;
input rst_n;
output reg led;
always @(posedge clk or negedge rst_n)
begin
if(!rst_n)
led <= 0;
else
led <= 1;
end
endmodule
(2)基础语法要点:
在always里面被赋值必须是reg变量。
凡是在时序电路中被赋值的变量 必须是非阻塞赋值。always @ ( posedge clk or negedge rst_n)
凡是在组合电路中被赋值的变量 必须是阻塞赋值always @ ( *)
(3)Modelsim仿真测试文件。
//指定时间单位为1ns,精度为1ps
`timescale 1 ns/ 1 ps
module test_tb();
reg clk;
reg rst_n;
wire led;
//实例化myled,注意要带实例名子。
myled i1 (
.clk(clk),
.led(led),
.rst_n(rst_n)
);
initial
begin
$display("Running testbench");
clk=0;
rst_n=0;
#20 rst_n=1;
end
always #10 clk=~clk;
//always @(posedge clk)
//begin
//rst_n = ~rst_n;
//end
endmodule
再执行仿真,直接出来结果。
如上图所示,clk 10ns 翻转一次,rest_n初始化为0,20ns以后,变为1.
在条件“posedge clk or negedge rst_n”,即clk上升沿或者rst_n的下降沿,led变为1.即在clk上升沿变为1.
(3)Modelsim仿真变化
要求每个clk时,rst_n变化,再重写I测试激励文件。
`timescale 1 ns/ 1 ps
module test_tb();
reg clk;
reg rst_n;
wire led;
myled i1 (
.clk(clk),
.led(led),
.rst_n(rst_n)
);
initial
begin
$display("Running testbench");
clk=0;
rst_n=0;
#20 rst_n=1;
forever
begin
#20 rst_n=~rst_n;
end
end
always #10 clk=~clk;
endmodule
如下图,实际效果是clk上升沿或者rst_n的下降沿,led变化,如果rst_n为高,则为0.
注意,只有一个外部clk,即原来的两个always是不对的。翻转时,需要加在内部,使用forever语句。
//always @(posedge clk or negedge clk)
//always @(posedge clk)
//begin
//rst_n = ~rst_n;
//end