数字逻辑电路课程设计报告
姓名 姜楠
学号 201126100207
指导教师 贾立新
专业班级 计算机+自动化1101
学 院 计算机学院
提交日期 2013年 6月 6日
一、实验内容
1. 12进制计数器设计。
2. 数字频率计的设计。
二.12进制计数器设计
1.设计要求
用74LS192设计12进制加法计数器,计数值从01~12循环,用7段LED数码管显示计数值。用DEII实验板验证。
2.原理图设计
利用两个74LS192充当计数器的高位和低位,下图中左边的74LS192作为低位,右边的74LS192为高位.两片的输入端A,B,C,D均置数0,0,0,0,左边的74LS192输入频率为1kHZ的信号.
利用74LS47译码器,将传入的十进制信号直接翻译成7段显示码,输出接口接上7段显示管。
利用一个与非门实现十进制。当产生001011时设置清零端口有效
12进制加法计数器原理图如图1所示。
图1 12进制加法计数器原理图
3.操作步骤
.打开QuartusII软件,创建wizard,选择器件为CycloneIIEP2C35F672C8。新建 block Diagram/Schematic File,创建cnt12.bdf文件
. 将元器件74LS192,74LS47,与非门,输入输出引脚从library导入,连好图,修改输入输出引脚的名字。
进行全程编译,无误后启动"Assigment-Pin"菜单,配置引脚的location
分别为PIN-V13,PIN-V14,PIN-AE11,PIN-AD11,PIN-AC12,PIN-AB12,PIN-AF12.
在QuartusII软件选择"Tools"菜单下的"Programmer"命令。在下载之前,要进行硬件配置,在"Hardware Setting"中选择"USB-Blaster",将编程模式选择为"JTAG",并在"Program/Configure"复选框内打勾,便可点击"start"按钮,开始下载。
在FPGA上检验是否为12进制。
三.4位数字频率计设计
1.设计要求
设计4位数字频率计,测频范围0000~9999Hz。用DEII实验板验证。
2.数字频率计的工作原理
当闸门信号(宽度为1s的正脉冲)到来时,闸门开通,被测信号通过闸门送到计数器,计数器开始计数,当闸门信号结束时,计数器停止计数。由于闸门开通时间为1s,计数器的数值就是被测信号频率。为了使测得的频率值准确,在闸门开通之前,计数器必须清零。为了使显示电路稳定的显示频率值,计数器和显示电路之间加了锁存器,当计数器计数截止,将计数值通过锁存信号送到锁存器。
控制电路在时基电路的控制下产生三个信号:闸门信号,锁存信号和清零信号。
图2 数字频率计原理框图
图3 数字频率计原理框图工作时序
3.数字频率计顶层原理图设计
图中总共有四个不同的功能模块:CNT10,LATCH4,DECODER和CONTROL模块。
四个十进制计数器CNT10组成10000进制计数器,是频率计的测量范围达到0-9999Hz;
LATCH4模块用于锁存计数器计数结果;
DECODER模块将计数器输出的8421BCD码转换为7段显示码。
CONTROL模块为频率计的控制器,产生满足时序要求的控制信号。
图4 数字频率计顶层原理图
4.数字频率计底层模块仿真
(1)计数器模块仿真
Clk:时基信号
Clr:清零信号
Cs:片选信号,cs=1时才会计数。
图5 计数器模块仿真结果
(2)锁存器模块仿真
当le=1时将dd信号锁存到qq中。
图6 锁存器模块仿真结果
(3)显示译码模块仿真结果
将din传入的8421BCD码转换成7段显示码
图7 显示译码模块仿真结果
(4)控制模块仿真结果
控制电路在时基电路的控制下产生三个信号:闸门信号,锁存信号和清零信号。
图8 控制模块仿真结果
5.数字频率操作过程
1.打开QuartusII软件,创建wizard,选择器件为CycloneIIEP2C35F672C8。新建VHDL File,创建cnt10,latch4,decoder,control四个模块.
2. 编写VHDL代码.
CNT10:
library ieee; use ieee.std_logic_1164.all; use ieee.std_logic_unsigned.all; entity cnt10 is port(clk:in std_logic; clr:in std_logic; cs :in std_logic; qq :buffer std_logic_vector(3 downto 0); co :out std_logic); end cnt10; architecture one of cnt10 is begin process(clk,clr,cs) begin if (clr='1') then qq<="0000"; elsif (clk'event and clk='1') then if (cs='1') then if (qq=9) then qq<="0000"; else qq<=qq+1; end if; end if; end if; end process; process(qq) begin if (qq=9) then co<= '0'; else co<='1'; end if; end process; end; |
Latch4:
LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; USE IEEE.STD_LOGIC_UNSIGNED.ALL; ENTITY LATCH4 IS PORT(le: IN STD_LOGIC; dd: IN STD_LOGIC_VECTOR(3 DOWNTO 0); qq: OUT STD_LOGIC_VECTOR(3 DOWNTO 0)); END LATCH4; ARCHITECTURE one OF LATCH4 IS BEGIN PROCESS(le,dd) BEGIN IF (le='1') THEN qq<=dd; END IF; END PROCESS; END one; |
Decoder:
library ieee; use ieee.std_logic_1164.all; entity decoder is port(din:in std_logic_vector(3 downto 0); led7s:out std_logic_vector(6 downto 0) ); End; architecture one of decoder is begin process(din) begin case din is when "0000"=>led7s<="1000000"; when "0001"=>led7s<="1111001"; when "0010"=>led7s<="0100100"; when"0011"=>led7s<="0110000"; when"0100"=>led7s<="0011001"; when"0101"=>led7s<="0010010"; when"0110"=>led7s<="0000010"; when"0111"=>led7s<="1111000"; when"1000"=>led7s<="0000000"; when"1001"=>led7s<="0010000"; when"1010"=>led7s<="0001000"; when"1011"=>led7s<="0000011"; when"1100"=>led7s<="1000110"; when"1101"=>led7s<="0100001"; when"1110"=>led7s<="0000110"; when"1111"=>led7s<="0001110"; when others=>led7s<=null; end case; end process; end; |
Control:
library ieee; use ieee.std_logic_1164.all; entity control is port(clk: in std_logic; cs,clr,le: out std_logic); end control; architecture behav of control is signal current_state,next_state:std_logic_vector(3 downto 0); constant st0:std_logic_vector :="0011" ; constant st1:std_logic_vector :="0010"; constant st2:std_logic_vector :="0110"; constant st3:std_logic_vector :="0111"; constant st4:std_logic_vector :="0101"; constant st5:std_logic_vector :="0100"; constant st6:std_logic_vector :="1100"; constant st7:std_logic_vector :="1101"; constant st8:std_logic_vector :="1111"; constant st9:std_logic_vector :="1110"; begin com1:process(current_state) begin case current_state is when st0=>next_state<=st1; clr<='1'; cs<='0'; le<='0'; when st1=>next_state<=st2; clr<='0'; cs<='1'; le<='0'; when st2=>next_state<=st3; clr<='0'; cs<='1'; le<='0'; when st3=>next_state<=st4; clr<='0'; cs<='1'; le<='0'; when st4=>next_state<=st5; clr<='0'; cs<='1'; le<='0'; when st5=>next_state<=st6; clr<='0'; cs<='1'; le<='0'; when st6=>next_state<=st7; clr<='0' ; cs<='1'; le<='0'; when st7=>next_state<=st8; clr<='0'; cs<='1'; le<='0'; when st8=>next_state<=st9; clr<='0'; cs<='1'; le<='0'; when st9=>next_state<=st0; clr<='0'; cs<='0'; le<='1'; when others=>next_state<=st0; clr<='0'; cs<='0'; le<='0'; end case; end process com1; reg: process(clk) begin if (clk'event and clk='1') then current_state<=next_state; end if; end process reg; end behav; |
3.对各个子模块进行编译,若出现错误,则首先排查VHDL是否正确。
4.上一步成功编译后,再进行仿真。创建Vector Waveform File,确定仿真时间(End Time)和网格宽度(Grid Size),在列表处加入输入输出节点(Insert Node Or Bus),并配置输入波形,最后开始仿真(Start Simulation)。
5.仿真结果正确后,生成相应的模块符号,以便在顶层图中使用。
6.各个子模块完成后,创建fmeter.bdf.将各个子模块导入到文件中,并按照顶层原理图所示,正确布局和连接线路。设置fmeter.bdf为顶层并编译。
7.上一步正确后,开始分配引脚,打开Pin选项,为每一个Node设置Location,设置规则参考书本附录。
8.打开Programmer,将fmeter的配置下载到CycloneII芯片内,在FPGA面板上运行。检查是否出现错误,若没有,则实验顺利完成。
四.实验体会
- 碰到的问题
编写完VHDL代码后,对其编译,始终显示错误,检查代码无误,并重新创建wizard后,仍然无法通过编译。
解决:应当建立一个独立的文件夹,将文件存储在里面,否则,同级目录下出现其他不相关的文件,会影响编译。
将内容下载到FPGA后,无法正常运行。
解决:检查配置时发现,芯片型号配置错误,应该为CycloneIIEP2C35F672C8。
编写fmeter.bdf后,编译,但无法通过。
解决:检查错误时发现,存在多余的线头,部分连线没有真正连上。
- 实验收获
老师要求很严格,相比于其他专业,学生们只要从别人那里拷贝一下就可以顺利通过实验,我们的实验课不仅是在面包板上连线,而且还要学习如何使用Quartus软件,学习VHDL语言,利用FPGA来实现相应的功能。短短几次课学习到了很多知识。
首先,原先只学习软件知识,这几次实验使我对硬件描述语言有了初步认识,
拓展了对硬件的理解。
其次,提高了自身的学习能力和查错能力。很多时候,不知道接下来的步骤要如何完成,不知道自己完成的电路到底哪里出错,一心想着是不是我的仪器是坏的。最后在同学的帮助下,都顺利解决了。但过程却异常艰辛。看着同学的实验都验收了,自己的实验就是调试不对,心里急也没用,只能一步步检查。
- 建议
建议适时更新一下实验室配置,机器老了,应当及早维修。
而且应该为我们计算机学院单独配一个硬件实验室,而不是用其他学院的实验室。
电脑里有前人做实验留下的代码,有些人就这样用别人的成果水水地验收了。
建议及时清理硬盘。