P1-Verilog簡單部件與狀態機


通過本文,您的收獲可能有:從課下部分,了解一些基本部件搭建時可能遇到的坑點,稍微深入一點理解兩種狀態機的區別;從課上測試部分,可以了解重點的考察內容,明白設計時狀態機的類型在測試中的重要性。

課下測試部分:

課下測試主要考察了splitter的實現,ALU的實現,格雷碼計數器的實現,擴位器的實現,以及合法表達式判別的有限狀態機問題。本次課下部分比較簡單,正好讓下周工作量爆炸的我緩一口氣。

1.splitter實現:

  實現的方式就是用拼接運算符(大括號)直接把信號拼起來。需要注意的一點是,如果發現提交之后是CE,那么一定要檢查一下是不是交錯了文件,以及,文件名是不是正確。神TMD知道我之前就寫過一個叫spliter的東西,然后交上去了,后來反應過來好像日期對不上;接着我又交現在的,還是CE,過了好久我才反應過來:我文件名字拼寫從很久之前起就是錯的。真是要命的低級失誤!考慮到課上測試的時候會有3分鍾保護時間不讓提交,所以這樣的失誤會耽誤時間,也會很影響心情,一定要避免。

2.ALU的實現:

  關於如何將無符號數變成有符號數,請移步:https://blog.csdn.net/adaliu1998/article/details/80459262

  在verilog中運算時,如果同時出現有符號數和無符號數,有符號數會被處理為無符號數進行運算;所以當{hi,lo}不加signed時,$signed(A)的有符號化無效,仍然是作為無符號A

3.擴位器的實現:

  加強版的第一題,仍然利用拼接運算符即可。不會寫if_else或者case的話還是最好回歸課本,把前七章重新學一遍,會省很多事情。室友昨天因為case沒有放在過程塊always中,debug好久,這在課上可是耽誤不得!熟悉基本語法很重要!可以通過hdlbits.01xz.net上的練習來熟悉語法。

4.格雷碼計數器:

  也是屬於語法回顧題,考察了case語句。坑點可能是reset忘記給overflow置零,或者是在溢出之后回到0的時候由於不合理的邏輯,導致overflow被誤置為0。同步復位信號的always塊的最開始只需要寫always @(posedge clk)即可,如果加上了其他東西,比如寫成了always @(posedge clk,clr)之類的,就不是同步復位了,有興趣的可以單步調試一下,會發現出了意想不到的錯誤。另外,記得初始化(其實自己測試的時候應該就能想起來應該先初始化,不然會出現不定值)。

5.表達式狀態機:

 

 

 

 

 

 

 

  這個狀態機我考慮了四個狀態:沒有字符的empty狀態,是合法表達式的yes狀態,必定不是表達式的hopeless狀態(比如上來就是個符號,或者途中出現連續數字,或者出現連續符號,更有甚者,出現題目要求之外的符號),還有希望是表達式的hope狀態(比如從1變成1+的這種可以通過加數字變成合法表達式的情況)。狀態想好之后,轉移也比較容易能寫出來了。不清楚評測數據有沒有輸入非法字符,為了穩重,還是要考慮0-9以及+*之外的字符。

  異步置位的寫法:要clr為1,就要把狀態置為0,另外,本題的數據是在時鍾上升沿才會傳過去的,綜上可知,always應該寫成always @(posedge clk,posedge clr),如果加了in的變化(always @(posedge clk,posedge clr,in)),也會出現上一個題中說到的意想不到的錯誤,可以自行嘗試。//2019.10.21補充,為什么要在觸發條件里面寫posedge clr呢?因為我們要求異步復位,也就是說clr只要變為1,則從變成1的那一刻起就應該馬上重置。如果把posedge clr寫成了clr,在ISE語法檢查的時候不會報錯,在HDLBits上會CE,如果又干脆不寫clr的變化,就成了同步復位,如圖:

 

 

至於always @(posedge clk,posedge clr)與always @(posedge clk,clr)在ISE中波形的區別,這屬於很細節的問題了,有意者可以自行設計testbench進行探索。

 

 

 

 

  本題我犯了一個很沙雕的錯誤:狀態的編碼采用獨熱編碼是4位,但是我定義的state變量最開始是reg state;事實上應該是reg [3:0] state。這個地方如果錯了,測試的時候會發現很多該變化狀態的時候沒有變化。以后一定要引以為戒啊!!!

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

備考P1階段經驗總結:

做了hdlbits.01xz.net上的問題:Lemmings2 ,以練習有限狀態機的verilog實現,發現做該題的時候出現的問題蠻多,且十分典型,值得反省:

1.一個玄學問題:if-else報錯但case沒問題。這個問題出現在case中嵌套使用if-else時,至今也不知道為什么錯了,只知道只要改成case就完全沒問題。不管了

2.信號位數問題:這個問題在之前P1課下測試里面已經犯過了,這次犯得更難以發現一點:賦值時rightmove=3'b001寫成了rightmove=001,然后就會出現以下報錯:

 

 

 重要的是后兩行報錯信息。在ISE中並不會給出這種報錯,而這個網站為了幫助學習給出了這個報錯,才讓我意識到可能是賦值時漏寫了位數和進制。推薦把一些常用的數都聲明成parameter型,然后仔細檢查兩遍parameter,仔細考慮一下各個parameter的命名怎樣好,這樣在以后賦值的時候就不會出現這種難以察覺的問題了。

3.reset。沒錯又是復位,這次不是不會同步異步,而是干脆沒寫。。。這個在自己做測試的時候還是容易發現的。

4.初始化是個好東西,希望你寫的時候記得它。

5.verilog下的moore型與mealy型狀態機:

具體如何去寫,參見ISE模板(這幾天見到的版本太多已經有些凌亂了)

用verilog的時候我沒有明確區分過,因為我把所有的邏輯都集中在case里面了,這樣很不好!還記得P0的時候有很多同學因為狀態機的類型錯誤,吃了大虧,所以要慌,問題很大!之后兩天的訓練里面要試着把狀態轉移,狀態保存和輸出邏輯分開寫。

考慮下面的狀態機:(圖片來自P1教程部分)

 

 猛的一看,這好像是個mealy型狀態機,因為它寫的代碼看起來是輸入和狀態共同決定輸出。但是,仔細想一下,如果現在是3狀態,即state=3被存到了狀態存儲電路中,狀態轉移電路里面需要轉換的是state=3與一個輸入in,時鍾上升沿時,in與狀態轉移電路里的state (=3)算出來一個新狀態,然后,新狀態瞬間傳到了狀態存儲電路里面,在這一瞬間之后,狀態存儲電路就被鎖死了不可變了,而我們的輸出,就是由這時候被鎖住的狀態決定的。綜上所述,這是一個moore型狀態機(ISE模板中便是以這個給出的)

更新:關於mealy型狀態機

Mealy型狀態機的輸出不僅僅在時鍾上升沿時改變,而Moore型狀態機的輸出只在時鍾上升沿時改變。所以模板中輸出使用的assign

課上測試:

第一題:考察有符號數的比較,四位有符號數輸入,輸出較大的一個。有符號數輸入的是補碼。這個需要了解補碼是怎么回事兒,正數的補碼是本身,負數的補碼是這個數除了符號位之外的位取反加1。考試的時候為了保險起見,我先寫了一個簡單的輸入輸出,寫了一個tb,仿真了一下,把輸出調成有符號數,嗯,的確是這個規則(突然變得有底氣了)。然后就是比較了。這個先比符號位,比不出來再從高到低逐位比(不知道為什么題目不讓用>,<,<=號)。寫個tb試試各種情況即可。

經驗:有不太確定的知識點可以利用工具進行一波驗證,比如上次的算數右移(用Logisim自帶移位器造輸入輸出看輸出規律)和這次的原碼補碼。

第二題:又是賣東西的狀態機,和p0的差不多,只是題目要求有點繞。注意退幣的兩種情況:輸入2'b11或者大於等於2元。注意reset是異步復位,前面已經介紹過異步復位辦法,所以總體不難寫。讀題多花點時間是應該而且有必要的,這個題的退幣以及狀態轉移是需要仔細讀題的,有時還需要仔細讀題目給出的測試波形(本題的測試波形能讀得和自己的理解一樣的話,題意理解上就沒什么問題了)。寫代碼時注意上面說的易錯點,並做足下面的測試,有很大希望不用被卡等待時間。

經驗:題意看不懂時,逐步分析題給波形。

第三題:正則表達式匹配(此處是冪函數的格式),和p1的差不多,就是狀態有所增加(我寫了9種,可能多了)。記憶版題面是匹配滿足 ^[+-]?(\d+\*)?x(\^[+-]?\d+)? 的表達式。根據題意,從none開始,考慮下面幾種輸入:+,-,數字,^,x,*,即可逐步找到每個可能出現的狀態。常數較多,寫parameter比較好。

經驗:建立狀態機要慢,coding手速要快。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM