//
test10v
module
light1(clock,key,style,light);
input
clock,key,style
;
//端口定义
output
[2:0]light;
reg
[2:0]
light
=3'b111
;
reg
clk
=
1;
parameter
cnt
=
24000000;
reg
[24:0]count;
always
@
(posedge
clock)
//分频计数
begin
if
(count
<
cnt)
count
=
count
+
25'b1;
else
begin
count
=
0;
clk
=
~
clk;
end
end
always
@
(posedge
clk)
//LED灯输出
begin
if
(!key)
//key键被按下
light
=
light;
//暂停
else
begin
if
(!style)
//style被按下
begin
if
(light==0)
light=3'b111;
//LED灯全部点亮时,重新熄灭再准备下次循环
else
light
=light>>1;
//LED灯右移
end
else
begin
if
(light
==3'b000)
//LED灯全部点亮时,重新熄灭再准备下次循环
light
=3'b111;
else
light
=
light<<1;
//LED灯左移
end
end
end
endmodule
这个程序我已经在Actel板上烧过了,没问题。如果还有什么问题应该是你的板不同或者工具不同,我是在libero_85上做的
一、C语言程序中存在的问题
1“for(i=0;i<7;i=i+2)”是“左移4次”而不是“左移3次”,i=0,i=2,i=4,i=6,当i=8时结束for循环。
2“LED=(LED<<2)|0x03;”的含义是:将LED左移2位后,将最低两位置1。
3“LED=(LED>>2)|0xc0;”的含义是:将LED右移2位后,将最高两位置1。
4两者结合,将“LED=(LED<<2)|0x03;”重复运行4次后,LED=0xff,其中不再存在值等于0的位。
之后无论“LED=(LED>>2)|0xc0;”还是“LED=(LED<<2)|0x03;”都不会再有值等于0的位产生。
看你的程序,发光二极管应该是低电平点亮,所以以后无论如何移位都不再有发光二极管点亮了。
5解决方法:将“for(i=0;i<7;i=i+2)”改成“for(i=0;i<3;i++)”即可。
二、反汇编实际含义的问题
对“LED=(LED<<2)|0x03;”的反汇编:
; 38: LED=(LED<<2)|0x03; // 左移2位,并设定最低两位元为11C:0x000D E5B0 MOV A,P1(0x90)
C:0x000F 25E0 ADD A,ACC(0xE0)
C:0x0011 25E0 ADD A,ACC(0xE0)
C:0x0013 4403 ORL A,#0x03
C:0x0015 F5B0 MOV P1(0x90),A
;
1C程序中有从LED取值的指令“=LED”,因为LED在宏定义中为P1口,所以其对应汇编指令为“MOV A,P1”。
2在单片机实验中,P1口控制LED,常用灌电流直接驱动的方法。
在这样的电路下,即使引脚被内置置0,其对应外部引脚实际上还是被上拉成了高电平。
3因此,读取P1口值时将得到0xff,故而“LED=(LED<<2)|0x03;”后LED将直接的到0xff,所以以后发光二极管都不会亮了。
4解决办法:先对某个自定义寄存器进行移位处理,最后再将结构赋值给P1口。
修改后的程序:
/主要是想让灯两个两个的亮,可是程序不知道为什么只执行一遍// ch03-3-3c - 霹雳灯实验程序 /
/
一、C语言程序中存在的问题
1“for(i=0;i<7;i=i+2)”是“左移4次”而不是“左移3次”,i=0,i=2,i=4,i=6,当i=8时结束for循环。
2“LED=(LED<<2)|0x03;”的含义是:将LED左移2位后,将最低两位置1。
3“LED=(LED>>2)|0xc0;”的含义是:将LED右移2位后,将最高两位置1。
4两者结合,将“LED=(LED<<2)|0x03;”重复运行4次后,LED=0xff,其中不再存在值等于0的位。
之后无论“LED=(LED>>2)|0xc0;”还是“LED=(LED<<2)|0x03;”都不会再有值等于0的位产生。
看你的程序,发光二极管应该是低电平点亮,所以以后无论如何移位都不再有发光二极管点亮了。
5解决方法:将“for(i=0;i<7;i=i+2)”改成“for(i=0;i<3;i++)”即可。
二、反汇编实际含义的问题
对“LED=(LED<<2)|0x03;”的反汇编:
;
38: LED=(LED<<2)|0x03; // 左移2位,并设定最低两位元为11
C:0x000D E5B0 MOV A,P1(0x90)
C:0x000F 25E0 ADD A,ACC(0xE0)
C:0x0011 25E0 ADD A,ACC(0xE0)
C:0x0013 4403 ORL A,#0x03
C:0x0015 F5B0 MOV P1(0x90),A
;
1C程序中有从LED取值的指令“=LED”,因为LED在宏定义中为P1口,所以其对应汇编指令为“MOV A,P1”。
2在单片机实验中,P1口控制LED,常用灌电流直接驱动的方法。
在这样的电路下,即使引脚被内置置0,其对应外部引脚实际上还是被上拉成了高电平。
3因此,读取P1口值时将得到0xff,故而“LED=(LED<<2)|0x03;”后LED将直接的到0xff,所以以后发光二极管都不会亮了。
4解决办法:先对某个自定义寄存器进行移位处理,最后再将结构赋值给P1口。
/
//==声明区============================================
#include <reg51h> // 定义8051暂存器之标头档,P2-17~19
#define LED P1 // 定义LED接至Port 1
//==子程序=============================================
/ 延迟函数,延迟约x 5ms /
//void delay(int x) // 延迟函数开始
void delay(unsigned char x) // 延迟函数开始
{
int i,j; // 声明整数变数i,j
for (i=0;i<x;i++) // 计数x次,延迟x 5ms
for (j=0;j<600;j++);// 计数600次,延迟5ms
} // 延迟函数结束
//==主程序============================================
main() // 主程序开始
{
unsigned char i; // 声明无号数字元变数i(占1Bytes)
unsigned char temp=0x03;
//(舍去)LED=0xfc; // 初值=1111 1100,只有最右1灯亮
while(1) /// 无穷循环,程序一直跑
{
for(i=0;i<3;i++)// 左移3次
{
delay(100); // 延迟100 5m=05s
//(舍去)LED=(LED<<2)|0x03; // 左移2位,并设定最低两位元为11
temp=temp<<2;
LED=~temp;
} // 左移结束,只有最左1灯亮
for(i=0;i<3;i++)// 右移3次
{
delay(100); // 延迟100 5m=05s
//(舍去)LED=(LED>>2)|0xc0; // 右移2位,并设定最高位元为11
temp=temp>>2;
LED=~temp;
} // 结束右移,只有最右1灯亮
} // while循环结束
} // 主程序结束
1、 当控制开关为0时,灯全灭;当控制开关为1时,从第一盏开始,依次点亮,时间间隔为1秒。期间一直保持只有一盏灯亮、其他灯全灭的状态。
2、 8盏灯依次亮完后,从第8盏开始依次灭,期间一直保持只有一盏灯灭、其他灯全亮的状态。
3、 当8盏灯依次灭完后,8盏灯同时亮同时灭,其时间间隔为05秒,并重复4次。
4、 只要控制开关为1,上述亮灯次序不断重复。
5、 用层次化设计方法设计该电路,编写各个功能模块的程序。
6、 仿真各功能模块,通过观察有关波形确认电路设计是否正确。
7、 完成电路设计后,用实验系统下载验证设计的正确性。
以上就是关于求Verilog语言编写的循环彩灯控制器全部的内容,包括:求Verilog语言编写的循环彩灯控制器、单片机彩灯控制、如何设计8路彩灯控制器等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)