數(shù)字鐘verilog.doc
《數(shù)字鐘verilog.doc》由會員分享,可在線閱讀,更多相關(guān)《數(shù)字鐘verilog.doc(23頁珍藏版)》請在裝配圖網(wǎng)上搜索。
目 錄 1 設(shè)計任務(wù)及要求 1 2 總體設(shè)計分析 1 3 各模塊設(shè)計 2 3.1 數(shù)字鐘主體部分 2 3.1.1小時計數(shù)器 2 3.1.2 分、秒計數(shù)器 3 3.2 分頻部分 4 3.3 秒表模塊 5 3.4 鬧鐘模塊 5 3.5 時間設(shè)置模塊 7 3.6 報時模塊 7 3.7 控制顯示模塊 8 3.8 頂層模塊 11 4 總結(jié) 11 4.1 本次作業(yè)遇到的問題 11 4.2 建議和總結(jié) 12 附件 13 1 設(shè)計任務(wù)及要求 本次大作業(yè)的要求為設(shè)計一個多功能數(shù)字鐘,其具體要求如下: 1.有基礎(chǔ)的實時數(shù)字鐘顯示功能,即時、分、秒的正常顯示模式,并且在此基礎(chǔ)上增加上,下午顯示。 2.手動校準(zhǔn)。按動方式鍵,將電路置于校時狀態(tài),則計時電路可用手動方式校準(zhǔn),每按一下校時鍵,時計數(shù)器加1;按動方式鍵,將電路置于校分狀態(tài),以同樣方式手動校分。 3.整點報時,仿中央人民廣播電臺整點報時信號,從59分50秒起每隔2秒發(fā)出一次低音“嘟”信號(信號鳴叫持續(xù)時間1S,間隙時間1S)連續(xù)5次,到達(dá)整點(00分00秒時),發(fā)一次高音“噠”信號(信號持續(xù)時間1S)。 4.鬧時功能,按動方式鍵,使電路工作于預(yù)置狀態(tài),此時顯示器與時鐘脫開,而與預(yù)置計數(shù)器相連,利用前面手動校時,校分方式進行預(yù)置,預(yù)置后回到正常模式。當(dāng)計時計至預(yù)置的時間時,揚聲器發(fā)出鬧鈴信號,時間為半分鐘,鬧鈴信號可以用開關(guān)“止鬧”,按下此開關(guān)后,鬧鈴聲立刻中止,正常情況下應(yīng)將此開關(guān)釋放,否則無鬧時作用。 5.秒表功能。按start鍵開始計秒,按stop鍵停止計秒并保持顯示數(shù)不變,直到復(fù)位信號加入。 2 總體設(shè)計分析 設(shè)計的總體部分按照要求可以分為基本的數(shù)字時鐘顯示、手動校準(zhǔn)、整點報時、鬧鐘功能和秒表功能5大部分。其總體設(shè)計框圖如下: 秒 表 鬧 鐘 手 動 校 準(zhǔn) 整 點 報 時 數(shù) 字 鐘 圖1 總體設(shè)計框圖 其中整點報時跟鬧鐘部分要求不同頻率的聲響,所以需要加入分頻器模塊將輸入的1kHZ的分頻產(chǎn)生500HZ及1HZ的方波信號,其中1HZ的信號對應(yīng)1S的周期,可以用作時鐘秒的顯示及秒表部分。 3 各模塊設(shè)計 根據(jù)總體設(shè)計以及各分模塊的需要,將分立模塊分為7個部分運用verilog HDL編程來實現(xiàn)。其分別為數(shù)字鐘主體部分、手動設(shè)置、分頻、整點報時、鬧鐘功能、秒表、控制顯示和頂層8個模塊。下面將對各個模塊的設(shè)計思想做一詳細(xì)的介紹。 3.1 數(shù)字鐘主體部分 數(shù) 字 鐘 主 體 小時計數(shù)器 分計數(shù)器 秒計數(shù)器 24進制計數(shù)器 60進制 計數(shù)器 6進制 計數(shù)器 10進制 計數(shù)器 <12(早上) >12(下午) 數(shù)字鐘主體部分主要由三個計數(shù)器組成,包括1個24進制計數(shù)器,作為小時計數(shù)器,2個60進制計數(shù)器分別作為分計數(shù)器和秒計數(shù)器。一個60進制計數(shù)器由一個6進制計數(shù)器和一個10進制計數(shù)器組成,由于都是比較簡單的計數(shù)器,所以在用verilog設(shè)計時作為一個整體部分進行編程實現(xiàn)。同理小時計數(shù)器也作為整體部分來編程實現(xiàn)。設(shè)計的流程框圖如下圖2所示。 圖2 數(shù)字鐘整體部分設(shè)計框圖 3.1.1小時計數(shù)器 在verilog程序設(shè)計中,小時計數(shù)器為hour_counter模塊,其中hour_data0為24進制計數(shù)器的低位,即4進制計數(shù)器,hour_data1則為高位,2進制計數(shù)器。編程用always語句實現(xiàn),并且用clk上升沿觸發(fā)實現(xiàn)計數(shù)。EN為使能端,高電平有效。zox為顯示早上、下午的標(biāo)志位,其中小于12點之前為早上,zox為0,否則zox輸出為1表示下午。其QuartusⅡ仿真波形如下圖3所示,由于verilog HDL程序顯示不便,均附在附件上,下面各模塊相同。 圖3 小時計數(shù)器仿真 從仿真圖中可以看出,當(dāng)使能信號信號為高電平且始終上升沿到來時計數(shù)器開始計時,hour_data0計數(shù)為0—1—2—3—0的計數(shù)規(guī)律,即4進制計數(shù)器,同理hour_data1為2進制計數(shù)器,zox信號由圖中看出當(dāng)小于12小時的時候輸出為0,大于12小時時輸出為1,與預(yù)計效果相同。 3.1.2 分、秒計數(shù)器 由于分、秒計數(shù)器均為60進制計數(shù)器,所以以分計數(shù)器作為示例說明其編程思想。其中分計數(shù)器模塊在程序中為minute_counter程序段,由上面分析得分計數(shù)器由一個十進制計數(shù)器與一個六進制計數(shù)器組成,程序中有minute_data0表示分計數(shù)器低位即10進制計數(shù)器,minute_data1表示分計數(shù)器的高位為一個六進制計數(shù)器(秒計數(shù)器的低位、高位分別由second_data0、second_data1表示,其余均與分計數(shù)器相同)。其它信號定義與小時計數(shù)器相同,clk為時鐘信號,時鐘周期為1HZ,即1s,與小時計數(shù)器不同的是,EO為進位信號,即到60s后自動進位。Minute_data0、 minute_data1、second_data0、second_data1位寬均為4位reg型變量。仿真示意圖如下圖4所示。 圖4 分計數(shù)器仿真結(jié)果 由圖中可以看出,當(dāng)使能端信號端EN變?yōu)?的時候,計數(shù)器開始計時,minute_data0計數(shù)規(guī)律為0—1—2—3—4—5—6—7—8—9—0—1當(dāng)計數(shù)到9的時候,minute_data1加1,minute_data1計數(shù)規(guī)則為0—1—2—3—4—5—0—1當(dāng)高位minute_data1計數(shù)到5的時候,進位信號EO變?yōu)?。秒計數(shù)器second_counter模塊與分計數(shù)器完全一樣,這里不再贅述。 3.2 分頻部分 分頻器的功能主要有三個:一是產(chǎn)生計時用的標(biāo)準(zhǔn)秒脈沖1HZ信號;二是提供仿電臺用的1kHZ高音頻信號和500HZ低音頻信號;三是鬧鐘設(shè)置時用的200HZ閃爍信號和鬧鐘響鈴用的500HZ音頻信號。所用輸入信號為1kHZ的高頻信號。根據(jù)分析可知,1kHZ方波信號經(jīng)過2分頻可以得到500HZ方波,經(jīng)過5分頻得到200HZ信號,最后將分頻得到的200HZ信號作為分頻1HZ的時鐘,經(jīng)過200分頻得到1HZ的信號。設(shè)計框圖如下圖5所示。 2分頻 5分頻 1kHZ信號(clk) 500HZ(f500hz) 200HZ(f200hz) 1HZ(f1hz) 200分頻 圖5 分頻信號框圖 在程序設(shè)計的過程中,在復(fù)位信號rst為高電平時分頻器工作,輸入信號為1kHZ的高頻信號,分別經(jīng)過2分頻、5分頻、200分頻得到f500HZ的500HZ信號、f200HZ的200HZ信號和f1HZ的1HZ信號。仿真結(jié)果如下圖6所示。 圖6 分頻信號結(jié)果仿真圖 從仿真圖中可以看到,在rst為高電平時分頻過程開始,f500HZ、f200HZ和f1HZ也與預(yù)期的輸出結(jié)果一樣。 3.3 秒表模塊 秒表模塊實現(xiàn)秒表功能,在實現(xiàn)的過程中,通過改變自動工作模式下的時鐘頻率來實現(xiàn)秒表的功能。即按動start鍵鬧鐘開始工作,再次按動start鍵,鬧鐘便停止工作。由于秒表模塊比較簡單,流程圖在此省略。 根據(jù)分析,在verilog HDL實現(xiàn)過程中,clk作為時鐘正常工作時候的頻率,f500hz為秒表工作時候的頻率,仿真結(jié)果如下圖7所示。 圖7 秒表仿真模塊 由圖中可以看出,根據(jù)start高低電平的變化,時鐘在正常工作與秒表之間相互轉(zhuǎn)換。 3.4 鬧鐘模塊 鬧鐘模塊實現(xiàn)的是鬧鐘的設(shè)置及鬧鐘所設(shè)定的時間到之后的響鈴提示。鬧鐘模塊的設(shè)置主要思想是由控制鍵來設(shè)置數(shù)字鐘的鬧鐘響的時間,經(jīng)過與當(dāng)前數(shù)字鐘實時時間的比較,來決定鬧鐘提醒的時間。設(shè)計框圖如下圖8所示。 hour0 hour1 minute0 minute1 hour_set0 hour_set1 minute_set0 minute_set1 設(shè)置時間與當(dāng)前時間的比較 不相等 相等 con_alarm 0 1 鬧鐘不響 alarm=0 鬧鐘響 alarm=1 圖8 鬧鐘模塊設(shè)計框圖 在verilog HDL實現(xiàn)的過程中,由SW1、SW2兩個調(diào)整鍵來實現(xiàn),其中SW1為移位控制鍵,即按SW1一次,將移位一次,閃爍顯示當(dāng)前設(shè)置為數(shù)字,SW2為當(dāng)前位的鬧鐘數(shù)字設(shè)置,每按SW2一次,當(dāng)前數(shù)字設(shè)置位數(shù)字增加1,每一位上數(shù)字變化范圍由當(dāng)前位循環(huán)上限決定,不會超出范圍。EN為設(shè)置使能端,為1有效。Hour1、hour0、minute1和minute0分別為當(dāng)前時間每個位上顯示的數(shù)字,hour_set1、hour_set0、minute_set1和minute_set0為與當(dāng)前時間所對應(yīng)的每一位上設(shè)置的時間顯示,f200hz為鬧鐘設(shè)置過程中顯示閃爍的頻率。Con_alarm為鬧鐘響鈴的控制鍵,其值為1時,表示鬧鐘已設(shè)置,并且在鬧鐘響的時候,如果設(shè)置其值為0,則鬧鐘關(guān)閉。Alarm為鬧鐘響鈴提示輸出,即設(shè)定時間到時alarm值為1,否則為0。Alarmclock_disp_select為鬧鐘設(shè)置中位選信號,為4位reg型變量,其值采用獨熱編碼,為1000、0100、0010和0001分別表示設(shè)置過程中hour1、hour0、minute1和minute0四個位。其仿真結(jié)果如下圖9所示。 圖9 鬧鐘模塊仿真示意圖 由于設(shè)置波形輸入的時候如果調(diào)整過多,將不容易看出仿真結(jié)果的正確與否,所以圖中輸入比較簡單,以便可以更好地分析仿真結(jié)果。由圖中可以看出,經(jīng)過SW1的兩次調(diào)整,位選信號alarmclock_disp_select的值為0010,表示此時的設(shè)置位為hour_set0位,SW2鍵將其值設(shè)置為0001,其他位均為0000,然后在與當(dāng)前時鐘時間相等的情況下,并且在con_alarm值為1的時候鬧鐘響,即alarm值輸出為1,在當(dāng)前時間與鬧鐘時間仍然相等的情況下,將鬧鐘控制鍵con_alarm值設(shè)置為0,鬧鐘停止,即alarm值為0。很好的完成了鬧鐘的功能。 3.5 時間設(shè)置模塊 時間設(shè)置模塊實現(xiàn)的功能為通過按鍵調(diào)節(jié)可以對當(dāng)前時間進行手動控制。其主要是在時間設(shè)置使能端有效地情況下通過SW1和SW2兩個按鍵對數(shù)字鐘的小時和分鐘數(shù)進行調(diào)節(jié)。Disp_drive為設(shè)置中的顯示控制,即通過SW1對位的調(diào)整,Disp_drive隨之變化。SW2為對每一位上的數(shù)字在其范圍內(nèi)進行加1調(diào)節(jié),其調(diào)節(jié)過程與鬧鐘模塊相同。Disp_drive取值000、001、010和011分別對應(yīng)hour1、hour0、minute1和minute0的設(shè)置。Quartus下仿真結(jié)果如圖10所示。 圖10 時間設(shè)置模塊仿真效果 圖中,hour_set0、hour_set1、minute_set0和minute_set1為設(shè)置后的時間??梢钥吹?,當(dāng)前給的hour0為0010,hour1的值0001,在SW1經(jīng)過一次高電平之后,disp_drive的值變?yōu)?01,對hour0進行設(shè)置,加1之后hour_set0變?yōu)?001,SW1再按一下,變?yōu)?010,在SW2兩次高電平之后,SW1的值變?yōu)?,此時對分的高位進行加1設(shè)置,依此類推。 3.6 報時模塊 整點報時模塊的主要功能為仿中央人民廣播電臺整點報時信號,即從59分50秒起每隔2秒發(fā)出一次低音“嘟”信號,將其定義為500HZ的低頻信號,到達(dá)整點(00分00秒時),發(fā)一次高音“噠”信號,其響聲為高頻1kHZ信號。 由于整點報時程序比較簡單,所以框圖省略。為了程序簡化又與其他模塊有較好的兼容性,用minute、second分別表示minute1、minute0和second1,second0經(jīng)過位拼接之后的分和秒的當(dāng)前顯示時間。F1khz為到達(dá)整點之后的高音頻率,f500hz為59分50秒、52秒、54秒、56秒和58秒時的低音頻率,radio則為到達(dá)時間時的報時輸出。仿真圖如下圖11所示。 圖11 整點報時模塊仿真效果圖 從圖中可以看出,從59分50秒開始,輸出的radio開始以f500hz的頻率報時,當(dāng)?shù)竭_(dá)00分00秒時,輸出信號頻率為f1khz,到達(dá)00分01秒的時候之后便變?yōu)?,符合設(shè)計要求。 3.7 控制顯示模塊 控制顯示模塊在整個數(shù)字鐘的設(shè)計中起著非常重要的作用。它的作用是將時間等數(shù)據(jù)用數(shù)碼管顯示的控制和數(shù)據(jù)傳輸模塊,包括數(shù)據(jù)的傳輸以及BCD碼譯碼等。通過幾個控制使能端將其不同功能時的時間在數(shù)碼管上顯示出來。本模塊中端口定義比較多,下面是其所對應(yīng)的功能。 Time_EN:時間自動模式工作使能信號; Timeset_EN:時間設(shè)置使能信號; Stopwatch_EN:秒表使能信號; Alarmclock_EN:鬧鐘設(shè)置使能信號; Radio_EN:整點報時使能信號; Time_disp_select:時間顯示位選信號; Alarmclock_disp_select:鬧鐘設(shè)置的顯示位選信號; Disp_select:顯示位選信號輸出; Disp_data:經(jīng)過譯碼之后顯示的數(shù)據(jù)。 程序設(shè)計中,各使能端信號為1表示執(zhí)行該功能,以時間自動工作模式使能信號有效為例說明,當(dāng)Time_EN為1時,首先將時間顯示位選信號isp_select的值賦給顯示位選信號disp_select輸出,定義time_disp_select的狀態(tài)一共有6個,分別為100000、010000、001000、000100、000010和000001,其在各狀態(tài)下分別依次表示將hour0、hour1、minute0、minute1、second0和second1的值賦給data,用case語句來實現(xiàn),其實現(xiàn)語句如下: if((Time_EN == 1b1) begin disp_select <= time_disp_select; case(time_disp_select) 6b100000: Data <= hour1; 6b010000: Data <= hour0; 6b001000: Data <= minute1; 6b000100: Data <= minute0; 6b000010: Data <= second1; 6b000001: Data <= second0; default: Data <= 4b0; endcase 在quartusⅡ下仿真圖12如下: 圖12 控制顯示模塊當(dāng)前時間使能端有效時譯碼的顯示 從圖中可以看出,在第一個時鐘周期內(nèi),時間顯示位選信號time_disp_select的值為000000,此時應(yīng)執(zhí)行case語句的default,Data的值為0;在第二個時鐘周期內(nèi),time_disp_select的值為000001,此時對應(yīng)其最后一種狀態(tài),將second0的值賦給Data,即Data的值為0110,從圖中看,仿真結(jié)果正確,disp_data表示的是將當(dāng)前數(shù)據(jù)譯碼顯示之后七段數(shù)碼管的顯示,所以在第一個周期內(nèi)值為1111110,表示值為0,與Data所表示的數(shù)對應(yīng)。依次類推,可將Data的值全部表示出來。顯示譯碼數(shù)據(jù)段主要程序如下: case(Data) 4b0000: disp_data<=7b1111110; 4b0001: disp_data<=7b0110000; 4b0010: disp_data<=7b1101101; 4b0011: disp_data<=7b1111001; 4b0100: disp_data<=7b0110011; 4b0101: disp_data<=7b1011011; 4b0110: disp_data<=7b1011111; 4b0111: disp_data<=7b1110000; 4b1000: disp_data<=7b1111111; 4b1001: disp_data<=7b1111011; default: disp_data<=7b0; endcase 顯示譯碼程序說明了0到9十個數(shù)在7段數(shù)碼管中所對應(yīng)的值,在case語句里面最重要的是一定不能忘了default,否則仿真會發(fā)生所不希望看到的 結(jié)果。下圖13為鬧鐘設(shè)置使能有效時仿真結(jié)果。 圖13 控制顯示模塊當(dāng)鬧鐘設(shè)置使能信號有效時譯碼顯示 從圖中可以看出,當(dāng)只有鬧鐘使能信號alarmclock_EN有效時,其七段數(shù)碼管顯示結(jié)果,與數(shù)字鐘自動工作使能端的區(qū)別為鬧鐘設(shè)置使能端有效時只需對hour0、hour1、minute0和minute1進行設(shè)置,所以鬧鐘設(shè)置顯示位選信號alarmclock_disp_select的狀態(tài)只有4個,由于其同樣需要將值賦給disp_select,為了統(tǒng)一期間,其值也設(shè)為6位,其4個狀態(tài)分別為100000、010000、001000和000100。其他與自動工作模式相同。 3.8 頂層模塊 將以上設(shè)計的各個模塊組合起來,就可以得到多功能數(shù)字鐘的整體仿真結(jié)果。其主要作用是將各個模塊銜接起來,圖14為時鐘正常工作模式下Quartus仿真結(jié)果。 圖14 整體仿真結(jié)果 4 總結(jié) 4.1 本次作業(yè)遇到的問題 在做本次作業(yè)中,遇到的問題主要有以下幾個方面: (1)軟件的安裝與學(xué)習(xí)。在軟件的安裝過程中,首先通過自己從網(wǎng)上下載軟件安裝,第一次安裝的時候未經(jīng)破解,導(dǎo)致安裝的軟件雖然裝上了,但是打不開,無法使用。軟件的學(xué)習(xí)過程中,首先經(jīng)過上課講解,自己從網(wǎng)上下視頻的學(xué)習(xí),運行了幾個書上的小程序,對軟件進行了熟悉。 (2)由于Verilog HDL這門語言對自己來說屬于一個從未接觸過的東西,所以學(xué)習(xí)起來比較困難。本次作業(yè)選擇的題目為多功能數(shù)字鐘,前面是資料的搜集與設(shè)計思路的理清,再有了一定的基礎(chǔ)之后,開始對整個大的模塊進行分模塊分析設(shè)計。 (3)在作業(yè)的過程中,遇到了許多的問題,首先發(fā)現(xiàn)自己對軟件的運用上存在的一些問題,如剛開始的時候沒有生成功能網(wǎng)表,導(dǎo)致最后運行出錯;還有沒有選功能仿真的時候,波形出現(xiàn)了一些毛刺和延時。 (4)以為自己上課聽懂了阻塞與非阻塞賦值的區(qū)別,結(jié)果的程序的書寫上還是出現(xiàn)的問題,比如在秒表模塊中,用的電平觸發(fā),剛開始的時候時候用的阻塞賦值,發(fā)現(xiàn)仿真波形有延時,以為是阻塞賦值的問題,將阻塞賦值改為了非阻塞賦值,延時問題還是沒有解決,才發(fā)現(xiàn)進行的是時序仿真。這是由于自己當(dāng)時還是沒有深刻的理解兩者之間的區(qū)別,才造成的誤解,給解決問題帶來了一定的困擾。 (5)仿真過程中不夠細(xì)心,比如在整點報時模塊,波形輸入的時候,將minute與second的值設(shè)置反了,造成找了一下午的問題,radio就是不報時,后來發(fā)現(xiàn)問題的時候,覺著特別不可思議,還把程序改了半天。 (6)在控制顯示模塊,波形文件仿真的過程中,由于其輸入輸出接口比較多,為了看得更清楚期間,在數(shù)字鐘正常工作模式下顯示的過程中,將鬧鐘設(shè)置使能端去掉了,結(jié)果在仿真的過程中data跟disp_data就是沒有值,后來發(fā)現(xiàn)原因是在將鬧鐘使能端去掉之后,不確定鬧鐘使能端是否有效。造成沒有顯示結(jié)果,后來把鬧鐘使能段加上之后并將其置為0,仿真結(jié)果正確。 作業(yè)過程中,遇到的小問題不計其數(shù),在多方努力之下,問題基本解決,這里就不一一列舉??偨Y(jié)出的寶貴經(jīng)驗就是要多看書,學(xué)會自己解決問題,一般的問題在看書找資料之后基本都能解決;還有就是一定要細(xì)心,這樣可以避免很多不必要的麻煩。 4.2 建議和總結(jié) 首先非常感謝老師在每周末還那么辛苦的給我們上課,真的使我學(xué)到了很多的東西,在此對老師致以深深的謝意! 對老師的建議就是可以在剛開始上課的時候就可以給同學(xué)布置一些小的作業(yè),然后可以讓同學(xué)慢慢接觸一下軟件,學(xué)一點淺顯的編程,這樣在最后寫大作業(yè)的時候就不會感覺無從下手,以便起到一個循序漸進的作用。 附件 1.小時計數(shù)器模塊 module hour_counter(EN,clk,hour_data1,hour_data0,zox); input clk,EN; //時鐘與使能端 output [3:0] hour_data1,hour_data0;//小時的高位和低位 output zox; //上下午指示模塊 reg [3:0] hour_data1,hour_data0; reg zox; always @(posedge clk) begin if(EN == 1b1) begin if(hour_data0 < 4b0011) hour_data0 <= hour_data0 + 4b1; else begin zox <= 1b0; hour_data0 <= 4b0; if(hour_data1 < 4b0001) hour_data1 <= hour_data1 + 4b1; else begin hour_data1 <= 4b0; zox <= 1b1; end end end end endmodule 2.分秒計數(shù)器模塊 module minute_counter(EN,clk,minute_data1,minute_data0,EO); input clk,EN; output [3:0] minute_data1,minute_data0; 分高位、低位 output EO; //進位輸出端 reg [3:0] minute_data1,minute_data0; reg EO; always @(posedge clk) //上升沿觸發(fā) begin if(EN == 1b1) //使能端為1有效 begin if(minute_data0 < 4b1001) minute_data0 <= minute_data0 + 4b1; else begin EO <= 1b0; minute_data0 <= 4b0; if(minute_data1 < 4b0101) minute_data1 <= minute_data1 + 4b1; else begin minute_data1 <= 4b0; EO <= 1b1; end end end end endmodule 3. 分頻模塊 module fdiv(clk,rst,f500hz,f200hz,f1hz); input clk,rst; //1KHz 輸入 output f500hz,f200hz,f1hz; //分頻出500HZ、200HZ、1HZ輸出 reg f500hz,f200hz,f1hz; integer CNT1=0,CNT2=0; //兩個常數(shù)變量,分頻技術(shù)用 always @(posedge clk) //2分頻 begin if(!rst) f500hz=0; else f500hz=~f500hz; end always @(posedge clk) //5分頻 if (!rst) begin f200hz<=0; CNT2<=0; end else begin if(CNT2==4) begin CNT2 <= 0; f200hz <=~f200hz; end else CNT2 <= CNT2+1; end always @(posedge f200hz) //將200HZ信號200分頻為1HZ if (!rst) begin f1hz<=0; CNT1<=0; end else begin if(CNT1==199) begin CNT1 <= 0; f1hz <=~f1hz; end else CNT1 <= CNT1+1; end endmodule 4.秒表模塊 module stopwatch(clk,f500hz,start,F_out); input clk,f500hz,start; //start為控制秒表信號 output F_out; //輸出,秒表工作方式 reg F_out; always @(start or clk or f500hz) begin case(start) 1b0:F_out=clk; 1b1:F_out=f500hz; default:F_out=1b0; endcase end endmodule 5.鬧鐘模塊 module alarmclock(clk_200hz,EN, SW1,SW2, hour1,hour0,hour_set1,hour_set0, minute1,minute0, minute_set1,minute_set0, alarm,control_alarm, alarmclock_disp_select); input EN,SW1,SW2,clk_200hz; //SW1、SW2為鬧鐘設(shè)置鍵 input [3:0] hour1,hour0,minute1,minute0;//顯示當(dāng)前時間 input control_alarm; //鬧鐘控制鍵 output alarm; //鬧鐘響鈴輸出 output [3:0] alarmclock_disp_select; //鬧鐘設(shè)置位選信號 output [3:0] hour_set1,hour_set0,minute_set1,minute_set0; reg [3:0] alarmclock_disp_select; reg alarm; reg [3:0] hour_set1,hour_set0; //存放設(shè)置的小時 reg [3:0] minute_set1,minute_set0; //存放設(shè)置的分 reg [2:0] disp_drive; //設(shè)置鬧鐘時間時,數(shù)碼管顯示的動態(tài)位選擇 //鬧鐘一直工作(設(shè)置的鬧鐘時間與當(dāng)前時間比較) always begin if((hour_set1 == hour1)&&(hour_set0 == hour0) &&(minute_set1 ==minute1)&&(minute_set0==minute0)&&(control_alarm==1)) alarm <= 1b1; //相等,鬧鐘響 else if(control_alarm==0) alarm <= 1b0; //不相等,輸出1 end //鬧鐘設(shè)置中,按SW1一次,將移位一次,顯示當(dāng)前設(shè)置位 always @(posedge SW1) begin if(EN == 1b1) begin if(disp_drive != 3b101) disp_drive <= disp_drive + 3b1; else disp_drive <= 3b000; end end //當(dāng)前位的鬧鐘數(shù)字設(shè)置,按SW2一次,數(shù)字增加1 always @(posedge SW2) begin case(disp_drive) 3b000: begin //000時,設(shè)置小時的高位 if(hour_set1 < 4b0010) hour_set1 <= hour_set1 + 4b1; else hour_set1 <= 4b0; end 3b001: begin //001時,小時低位 if((hour_set1 < 4b0010)&&(hour_set0 < 4b1001)) hour_set0 <= hour_set0 + 4b1; else if((hour_set1==4b0010)&&(hour_set0 < 4b0100)) hour_set0 <= hour_set0 + 4b1; else hour_set0 <= 4b0; end 3b010: begin //010時,分鐘高位 if(minute_set1 < 4b0101) minute_set1 <= minute_set1 + 4b1; else minute_set1 <= 4b0; end 3b011: begin //011時,分鐘低位 if(minute_set0 < 4b1001) minute_set0 <= minute_set0 + 4b1; else minute_set0 <= 4b0; end endcase end //閃爍顯示 always @(posedge clk_200hz) //設(shè)置時閃爍頻率 begin case(disp_drive) 3b000: alarmclock_disp_select <= 6b1000; 3b001: alarmclock_disp_select <= 6b0100; 3b010: alarmclock_disp_select <= 6b0010; 3b011: alarmclock_disp_select <= 6b0001; default: alarmclock_disp_select <= 6b0000; endcase end endmodule 6.時間設(shè)置模塊 module timeset( TimeSet_EN, SW1,SW2,disp_drive, hour1,hour0, minute1,minute0, hour_set1,hour_set0,minute_set1,minute_set0 ); input TimeSet_EN; input SW1,SW2; input [3:0] hour1,hour0; input [3:0] minute1,minute0; output [3:0] hour_set1,hour_set0; output [3:0] minute_set1,minute_set0; output [2:0] disp_drive; reg [3:0] hour_set1,hour_set0; reg [3:0] minute_set1,minute_set0; reg [2:0] disp_drive; //初始化 initial begin hour_set1 <= hour1; hour_set0 <= hour0; minute_set1 <= minute1; minute_set0 <= minute0; end always @(posedge SW1) //手動設(shè)置使能 begin if(TimeSet_EN == 1b1) begin if(disp_drive < 3b101) disp_drive <= disp_drive + 3b1; else disp_drive <= 3b0; end end always @(posedge SW2) begin case(disp_drive) 3b000: begin //小時的高位 if(hour_set1 < 4b0010) hour_set1 <= hour_set1 + 4b1; else hour_set1 <= 4b0; end 3b001: begin //小時的低位 if(hour_set0 < 4b1001) hour_set0 <= hour_set0 + 4b1; else hour_set0 <= 4b0; end 3b010: begin //分的高位 if(minute_set1 < 4b0101) minute_set1 <= minute_set1 + 4b1; else minute_set1 <= 4b0; end 3b011: begin //分的低位 if(minute_set0 < 4b1001) minute_set0 <= minute_set0 + 4b1; else minute_set0 <= 4b0; end default:begin end endcase end endmodule 7.報時模塊 Module Radio(alarm_radio,minute1,minute0,second1,second0, minute,second, f1khz,f500hz); input f1khz,f500hz; input[3:0]minute1,minute0,second1,second0; input[7:0]minute,second; output alarm_radio; //拼接之后時間 reg alarm_radio; //報時輸出信號 always@(minute1 or minute0 or second1 or second0) begin reg [7:0] minute,second; {minute[7:0]}={minute1[3:0],minute0[3:0]}; //分拼接 {second[7:0]}={second1[3:0],second0[3:0]}; //秒拼接 end always@(minute or second) if(minute==8h59) //59分鐘時 case(second) //秒為50、52、54、56、58低音報時 8h50, 8h52, 8h54, 8h56, 8h58:alarm_radio<=f500hz; default:alarm_radio<=1b0; endcase else if(minute==8h00&&second==8h00) //00分00秒高音報時 alarm_radio<=f1khz; else alarm_radio<=1b0; endmodule 8.控制顯示模塊 module disp_data_mux(Time_EN,TimeSet_EN,Stopwatch_EN, time_disp_select,Alarmclock_EN, alarmclock_disp_select, hour1,hour0,minute1,minute0,second1,second0, disp_select,disp_data,Data); input Time_EN,TimeSet_EN,Stopwatch_EN; input [5:0] time_disp_select; input Alarmclock_EN; input [5:0] alarmclock_disp_select; input [3:0] hour1,hour0,minute1,minute0,second1,second0; output [5:0] disp_select; output [6:0] disp_data; output[3:0] Data; reg [5:0] disp_select; reg [6:0] disp_data; reg [3:0] Data; always @(Time_EN, TimeSet_EN,Stopwatch_EN,time_disp_select, Alarmclock_EN,alarmclock_disp_select,disp_select, hour1,hour0,minute1,minute0,second1,second0) begin //時鐘,秒表顯示 if((Time_EN || TimeSet_EN || Stopwatch_EN) == 1b1) begin disp_select <= time_disp_select; case(time_disp_select) 6b100000: Data <= hour1; 6b010000: Data <= hour0; 6b001000: Data <= minute1; 6b000100: Data <= minute0; 6b000010: Data <= second1; 6b000001: Data <= second0; default: Data <= 4b0; endcase end else if(Alarmclock_EN == 1b1) //鬧鐘設(shè)置顯示 begin disp_select <= alarmclock_disp_select; case(alarmclock_disp_select) 6b100000: Data <= hour1; 6b010000: Data <= hour0; 6b001000: Data <= minute1; 6b000100: Data <= minute0; default: Data <= 4b0; endcase end case(Data) //顯示數(shù)據(jù)譯碼 4b0000: disp_data <= 7b1111110; 4b0001: disp_data <= 7b0110000; 4b0010: disp_data <= 7b1101101; 4b0011: disp_data <= 7b1111001; 4b0100: disp_data <= 7b0110011; 4b0101: disp_data <= 7b1011011; 4b0110: disp_data <= 7b1011111; 4b0111: disp_data <= 7b1110000; 4b1000: disp_data <= 7b1111111; 4b1001: disp_data <= 7b1111011; default: disp_data <= 7b0; endcase end endmodule- 1.請仔細(xì)閱讀文檔,確保文檔完整性,對于不預(yù)覽、不比對內(nèi)容而直接下載帶來的問題本站不予受理。
- 2.下載的文檔,不會出現(xiàn)我們的網(wǎng)址水印。
- 3、該文檔所得收入(下載+內(nèi)容+預(yù)覽)歸上傳者、原創(chuàng)作者;如果您是本文檔原作者,請點此認(rèn)領(lǐng)!既往收益都?xì)w您。
下載文檔到電腦,查找使用更方便
9.9 積分
下載 |
- 配套講稿:
如PPT文件的首頁顯示word圖標(biāo),表示該PPT已包含配套word講稿。雙擊word圖標(biāo)可打開word文檔。
- 特殊限制:
部分文檔作品中含有的國旗、國徽等圖片,僅作為作品整體效果示例展示,禁止商用。設(shè)計者僅對作品中獨創(chuàng)性部分享有著作權(quán)。
- 關(guān) 鍵 詞:
- 數(shù)字 verilog
鏈接地址:http://www.3dchina-expo.com/p-6615843.html