|
0.jpg (102.81 KB, 下載次數(shù): 89)
下載附件
2019-7-4 23:24 上傳
03TL%%Y[K5ZC@Z2FC74}89Y.png (57.99 KB, 下載次數(shù): 94)
下載附件
原理圖鏈接
2019-7-3 17:32 上傳
VHDL硬件描述語言是一門技術(shù)性、應(yīng)用性很強(qiáng)的學(xué)科,學(xué)生不但能夠?qū)⒄n堂上學(xué)到的理論知識(shí)與實(shí)際應(yīng)用結(jié)合起來,而且能夠?qū)Ψ治、解決實(shí)際問題的數(shù)字電路問題進(jìn)一步加深認(rèn)識(shí),為今后能夠獨(dú)立進(jìn)行某些數(shù)字應(yīng)用系統(tǒng)的開發(fā)設(shè)計(jì)工作打下一定的基礎(chǔ)。本次的設(shè)計(jì)是基于VHDL的實(shí)時(shí)時(shí)鐘電路設(shè)計(jì),完成時(shí)、分、秒的顯示及調(diào)整設(shè)置功能。設(shè)計(jì)利用VHDL語言自頂向下的設(shè)計(jì)理念,突出其作為硬件描述語言的良好的可讀性、可移植性以及易于理解等優(yōu)點(diǎn)。通過QuartusII5.1和QuartusII12.1軟件完成仿真、綜合。程序下載到FPGA芯片后,可用于實(shí)際的數(shù)字鐘顯示。
2. 主要問題
進(jìn)行實(shí)驗(yàn)的過程中有許多的問題,一開始不知道原理,對(duì)程序無從下手;編寫過程中有語和定義錯(cuò)誤,在模塊調(diào)用時(shí)出現(xiàn)重復(fù);不知道如何分配管腳以致調(diào)試錯(cuò)誤。在分頻模塊的順序添加上,在計(jì)時(shí)模塊的小時(shí)分鐘調(diào)節(jié)上,數(shù)碼管的譯碼也遇到了問題。
3. 解決方法
在向老師和同學(xué)請(qǐng)教,查詢相關(guān)資料以及網(wǎng)上查找以后,上述問題得以解決。
4. 最終結(jié)果
此次設(shè)計(jì)的邏輯結(jié)構(gòu)主要由分頻、計(jì)數(shù)和譯碼顯示三個(gè)模塊構(gòu)成。分頻模塊將50MHz系統(tǒng)基準(zhǔn)時(shí)鐘分頻產(chǎn)生時(shí)鐘信號(hào),由輸入端控制輸出時(shí)鐘信號(hào),有正常的計(jì)數(shù)功能。數(shù)字時(shí)鐘計(jì)時(shí)工作模塊,計(jì)時(shí)模塊對(duì)1Hz的時(shí)鐘信號(hào)進(jìn)行計(jì)時(shí),分為時(shí)、分、秒三個(gè)部分;最后通過主模塊調(diào)用三個(gè)子模塊函數(shù)實(shí)現(xiàn)整體設(shè)計(jì)要求。
實(shí)時(shí)時(shí)鐘電路設(shè)計(jì):
(1) 設(shè)計(jì)一個(gè)數(shù)碼管實(shí)時(shí)顯示時(shí)、分、秒的數(shù)字時(shí)鐘(24小時(shí)顯示模式);
(2) 為了演示方便,應(yīng)具有分鐘、小時(shí)快進(jìn)功能;
(3) 時(shí)、分、秒的設(shè)置功能(選作)。
2 方案分析與總體設(shè)計(jì)
本次的設(shè)計(jì)是基于VHDL的實(shí)時(shí)時(shí)鐘電路設(shè)計(jì),完成時(shí)、分、秒的顯示及調(diào)整功能。此次設(shè)計(jì)的邏輯結(jié)構(gòu)主要由分頻、計(jì)數(shù)、譯碼三個(gè)模塊構(gòu)成。分頻模塊將50MHz系統(tǒng)基準(zhǔn)時(shí)鐘分頻產(chǎn)生兩路時(shí)鐘信號(hào),一路是1Hz的數(shù)字鐘計(jì)時(shí)工作頻率,一路是數(shù)碼管動(dòng)態(tài)顯示的掃描頻率;計(jì)時(shí)模塊對(duì)1Hz的時(shí)鐘信號(hào)進(jìn)行計(jì)時(shí),分為時(shí)、分、秒三個(gè)部分,同時(shí)具有時(shí)分秒調(diào)整功能,方便演示;譯碼顯示模塊采用動(dòng)態(tài)掃描的方式完成8個(gè)7位數(shù)碼管的動(dòng)態(tài)顯示,最后通過主模塊調(diào)用三個(gè)子模塊實(shí)現(xiàn)整體設(shè)計(jì)要求。
綜上,給出如下輸入輸出變量:
輸入變量:1.時(shí)鐘信號(hào): 每個(gè)時(shí)鐘的上升沿觸發(fā)系統(tǒng)的狀態(tài)轉(zhuǎn)換;
2.計(jì)時(shí)復(fù)位信號(hào):下降沿觸發(fā),按下后計(jì)時(shí)自動(dòng)回到初始狀態(tài);
3.使能信號(hào):激發(fā)時(shí)鐘工作。
輸出變量:1.數(shù)碼管信號(hào):按位輸入到數(shù)碼管,顯示時(shí)鐘;
2.計(jì)時(shí)時(shí)鐘信號(hào):分頻后的計(jì)時(shí)時(shí)鐘信號(hào);
3.進(jìn)位信號(hào):進(jìn)制轉(zhuǎn)換。
3 各功能模塊原理及實(shí)現(xiàn)
3.1 功能模塊設(shè)計(jì)3.1.1 分頻模塊
1. 設(shè)計(jì)原理
本時(shí)鐘電路的設(shè)計(jì)中使用DE2-115時(shí)鐘芯片,故需對(duì)系統(tǒng)提供的50MHz時(shí)鐘頻率進(jìn)行分頻,得到計(jì)時(shí)所需的時(shí)鐘頻率。
定義變量并根據(jù)需要得到的分頻信號(hào)設(shè)定計(jì)數(shù)值,對(duì)該變量進(jìn)行加或減計(jì)數(shù),每到達(dá)一次計(jì)數(shù)值點(diǎn),將該變量清零或重置,并且對(duì)輸出信號(hào)取一次反,即可以得到所需的分頻信號(hào)。本模塊采用此方法實(shí)現(xiàn)上述所需時(shí)鐘信號(hào)的分頻功能。
代碼實(shí)現(xiàn)
library ieee;
use ieee.STD_logic_1164.all;
use ieee.STD_logic_unsigned.all;
entity clock0710 is -- divide50MHz to 1Hz
generic(d : integer :=50000000);
port( clk: in STD_logic;
dav: out STD_logic);
end;
architecture bhv of clock0710 is
signal s : STD_logic;
signal c :STD_logic_vector(25 downto 0);
begin
process(clk)
--variable cnt:STD_logic_vector(25 downto 0);
begin
if clk'event and clk='1'then
if c = (d-1) then
c <="00000000000000000000000000";s <= '1';
elsif c >= d/2then
c <= c+ 1;s <= '1';
else c <= c +1;s <= '0';
end if;
end if;
end process;
dav <= s;
end;
3.1.2計(jì)數(shù)模塊
1. 設(shè)計(jì)原理
計(jì)數(shù)模塊采用對(duì)1秒的信號(hào)源進(jìn)行計(jì)數(shù)并向高位進(jìn)位的思想實(shí)現(xiàn)計(jì)時(shí)功能,采用6個(gè)變量分別對(duì)時(shí)分秒的高低位進(jìn)行計(jì)數(shù),低位滿后向高位進(jìn)位。
2. 代碼實(shí)現(xiàn)
時(shí)鐘
library ieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entity hour0710 is
port(CLK,reset:instd_logic;
daout:out std_logic_vector(7 downto 0));
end entity hour0710;
architecture fun ofhour0710 is signal count:std_logic_vector(7 downto 0);
begin
daout<=count;
process(CLK,reset)
begin
IF(reset='0')THENcount<="00000000"; --若reset=0,則異步清零
elsif(CLK'event andCLK='1')then --否則,若clk上升沿到
if(count(3 downto0)="1001")then --若個(gè)位計(jì)時(shí)恰好到"1001"即9
if(count<16#23#)then --23進(jìn)制
count<=count+7; --若到23D則
else
count<="00000000"; --復(fù)0
end if;
elsif(count<16#23#)then --若未到23D,則count進(jìn)1
count<=count+1;
else --否則清零
count<="00000000";
end if; --end if(count(3downto 0)="1001")
end if; --end if(reset='0')
end process;
end fun;
分鐘
library ieee;
use ieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entity minute0710 is
port(CLK,CLK1,reset,hour0710:instd_logic;
enhour0710:out std_logic;
daout:out std_logic_vector(7 downto 0));
end entity minute0710;
architecture fun ofminute0710 is
signal count:std_logic_vector(7downto 0);
signalenhour0710_1,enhour0710_2:std_logic;--enhour0710_1為59分時(shí)的進(jìn)位信號(hào)
begin --enhour0710_2由clk調(diào)制后的手動(dòng)調(diào)時(shí)脈沖信號(hào)串
daout<=count;
enhour0710_2<=(hour0710and CLK1); --enhour0710為手動(dòng)調(diào)時(shí)控制信號(hào),高電平有效
enhour0710<=(enhour0710_1or enhour0710_2);
process(CLK,reset,hour0710)
begin
if(reset='0')thencount<="00000000"; --若reset=0,則異步清零
elsif(CLK'event andCLK='1')then --否則,若clk上升沿到
if(count(3 downto0)="1001")then --若個(gè)位計(jì)時(shí)恰好到"1001"即9
if(count<16#60#)then --又若count小于 16#60#,即60
if(count="1011001")then --又若59D
enhour0710_1<='1'; --則置進(jìn)位為1
count<="00000000"; --count復(fù)0
else
count<=count+7; --若count未到59D,則加7,即作"加6校正"
end if; --使前面的16#60#的個(gè)位轉(zhuǎn)變?yōu)?421BCD的容量
elsecount<="00000000"; --count復(fù)0(有此句,則對(duì)無效狀態(tài)電路可自啟動(dòng))
end if; --end if(count<16#60#)
elsif(count<16#60#)then
count<=count+1; --若count<16#60#,則count加1
enhour0710_1<='0'after100 ns; --沒有發(fā)生進(jìn)位
elsecount<="00000000"; --否則,若count不小于16#60#,count復(fù)0
end if; --endif(count(3 downto 0)="1001")
end if; --endif(reset='0')
end process;
end fun;
秒鐘
library ieee;
useieee.std_logic_1164.all;
useieee.std_logic_unsigned.all;
entity second0710 is
port(CLK,reset,min0710:std_logic;
enmin0710:out std_logic;
daout:out std_logic_vector(7 downto 0));
end entity second0710;
architecture fun ofsecond0710 is signal count:std_logic_vector(7 downto 0);
signal
enmin0710_1,enmin0710_2:std_logic;--enmin0710_1為59分時(shí)的進(jìn)位信號(hào)
begin --enmi0710_2由clk調(diào)制后的手動(dòng)調(diào)時(shí)脈沖信號(hào)串
daout<=count;
enmin0710_2<=(min0710and CLK); --enmin0710為手動(dòng)調(diào)時(shí)控制信號(hào),高電平有效
enmin0710<=(enmin0710_1or enmin0710_2);--enmin為向分進(jìn)位信號(hào)
process(CLK,reset,min0710)
begin
if(reset='0')thencount<="00000000";--若reset=0,則異步清零
elsif(CLK'event andCLK='1')then --否則,若clk上升沿到
if(count(3 downto0)="1001")then --若個(gè)位計(jì)時(shí)恰好到"1001"即9
if(count<16#60#)then --又若count小于 16#60#,即60H
if(count="1011001")then --又若59D
enmin0710_1<='1';count<="00000000";--則置進(jìn)位為1 count復(fù)0
else --未到59D
count<=count+7; --則加7,而+7=+1+6,即作"加6校正"
end if;
else --若count不小于16#60#
count<="00000000"; --count復(fù)0
end if; --end
elsif(count<16#60#)then --若個(gè)位計(jì)時(shí)未到"1001"則轉(zhuǎn)此句再判
count<=count+1; --若count<16#60#,則count加1
enmin0710_1<='0'after100 ns; --沒有發(fā)生進(jìn)位
else --否則,若count不小于16#60#
count<="00000000"; --count復(fù)0
end if; --end if(count(3downto 0)="1001")
end if; --endif(reset='0')
end process;
end fun;
3.1.3 數(shù)碼管顯示模塊
1. 設(shè)計(jì)原理
譯碼顯示模塊是將時(shí)間的數(shù)值轉(zhuǎn)化成數(shù)碼管段碼值,計(jì)數(shù)器將分頻器分頻的信號(hào)計(jì)數(shù)后傳給了譯碼器翻譯成7位的信號(hào)傳給晶體管。選六個(gè)晶體管來分別記錄時(shí)分秒,分為兩組數(shù)碼管,所以分別定義高位和低位和來分別控制兩組數(shù)碼管。
2. 代碼實(shí)現(xiàn)
分位
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
entity fenwei0710 is
port(uc:in std_logic_vector(7 downto 0);
dp1,dp2:out std_logic_vector(3 downto 0));
end;
architecture ott of fenwei0710 is
begin
process(uc)
begin
dp1(3 downto 0)<=uc(3 downto 0);
dp2(3 downto 0)<=uc(7 downto 4);
end process;
end;
譯碼器
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
entity LED7S is
Port(din: in std_logic_vector(3 downto 0);
y: out std_logic_vector(6 downto 0));
end LED7S;
architecture one of LED7S is
begin
process(din)
begin
case dinis
when "0000" =>y<="1000000"; ---Display "0"
when "0001" =>y<="1111001"; ---Display "1"
when "0010" =>y<="0100100"; ---Display "2"
when "0011" =>y<="0110000"; ---Display "3"
when "0100" =>y<="0011001"; ---Display "4"
when "0101" =>y<="0010010"; ---Display "5"
when "0110" =>y<="0000010"; ---Display "6"
when "0111" =>y<="1111000"; ---Display "7"
when "1000" =>y<="0000000"; ---Display "8"
when "1001" =>y<="0010000"; ---Display "9"
when "1010" =>y<="0001000"; ---Display "A"
when "1011" => y<="0000011"; --- Display "B"
when "1100" =>y<="1000110"; ---Display "C"
when "1101" =>y<="0100001"; ---Display "D"
when "1110" =>y<="0000110"; ---Display "E"
when "1111" =>y<="0001110"; ---Display "F"
when others => y<=null;
end case;
end process;
end one;
3.2 整體功能測(cè)試
整體頂層模塊程序代碼及原理圖
-- Copyright (C)1991-2006 Altera Corporation
-- Your use ofAltera Corporation's design tools, logic functions
-- and othersoftware and tools, and its AMPP partner logic
-- functions, andany output files any of the foregoing
-- (includingdevice programming or simulation files), and any
-- associateddocumentation or information are expressly subject
-- to the termsand conditions of the Altera Program License
-- SubscriptionAgreement, Altera MegaCore Function License
-- Agreement, orother applicable license agreement, including,
-- withoutlimitation, that your use is for the sole purpose of
-- programminglogic devices manufactured by Altera and sold by
-- Altera or itsauthorized distributors. Please refer tothe
-- applicableagreement for further details.
-- PROGRAM"Quartus II"
-- VERSION"Version 5.1 Build 216 03/06/2006 Service Pack 2 SJ Full Version"
LIBRARY ieee;
USEieee.std_logic_1164.all;
LIBRARY work;
ENTITY Block1 IS
port
(
reset : IN STD_LOGIC;
min0710 : IN STD_LOGIC;
clk : IN STD_LOGIC;
hour0710 : IN STD_LOGIC;
enhour1 : OUT STD_LOGIC_VECTOR(6 downto 0);
enhour2 : OUT STD_LOGIC_VECTOR(6 downto 0);
enmin1 : OUT STD_LOGIC_VECTOR(6 downto 0);
enmin2 : OUT STD_LOGIC_VECTOR(6 downto 0);
ensecond1 : OUT STD_LOGIC_VECTOR(6 downto 0);
ensecond2 : OUT STD_LOGIC_VECTOR(6 downto 0)
);
END Block1;
ARCHITECTUREbdf_type OF Block1 IS
component clock
GENERIC ();
PORT(clk : IN STD_LOGIC;
dav : OUT STD_LOGIC
);
end component;
component led7s
PORT(din : IN STD_LOGIC_VECTOR(3 downto0);
y : OUT STD_LOGIC_VECTOR(6 downto 0)
);
end component;
componentfenwei0710
PORT(uc : IN STD_LOGIC_VECTOR(7 downto0);
dp1 : OUT STD_LOGIC_VECTOR(3 downto 0);
dp2 : OUT STD_LOGIC_VECTOR(3 downto 0)
);
end component;
componentminute0710
PORT(CLK : IN STD_LOGIC;
CLK1 : IN STD_LOGIC;
reset : IN STD_LOGIC;
hour0710 : IN STD_LOGIC;
enhour0710 : OUT STD_LOGIC;
daout : OUT STD_LOGIC_VECTOR(7 downto 0)
);
end component;
componentsecond0710
PORT(CLK : IN STD_LOGIC;
reset : IN STD_LOGIC;
min0710 : IN STD_LOGIC;
enmin0710 : OUT STD_LOGIC;
daout : OUT STD_LOGIC_VECTOR(7 downto 0)
);
end component;
component hour0710
PORT(CLK : IN STD_LOGIC;
reset : IN STD_LOGIC;
daout : OUT STD_LOGIC_VECTOR(7 downto 0)
);
end component;
signal SYNTHESIZED_WIRE_0 : STD_LOGIC_VECTOR(3 downto 0);
signal SYNTHESIZED_WIRE_1 : STD_LOGIC_VECTOR(7 downto 0);
signal SYNTHESIZED_WIRE_2 : STD_LOGIC_VECTOR(7 downto 0);
signal SYNTHESIZED_WIRE_3 : STD_LOGIC_VECTOR(3 downto 0);
signal SYNTHESIZED_WIRE_4 : STD_LOGIC_VECTOR(3 downto 0);
signal SYNTHESIZED_WIRE_5 : STD_LOGIC_VECTOR(3 downto 0);
signal SYNTHESIZED_WIRE_6 : STD_LOGIC_VECTOR(3 downto 0);
signal SYNTHESIZED_WIRE_7 : STD_LOGIC_VECTOR(3 downto 0);
signal SYNTHESIZED_WIRE_8 : STD_LOGIC;
signal SYNTHESIZED_WIRE_13 : STD_LOGIC;
signal SYNTHESIZED_WIRE_11 : STD_LOGIC_VECTOR(7 downto 0);
signal SYNTHESIZED_WIRE_12 : STD_LOGIC;
BEGIN
b2v_inst : clock
GENERIC MAP()
PORT MAP(clk =>clk,
dav => SYNTHESIZED_WIRE_13);
b2v_inst10 : led7s
PORT MAP(din =>SYNTHESIZED_WIRE_0,
y => ensecond1);
b2v_inst11 :fenwei0710
PORT MAP(uc =>SYNTHESIZED_WIRE_1,
dp1 => SYNTHESIZED_WIRE_4,
dp2 => SYNTHESIZED_WIRE_5);
b2v_inst12 :fenwei0710
PORT MAP(uc =>SYNTHESIZED_WIRE_2,
dp1 => SYNTHESIZED_WIRE_6,
dp2 => SYNTHESIZED_WIRE_7);
b2v_inst14 : led7s
PORT MAP(din =>SYNTHESIZED_WIRE_3,
y => ensecond2);
b2v_inst15 : led7s
PORT MAP(din =>SYNTHESIZED_WIRE_4,
y => enmin1);
b2v_inst18 : led7s
PORT MAP(din =>SYNTHESIZED_WIRE_5,
y => enmin2);
b2v_inst19 : led7s
PORT MAP(din =>SYNTHESIZED_WIRE_6,
y => enhour1);
b2v_inst20 : led7s
PORT MAP(din =>SYNTHESIZED_WIRE_7,
y => enhour2);
b2v_inst4 :minute0710
PORT MAP(CLK =>SYNTHESIZED_WIRE_8,
CLK1 => SYNTHESIZED_WIRE_13,
reset => reset,
hour0710 => hour0710,
enhour0710 => SYNTHESIZED_WIRE_12,
daout => SYNTHESIZED_WIRE_1);
b2v_inst6 :second0710
PORT MAP(CLK =>SYNTHESIZED_WIRE_13,
reset => reset,
min0710 => min0710,
enmin0710 => SYNTHESIZED_WIRE_8,
daout => SYNTHESIZED_WIRE_11);
b2v_inst8 :fenwei0710
PORT MAP(uc =>SYNTHESIZED_WIRE_11,
dp1 => SYNTHESIZED_WIRE_0,
dp2 => SYNTHESIZED_WIRE_3);
b2v_inst9 :hour0710
PORT MAP(CLK =>SYNTHESIZED_WIRE_12,
reset => reset,
daout => SYNTHESIZED_WIRE_2);
END;
實(shí)驗(yàn)箱調(diào)試結(jié)果
將程序下載到實(shí)驗(yàn)箱上,撥動(dòng)開關(guān)SW2小時(shí)自動(dòng)調(diào)節(jié),撥動(dòng)開關(guān)SW1分鐘自動(dòng)調(diào)節(jié),按下開關(guān)SW0,所有時(shí)間會(huì)自動(dòng)清零。
|
評(píng)分
-
查看全部評(píng)分
|