ISE實(shí)現(xiàn)多功能數(shù)字鐘設(shè)計(jì).doc
一、 任務(wù)要求用FPGA器件和EDA技術(shù)實(shí)現(xiàn)多功能數(shù)字鐘的設(shè)計(jì)?;竟δ芤螅耗茱@示小時(shí)、分鐘、秒鐘(時(shí)、分用7段LED顯示器,秒用LED燈)。 小時(shí)計(jì)數(shù)器為同步24進(jìn)制; 要求手動(dòng)校時(shí)、校分。擴(kuò)展功能要求:任意時(shí)刻鬧鐘; 小時(shí)顯示(12/24)切換電路 自動(dòng)報(bào)整點(diǎn)時(shí)數(shù)。二、 建立工程在ISE 14,9軟件中建立名為clock 的工程文件。芯片系列選擇Spatan3E,具體芯片型號(hào)選擇XC3S100E,封裝類(lèi)型選擇CP132,速度信息選擇-5。三、 原理設(shè)計(jì)四、 頂層模塊設(shè)計(jì)創(chuàng)建名為top_clock的文件,本設(shè)計(jì)中頂層模塊用于調(diào)用各個(gè)子模塊,以及將鬧鐘與整點(diǎn)報(bào)時(shí)模塊綜合在內(nèi),頂層源碼如下:module top_clock(input Hchange,/24小時(shí),12小時(shí)切換信號(hào)input Change,/用來(lái)進(jìn)行時(shí)分和秒的顯示切換input CLK_50,/50MHz時(shí)鐘input nCR,EN,Clock_EN,input Adj_Min,Adj_Hour,Adj_Clock,/使能信號(hào),小時(shí)分鐘調(diào)時(shí)允許信號(hào),鬧鐘使能信號(hào)(撥鈕開(kāi)關(guān))output 6:0 HEX0,output reg Led_Alarm,output reg 3:0 HEX/共陽(yáng)極數(shù)碼管對(duì)應(yīng)端);reg Alarm;wire ENM_L,ENM_H,ENH;wire 7:0 Hour_24,TMinute,TSecond,CHour,CMinute;/中間變量聲明,正常時(shí)鐘變量和鬧鐘時(shí)鐘變量wire 7:0 Hour_12,Display_HourT,Display_HourAdjust;reg 3:0 bcd=4b0000;/記載數(shù)碼管所要顯示的數(shù)據(jù)reg 7:0 Display_Hour,Minute;reg LD_6_RADIO;reg 7:0 sum,counter;supply1 Vdd; wire CP_1Hz;/=分頻=Divider50MHz U0(.CLK_50M(CLK_50),.nCLR(nCR),.CLK_1HzOut(CP_1Hz);/用以時(shí)鐘計(jì)數(shù)的CPdefparam U0.N = 25,U0.CLK_Freq = 50000000,U0.OUT_Freq = 1;Divider50MHz U1(.CLK_50M(CLK_50),.nCLR(nCR),.CLK_1HzOut(CP_200Hz);/用以動(dòng)態(tài)掃描的CP,供給數(shù)碼管defparam U1.N = 18,U1.CLK_Freq = 50000000,U1.OUT_Freq = 200;/=60進(jìn)制秒計(jì)數(shù)器=Scounter10 S0(TSecond3:0,nCR,EN,CP_1Hz);/秒:個(gè)位Scounter6 S1(TSecond7:4,nCR,(TSecond3:0=4h9),CP_1Hz);/秒:十位/=60進(jìn)制分計(jì)數(shù)器=Mcounter10 M0(TMinute3:0,nCR,ENM_L,EN,CP_1Hz);/分:個(gè)位Mcounter6 M1(TMinute7:4,nCR,ENM_H,EN,CP_1Hz);/分:十位assign ENM_L=Adj_Min?Vdd:(TSecond=8h59);/分鐘按書(shū)上CP調(diào)時(shí)assign ENM_H=(Adj_Min&&(TMinute3:0=4h9)|(TMinute3:0=4h9)&&(TSecond=8h59); /24小時(shí)制 counter24 H0(Hour_247:4,Hour_243:0,nCR,ENH,EN,CP_1Hz);assign ENH = Adj_Hour?Vdd:(TMinute=8h59)&&(TSecond=8h59);/=12小時(shí)與24小時(shí)進(jìn)制切換控制=assign Display_HourAdjust=(Hour_24=8h20)|(Hour_24=8h21)?(Hour_24-24):(Hour_24-18);assign Hour_12 = (Hour_24<8h13)?Hour_24:Display_HourAdjust;assign Display_HourT = Hchange?Hour_12:Hour_24;/=鬧鐘=/-時(shí)鐘秒-/counter60 CCS(nCR,CP_1Hz,EN,CSecond7:4,CSecond3:0);/-時(shí)鐘分-counter60 CCM(nCR,CP_1Hz,CMin_EN,CMinute7:4,CMinute3:0);/-產(chǎn)生分使能信號(hào)-assign CMin_EN = (!EN && Adj_Clock && Adj_Min);/-時(shí)鐘時(shí)-Counter24C CCH(nCR,CP_1Hz,CHour_EN,CHour7:4,CHour3:0);/-產(chǎn)生時(shí)使能信號(hào)-assign CHour_EN = (!EN && Adj_Clock && Adj_Hour);/-鬧鐘響-always(EN or Clock_EN) /鬧鐘開(kāi)關(guān)beginif(EN && Clock_EN && (CHour = Display_HourT) && (CMinute = TMinute)Alarm <= 1;else Alarm <= 0;endalways(posedge CLK_50 or negedge EN or negedge Alarm) /表示鬧鐘的LEDbeginif(EN) Led_Alarm <= 0;elsebeginif(Alarm) Led_Alarm <= 0;else Led_Alarm <= Led_Alarm;endend/alarm_clock AL0(Hour24,Minute,CP_1Hz,Set_Alarm,Close_clock,nCR,KeySet_Hour_ev,KeySet_Minute_ev,LD_7,Alarm_Hour,Alarm_Minute);/=數(shù)碼顯示=always(Adj_Clock)/確定數(shù)碼管顯示鬧鐘還是正常時(shí)鐘beginif(Adj_Clock) begin Display_Hour <= CHour;Minute <= CMinute;endelse begin Display_Hour <= Display_HourT;Minute <= TMinute;endendalways(posedge CP_200Hz)beginif(Change=1)/數(shù)碼管進(jìn)行時(shí)分顯示begincase(HEX)4b1110: begin HEX<=4b0111; bcd<= Display_Hour 7:4; end/第一根數(shù)碼管顯示小時(shí)十位4b0111: begin HEX<=4b1011; bcd<= Display_Hour 3:0; end/第二根顯示小時(shí)個(gè)位4b1011: begin HEX<=4b1101; bcd<= Minute 7:4; end/第三根顯示分鐘十位4b1101: begin HEX<=4b1110; bcd<= Minute 3:0; end/第四根顯示分鐘個(gè)位default: begin HEX<=0111; bcd<=Display_Hour 7:4; endendcaseendelse/數(shù)碼管進(jìn)行秒顯示,change為低電平時(shí)顯示秒begincase(HEX)4b1110: begin HEX<=4b1101; bcd<= TSecond 7:4; end/第三根顯示秒十位4b1101: begin HEX<=4b1110; bcd<= TSecond 3:0; end/第四根顯示秒個(gè)位default: begin HEX<=1101; bcd<= TSecond 7:4; endendcaseendendSEG7_LUT L0(HEX0,bcd);/調(diào)用數(shù)碼管子函數(shù)/=整點(diǎn)報(bào)時(shí)=assign LD_6 = LD_6_RADIO; always(CP_1Hz) begin if(Minute7:0 = 8h00) && (counter7:0 < (Hour_247:4*10 + Hour_243:0) begin LD_6_RADIO <= CP_1Hz; end else begin LD_6_RADIO <= 0; end end always(posedge CP_1Hz) if(Minute7:0=8h00) begin counter7:0<=counter7:0+1b1; end else begin counter7:0<=8h00; endendmodule五、 頂層模塊設(shè)計(jì)圖六、 子模塊設(shè)計(jì)1、 50MHz分頻器module Divider50MHz(CLK_50M,nCLR,CLK_1HzOut);parameter N = 25;/位寬parameter CLK_Freq = 50000000;/50MHz時(shí)鐘輸入parameter OUT_Freq = 1;/1Hz時(shí)鐘輸出input nCLR,CLK_50M;/輸入端口說(shuō)明output reg CLK_1HzOut;/輸出端口說(shuō)明reg N-1:0 Count_DIV;/內(nèi)部節(jié)點(diǎn),存放計(jì)數(shù)器的輸出值always(posedge CLK_50M or negedge nCLR)beginif(!nCLR) begin CLK_1HzOut <= 0; Count_DIV <= 0; endelse beginif(Count_DIV <(CLK_Freq/(2*OUT_Freq)-1)/計(jì)數(shù)器模Count_DIV <= Count_DIV + 1b1;/分頻器計(jì)數(shù)加1else beginCount_DIV <= 0;/分頻器輸出清零CLK_1HzOut <= CLK_1HzOut;/輸出信號(hào)取反endend endendmodule2、 秒模10計(jì)數(shù)器module Scounter10(Q,nCR,EN,CP);input CP,nCR,EN;output Q;reg 3:0 Q;always (posedge CP or negedge nCR)begin if(nCR) Q <= 4b0000;/異步清零else if(EN) Q <= Q; /暫停計(jì)數(shù)else if(Q=4b1001) Q <= 4b0000;else Q <= Q + 1b1;end3、 秒模6計(jì)數(shù)器module Scounter6(Q,nCR,EN,CP);input CP,nCR,EN;output Q;reg 3:0 Q;always (posedge CP or negedge nCR)begin if(nCR) Q <= 4b0000;/異步清零else if(EN) Q <= Q; /暫停計(jì)數(shù)else if(Q=4b0101) Q <= 4b0000;else Q <= Q + 1b1;end4、 分模10計(jì)數(shù)器module Mcounter10(Q,nCR,EN1,EN2,CP);input CP,nCR,EN1,EN2;output Q;reg 3:0 Q;always (posedge CP or negedge nCR)begin if(nCR) Q <= 4b0000;/異步清零else if(EN1|!EN2) Q <= Q; /暫停計(jì)數(shù)else if(Q=4b1001) Q <= 4b0000;else Q <= Q + 1b1;end5、 分模6計(jì)數(shù)器module Mcounter6(Q,nCR,EN1,EN2,CP);input CP,nCR,EN1,EN2;output Q;reg 3:0 Q;always (posedge CP or negedge nCR)begin if(nCR) Q <= 4b0000;/異步清零else if(EN1|EN2) Q <= Q; /暫停計(jì)數(shù)else if(Q=4b0101) Q <= 4b0000;else Q <= Q + 1b1;end6、 模24計(jì)數(shù)器module counter24(CntH,CntL,nCR,EN1,EN2,CP);input CP,nCR,EN1,EN2;output reg 3:0 CntH,CntL;/小時(shí)的十位和個(gè)位輸出always(posedge CP or negedge nCR)beginif(nCR) CntH,CntL <= 8h00; /異步清零else if(EN1|EN2) CntH,CntL <= CntH,CntL;/暫停計(jì)數(shù)else if(CntH)>2|(CntL>9)|(CntH)=2&&(CntL)>=3)CntH,CntL <= 8h00; /對(duì)小時(shí)計(jì)數(shù)器出錯(cuò)時(shí)的處理else if(CntH)=2&&(CntL)<3) /進(jìn)行2023計(jì)數(shù)begin CntH <=CntH; CntL <= CntL + 1b1; endelse if(CntL=9) /小時(shí)十位的計(jì)數(shù)begin CntH <=CntH + 1b1; CntL <= 4b0000; endelse begin CntH <= CntH; CntL <= CntL + 1b1; end endendmodule7、 模60計(jì)數(shù)器module counter60(nCLR,Clk,EN,CntH,CntL); input nCLR,Clk,EN; output reg 3:0 CntH,CntL; always(posedge Clk or negedge nCLR) beginif(nCLR)CntH,CntL <= 0; /異步清零else if(EN)CntH,CntL <= CntH,CntL; /暫停信號(hào)else if(CntH > 5)|(CntL > 9)|(CntH = 5)&&(CntL = 9)CntH,CntL <= 8h00; /異常處理else if(CntL = 9)begin CntH <= CntH + 1b1;CntL <= 0;end /十位計(jì)數(shù)elsebegin CntH <= CntH;CntL <= CntL + 1b1;end /個(gè)位計(jì)數(shù) endendmodule8、 數(shù)碼管顯示module SEG7_LUT(oSEG,iDIG);input 3:0 iDIG;/二進(jìn)制輸入output reg 6:0 oSEG; /7段碼輸出always(iDIG)begincase(iDIG)4h0: oSEG = 7b000_0001;4h1: oSEG = 7b100_1111;4h2: oSEG = 7b001_0010;4h3: oSEG = 7b000_0110;4h4: oSEG = 7b100_1100;4h5: oSEG = 7b010_0100;4h6: oSEG = 7b010_0000;4h7: oSEG = 7b000_1111;4h8: oSEG = 7b000_0000;4h9: oSEG = 7b000_0100;default: oSEG=7b1111111;endcaseendendmodule七、 各模塊仿真1、 模10計(jì)數(shù)器測(cè)試代碼:/ Inputsreg nCR;reg EN;reg CP;/ Outputswire 3:0 Q;/ Instantiate the Unit Under Test (UUT)counter10 uut (.Q(Q), .nCR(nCR), .EN(EN), .CP(CP);parameter PERIOD =40;/時(shí)鐘信號(hào)周期設(shè)置為40nsalways beginCP=1b0;#(PERIOD/2) CP=1b1;#(PERIOD/2);endinitial begin/ Initialize InputsnCR = 0;EN = 1;CP = 1;/ Wait 100 ns for global reset to finish#100; nCR=1;/ Add stimulus hereendendmodule2、 模6計(jì)數(shù)器測(cè)試代碼:/ Inputsreg nCR;reg EN;reg CP;/ Outputswire 3:0 Q;/ Instantiate the Unit Under Test (UUT)counter6 uut (.Q(Q), .nCR(nCR), .EN(EN), .CP(CP);parameter PERIOD =40;/時(shí)鐘信號(hào)周期設(shè)置為40nsalways beginCP=1b0;#(PERIOD/2) CP=1b1;#(PERIOD/2);endinitial begin/ Initialize InputsnCR = 0;EN = 1;CP = 1;/ Wait 100 ns for global reset to finish#100;nCR =1;/ Add stimulus hereendendmodule3、 模24計(jì)數(shù)器測(cè)試代碼:/ Inputsreg nCR;reg EN;reg CP;/ Outputswire 3:0 CntH;wire 3:0 CntL;/ Instantiate the Unit Under Test (UUT)counter24 uut (.CntH(CntH), .CntL(CntL), .nCR(nCR), .EN(EN), .CP(CP);parameter PERIOD =40;/時(shí)鐘信號(hào)周期設(shè)置為40nsalways beginCP=1b0;#(PERIOD/2) CP=1b1;#(PERIOD/2);endinitial begin/ Initialize InputsnCR = 0;EN = 1;CP = 1;/ Wait 100 ns for global reset to finish#100; nCR=1;/ Add stimulus hereendendmodule4、 模60計(jì)數(shù)器測(cè)試代碼:/ Inputsreg nCLR;reg Clk;reg EN;/ Outputswire 3:0 CntH;wire 3:0 CntL;/ Instantiate the Unit Under Test (UUT)counter60 uut (.nCLR(nCLR), .Clk(Clk), .EN(EN), .CntH(CntH), .CntL(CntL);parameter PERIOD =40;/時(shí)鐘信號(hào)周期設(shè)置為40nsalways beginClk=1b0;#(PERIOD/2) Clk=1b1;#(PERIOD/2);endinitial begin/ Initialize InputsnCLR = 0;Clk = 1;EN = 1;/ Wait 100 ns for global reset to finish#100;nCLR=1;/ Add stimulus hereendendmodule八、 引腳分配N(xiāo)ET "CLK_50" TNM_NET = CLK_50;TIMESPEC TS_CLK_50 = PERIOD "CLK_50" 20 ns HIGH 50%;NET "CLK_50" LOC = B8;NET "nCR" LOC = P11;NET "EN" LOC = L3;NET "Adj_Min" LOC = K3;NET "Adj_Hour" LOC = B4;NET "Change" LOC = G3;NET "Led_Alarm" LOC = N4;NET "Adj_Clock" LOC = E2;NET "Clock_EN" LOC = N3;NET "HEX06" LOC = L14;NET "HEX05" LOC = H12;NET "HEX04" LOC = N14;NET "HEX03" LOC = N11;NET "HEX02" LOC = P12;NET "HEX01" LOC = L13;NET "HEX00" LOC = M12;NET "HEX0" LOC = F12;NET "HEX1" LOC = J12;NET "HEX2" LOC = M13;NET "HEX3" LOC = K14;NET "Hchange" LOC = F3;NET "CLK_50" SLEW = FAST;NET "LD_6" LOC = G1;九、 設(shè)計(jì)實(shí)現(xiàn)1. 運(yùn)行Implement Design選項(xiàng),進(jìn)行轉(zhuǎn)換、映射、布局布線(xiàn)操作。2. 選擇Manage Configuration Project選項(xiàng)l 選擇Boundary Scan,在窗口空白處點(diǎn)擊鼠標(biāo)右鍵,選中Initialize Chain選項(xiàng).l 將clock.bit文件導(dǎo)入至xc3s5001中l(wèi) 右擊xc3s5001,選擇program選項(xiàng),將程序燒錄至FPGA實(shí)驗(yàn)板中3. 觀(guān)察運(yùn)行情況1) 測(cè)試基本功能:打開(kāi)使能開(kāi)關(guān)L3,數(shù)碼管可以正常顯示分和時(shí),撥動(dòng)時(shí)分和秒的切換顯示開(kāi)關(guān)G3,數(shù)碼管可以切換顯示秒。撥動(dòng)K3和B4,可以實(shí)現(xiàn)校時(shí)功能。撥動(dòng)清零開(kāi)關(guān)P11,可以實(shí)現(xiàn)清零功能。當(dāng)時(shí)間到23:59時(shí),能運(yùn)行至00:00。2) 測(cè)試擴(kuò)展功能:撥動(dòng)F3,可實(shí)現(xiàn)24小時(shí)與12小時(shí)的切換。當(dāng)時(shí)間為整點(diǎn)時(shí),LED燈G1會(huì)根據(jù)當(dāng)前整點(diǎn)時(shí)數(shù)閃爍對(duì)應(yīng)次數(shù),撥動(dòng)N3,鬧鐘使能。撥動(dòng)E2,進(jìn)入鬧鐘設(shè)置狀態(tài),此時(shí)設(shè)置鬧鐘時(shí)間。當(dāng)正常時(shí)間跳到鬧鐘設(shè)置時(shí)刻時(shí),鬧鐘對(duì)應(yīng)LED燈N4會(huì)常亮,表示鬧鐘響。當(dāng)正常時(shí)間已經(jīng)越過(guò)鬧鐘設(shè)置時(shí)間時(shí),N4會(huì)熄滅。鬧鐘響時(shí)關(guān)閉鬧鐘使能端N3時(shí),N4也會(huì)熄滅。十、 實(shí)驗(yàn)總結(jié)本次實(shí)驗(yàn)是一個(gè)中等規(guī)模的設(shè)計(jì)實(shí)驗(yàn),相比步進(jìn)電機(jī)實(shí)驗(yàn),難度明顯上升,這就對(duì)我們的分析和設(shè)計(jì)能力有了更高的要求。要實(shí)現(xiàn)這個(gè)多功能的數(shù)字鐘,關(guān)鍵要做到思路清晰,先構(gòu)思好頂層架構(gòu),再一一考慮需要調(diào)用的模塊,最后依次編寫(xiě)各個(gè)模塊。在調(diào)試的時(shí)候,先要做到各子模塊調(diào)試無(wú)誤,再通過(guò)整機(jī)聯(lián)調(diào)觀(guān)察出現(xiàn)的不正常結(jié)果,列出可能的錯(cuò)誤,再去對(duì)應(yīng)的位置進(jìn)行改正。本次實(shí)驗(yàn)中,不可避免地出現(xiàn)了若干錯(cuò)誤之處,例如在實(shí)現(xiàn)24進(jìn)制和12進(jìn)制轉(zhuǎn)換時(shí),沒(méi)有發(fā)現(xiàn)代碼中的計(jì)算方式是以8421BCD碼來(lái)進(jìn)行計(jì)算的,于是在最后的12進(jìn)制顯示中出現(xiàn)了很多不正常狀態(tài),花費(fèi)了一些時(shí)間才找到解決辦法。這也提醒我在之后的學(xué)習(xí)過(guò)程中要保持細(xì)心的態(tài)度,不斷學(xué)習(xí)糾正錯(cuò)誤的方法,提高效率。