基于VHDL的秒表.docx
《基于VHDL的秒表.docx》由会员分享,可在线阅读,更多相关《基于VHDL的秒表.docx(13页珍藏版)》请在冰豆网上搜索。
基于VHDL的秒表
内容
1、总体设计要求
具有启动停止功能;
计时器能显示0.01s的时间;
计时器最长计时时间为24h;
具有复位功能 在任何情况下 按复位键 秒表无条件清零;
2、系统功能描述
本次课程设计通过VHDL做的秒表主要有以下的功能:
(1)在下载到实验箱后,打开开始开关才能开始计时;
(2)在开始开关打开后,能够通过另一个开关进行暂停;
(3)再按下清零键后能够清零,并且是在任何条件下都能清零;
(4)能够精确到0.01秒,更加精确的计时
3、系统设计方案论述,画出顶层电路图及功能分割图,并说明之间的联系或功能。
先是将100进制计数器、60进制计数器、60进制计数器和24进制计数器连接,
将100进制计数器的进位接到60进制计数器的CLK输入端上,然后将60进制的进位连接到另一个60进制的CLK输入端上,然后将已将连接进位的60进制计数器的几位连接到24进制计数器的输入端口CLK上,24进制的仅为端悬空,这就是秒表的主体。
当100进制计数器进位端口为1时,与之相连的60进制计数器开始工作,当进位为0时停止工作,剩余两个计数器的工作原理与之相同。
将100进制计数器、两个60进制计数器和24进制计数器的en端口相连并连接到input得输入端口上,并且将他们的cir连接到一起也连接到input的输入端口上,这样就实现了暂停和清零的功能,并且秒表的精确度为0.01。
在100进制的输入端口处还剩下一个clk端口,将两个输入端口通过一个与门与之相连,其中一个接入clk信号,而另一个就可当做一个开关,实现开始的功能,并且能够暂停。
将100进制计数器、两个60进制的计数器和24进制计数器的输出端分别接到8选1的数据选择器的输入端上,并且按高低位接好,而八进制的选择功能是通过一个8进制的不管计数来实现的,所以在8选1的数据选择器的sel输入端端口接到8进制计数器的输出端上,而八进制的输入端口上,通过两个输入端input,一个接扫描频率,另一个通过一个开关来控制8进制的工作,并且清零端接1使它的清零作用失效。
在8选1数据选择器的输出端接到7段译码器上,而7段译码器的输出端分别接七个output输出端,并采用不同的名字。
这样一个秒表的功能就基本实现了。
为了让他能够更好地先是数字,我们采用3线8线译码器再进一步控制,将3线8线译码器的输入端s1接1,s2、s3接地,这是3线8线译码器考试工作的必要条件,将3线8线译码器剩下的输入端接到8进制计数器的输出端上,然后3线8线的输出端口分别接7个output输出端口,采用不同的字母命名。
这样就实现了秒表的功能。
其仿真图如下
4、各功能模块设计说明及源程序
100进制计数器
libraryieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entitycnt_99is
port(clk,en,cir:
instd_logic;
q0,q1:
bufferstd_logic_vector(3downto0);
co:
bufferstd_logic);
endcnt_99;
architecturertlofcnt_99is
signals1:
std_logic_vector(3downto0);
signals2:
std_logic_vector(3downto0);
begin
process(clk)
begin
if(clk'eventandclk='1')then
if(cir='0')then
s1<="0000";s2<="0000";co<='1';
elsif(en='1')then
if(s1="1001"ands2="1001")then
s1<="0000";s2<="0000";co<='1';
elsif(s2="1001")then
s2<="0000";s1<=s1+'1';co<='0';
elses2<=s2+'1';co<='0';
endif;
endif;
endif;
q0<=s1;q1<=s2;
endprocess;
endrtl;
这是100进制的源程序:
设计中包含了清零功能,并且当en输入信号为1时,100进制计数器开始工作,当clk的信号为1时,100进制计数器开始计数,当cir为0时,100进制计数器无条件清零,当数码管上显示99时,数码管清零,并且产生进位信号co为1,当满足数码管上最低位显示为9时,高位在原来的基础上加1,而低位则是清零,并且进位信号为0;当上述的条件都不满足时,最低位在原来的基础上加1。
60进制计数器
libraryieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entitycnt_59is
port(clk,en,cir:
instd_logic;
q0,q1:
bufferstd_logic_vector(3downto0);
co:
bufferstd_logic);
endcnt_59;
architecturertlofcnt_59is
signals1:
std_logic_vector(3downto0);
signals2:
std_logic_vector(3downto0);
begin
process(clk)
begin
if(clk'eventandclk='1')then
if(cir='0')then
s1<="0000";s2<="0000";co<='1';
elsif(en='1')then
if(s1="0101"ands2="1001")then
s1<="0000";s2<="0000";co<='1';
elsif(s2="1001")then
s2<="0000";s1<=s1+'1';co<='0';
elses2<=s2+'1';co<='0';
endif;
endif;
endif;
q0<=s1;q1<=s2;
endprocess;
endrtl;
这是60进制计数器的源程序:
设计中包含了清零功能,并且当en输入信号为1时,100进制计数器开始工作,当clk的信号为1时,60进制计数器开始计数,当cir为0时,60进制计数器无条件清零,当数码管上显示59时,数码管清零,并且产生进位信号co为1,当满足数码管上最低位显示为9时,高位在原来的基础上加1,而低位则是清零,并且进位信号为0;当上述的条件都不满足时,最低位在原来的基础上加1。
23进制计数器
libraryieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entitycnt_23is
port(clk,en,cir:
instd_logic;
q0,q1:
bufferstd_logic_vector(3downto0);
co:
bufferstd_logic);
endcnt_23;
architecturertlofcnt_23is
signals1:
std_logic_vector(3downto0);
signals2:
std_logic_vector(3downto0);
begin
process(clk)
begin
if(clk'eventandclk='1')then
if(cir='0')then
s1<="0000";s2<="0000";co<='0';
elsif(en='1')then
if(s1="0010"ands2="0011")then
s1<="0000";s2<="0000";co<='1';
elsif(s2="1001")then
s2<="0000";s1<=s1+'1';co<='0';
elses2<=s2+'1';co<='0';
endif;
endif;
endif;
q0<=s1;q1<=s2;
endprocess;
endrtl;
这是24进制计数器的源程序:
设计中包含了清零功能,并且当en输入信号为1时,100进制计数器开始工作,当clk的信号为1时,24进制计数器开始计数,当cir为0时,24进制计数器无条件清零,当数码管上显示23时,数码管清零,并且产生进位信号co为1,当满足数码管上最低位显示为9时,高位在原来的基础上加1,而低位则是清零,并且进位信号为0;当上述的条件都不满足时,最低位在原来的基础上加1。
8进制计数器
libraryieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entitycnt_8is
port(clk,RD,en:
instd_logic;
q:
bufferstd_logic_vector(2downto0));
endcnt_8;
architecturertlofcnt_8is
signals1:
std_logic_vector(2downto0);
begin
process(clk)
begin
if(clk'eventandclk='1')then
if(RD='0')then
s1<="000";
elsif(en='1')then
if(s1="111")then
s1<="000";
else
s1<=s1+'1';
endif;
endif;
endif;
q<=s1;
endprocess;
endrtl;
这是8进制计数器:
设计中包含了清零功能,并且当en输入信号为1时,8进制计数器开始工作,当clk的信号为1时,8进制计数器开始计数,当rd为0时,8进制计数器无条件清零,当计数器计数到8时,计数器清零,进入下一个循环。
8选1数据选择器
libraryieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entitymux8_1is
port(d0,d1,d2,d3,d4,d5,d6,d7:
instd_logic_vector(3downto0);
sel:
instd_logic_vector(2downto0);
y:
bufferstd_logic_vector(3downto0));
endmux8_1;
architecturertlofmux8_1is
begin
process(d0,d1,d2,d3,d4,d5,d6,d7,sel)
begin
caseselis
when"000"=>y<=d0;
when"001"=>y<=d1;
when"010"=>y<=d2;
when"011"=>y<=d3;
when"100"=>y<=d4;
when"101"=>y<=d5;
when"110"=>y<=d6;
when"111"=>y<=d7;
whenothers=>y<="0000";
endcase;
endprocess;
endrtl;
这是8选1数据选择器的源程序:
当输入信号为“000”时,选择d0作为输出
当输入信号为“001”时,选择d1作为输出
当输入信号为“010”时,选择d2作为输出
当输入信号为“011”时,选择d3作为输出
当输入信号为“100”时,选择d4作为输出
当输入信号为“101”时,选择d5作为输出
当输入信号为“110”时,选择d6作为输出
当输入信号为“111”时,选择d7作为输出
在其他情况下输出的信号为“0000”
这样就实现了8选1的功能。
七段译码器
libraryieee;
useieee.std_logic_1164.all;
entitybcd_7disis
port(bcdm:
instd_logic_vector(3downto0);
a,b,c,d,e,f,g:
outstd_logic);
endbcd_7dis;
architecturertlofbcd_7disis
signalw:
std_logic_vector(6downto0);
begin
process(bcdm)
begin
a<=w(6);b<=w(5);c<=w(4);d<=w(3);e<=w
(2);f<=w
(1);g<=w(0);
casebcdmis
when"0000"=>w<="1111110";
when"0001"=>w<="0110000";
when"0010"=>w<="1101101";
when"0011"=>w<="1111001";
when"0100"=>w<="0110011";
when"0101"=>w<="1011011";
when"0110"=>w<="1011111";
when"0111"=>w<="1110000";
when"1000"=>w<="1111111";
when"1001"=>w<="1111011";
whenothers=>w<="0000000";
endcase;
endprocess;
endrtl;
这是7段译码器的源程序
通过输入特定的信号来输出确定的信号,而这写确定的信号就确定的数码管上所显示的数据。
3线8线译码器
libraryieee;
useieee.std_logic_1164.all;
entitydecode3_8is
port(a:
instd_logic_vector(2downto0);
s1,s2,s3:
instd_logic;
y:
outstd_logic_vector(7downto0));
enddecode3_8;
architecturertlofdecode3_8is
signalind:
std_logic_vector(2downto0);
begin
ind<=a;
process(ind,s1,s2,s3)
begin
if(s1='1'ands2='0'ands3='0')then
caseindis
when"000"=>y<="00000001";
when"001"=>y<="00000010";
when"010"=>y<="00000100";
when"011"=>y<="00001000";
when"100"=>y<="00010000";
when"101"=>y<="00100000";
when"110"=>y<="01000000";
when"111"=>y<="10000000";
whenothers=>y<="XXXXXXX";
endcase;
else
y<="11111111";
endif;
endprocess;
endrtl;
这是3线8线译码器的源程序:
这次的课程设计中,3线8线译码器的主要做用主要是让数码管显示上循环,通过8进制计数器上的输入频率的加大,数码管显示的数循环的频率很快,能够使所有数码管上都能显示出数来,从而达到了秒表应该具有的效果。
5、设计实验过程及引脚锁定
这次实验的设计过程主要是从秒表的功能出发,通过精确的0.01,可知道这次实验需要100进制的计数器,而秒表还有分钟和小时,这也说明实验需要60进制和24进制的计数器,这些计数器的连接主要是这次是要的主体,在这几个计数器的连接过程中还需要实现清零、暂停和开始的功能。
这些功能的实现主要是在编写计数器程序中加入的输入端口的功能实现的,而通过连线,将100进制计数器、两个60进制计数器和24进制计数器连接成一个整体,由一个清零端口控制所有计数器的清零,一个开始端口控制100进制计数器的开始,而100进制计数器通过进位进而带动其余计数器的工作,将所有计数器的en端口连接到一个输入端口上,从而实现了秒表的暂停的功能。
秒表的主体实现了,剩下的主要是显示的问题了,通过编写一个8选1数据选择器和一个7段译码器,而8选1数据选择器的工作功能的实现是通过8进制计数器的工作来实现的,在编辑一个8机制计数器后,通过连接准确无误后,在数码管上实现时,只能够实现一个数,这时需要我们再编写一个3线8线译码器,通过3线8线译码器来实现所有数据都显示在数码管上,而3线8线译码器的工能也需要8进制的计数器的工作来实现,再编写3线8线译码器时设定了一个限制,就是当输入信号s1为1,s2,s3为0时3线8线译码器才能工作,从而所有的数在数码管上都完成了实现。
6、实验结果记录及讨论
将文件编译成功够下载带到实验箱,能够实现计数,清零,暂停和开始的功能,说明本次试验成功了。
7、心得体会
通过本次课程设计,首先是巩固了自己所学的知识,是一种整体上的把握,使自己能运用娴熟,其实是锻炼了自己的心理素质,这次课程设计的难度还是挺大的,自己在处错误后,先是找错误,在找不到错误后心情逐渐变得烦躁,到急躁,到无奈,再到找到错误后的那种喜悦,好像是自己重生了一样;然后就是我感到了集体的概念,首先从秒表上来说,秒表是由不同的模块构成的,各个模块的作用是微小的,自己有自己的功能,而将他们连接到一起后,就实现了秒表的功能,能够用于体育赛事的秒表的功能,这些功能的实现是各个模块共同作用的结果。
这就想到了我们的生活,如果我们团队每个人都发挥自己的作用,每个人对团队贡献自己的力量,那么这个团队是无敌的,大到一个班,一个民族,一个国家。
其实这次实验能够成功也离不了同学们的帮助,所谓当局者迷,旁观者清,当自己陷入到错误的怪圈中迷失方向时,同学们的帮助就是我的指向灯,这次实验也加深了同学们之间在学习上的交流。
然而,最辛苦的当属老师了,一共三个班,150名学生,老师无疑是最累的,为了能够使同学能够多学点知识,故意提高了难度,而在验收中虽然很严厉,但是我们知道老师是为了我们好。
这次课程设计收获了知识,收获了欢乐。
谢谢老师的指导,同学们的帮助!