iT邦幫忙

2024 iThome 鐵人賽

DAY 2
0
佛心分享-SideProject30

RISC-V CPU 設計與實作系列 第 4

[Day 04] Verilog 與 循序電路

  • 分享至 

  • xImage
  •  

數位電路大致上分成 2 種,組合電路 (Combinational Circuit) 和循序電路 (Sequential Circuit)。

當一個電路通電,組合電路就開始運作,馬上就可以得到正確的輸出,當外部輸入相同,則每次的輸出都會一樣,就像上一篇文章提到的多工器等。但是循序電路的運作方式比較不一樣,即便外部輸入都是相同的,循序電路的輸出會根據前一次的運算結果而有不同。

計數器

「計數器」是一個循序電路中很經典的例子。以一個倒數計數器來說,第一次的運算結果是 N ,下一次會變成 N-1,直到變成 0 為止。但是我們該怎麼區分現在是進到了計數器中的第幾個狀態呢?簡單來說,我們會根據時間來決定當前的結果,時間在電路設計中有一個更專業的術語叫做「時脈」。

試著用 Verilog 來實作 10 ~ 0 的倒數計數器吧!

先假設我們有變數 clk, reset, cnt,而 reset 是用來告知硬體中的暫存器需要被初始化。

module DCounter (
    input clk,
    input reset
);
    reg [3 : 0] cnt;
    // reset counter
    // counter body
endmodule 

因為計數器需要被告知從何處開始倒數,所以我們來處理初始化的部分。Reset 的方式可以分成 2 種:同步 (synchronous) 和非同步 (asynchronous) 。同步的意思是即便我們接收到 reset 訊號,我們也要根據時脈的數值,才可以決定是否重置。非同步的意思則是不論時脈的數值為何,當我們接收到 reset 訊號,就會執行重置。以下我們示範「非同步重置」。

// reset counter
always @(posedge reset) cnt = 4'd10;

此處以 posedge reset 作為 reset 啟動的條件,意思是當 reset 訊號從低電位變為高電位的瞬間,變數 cnt 會被初始化為 10

接著,要來實作計數器的主體。當計數器數到 0 時,計數器會回到 10 ,其餘情形計數器會做「遞減」。

// counter body
always @(posedge clk) begin
    if (cnt == 4'd0) cnt <= 4'd10;
    else cnt <= cnt - 1;
end

特別注意的是此處的「賦值」使用的是 <= ,和之前使用的 = 較為不同。這個議題叫做 blockingnonblocking,我們會在下一篇文章提到。若使用錯誤,結果會完全不同。


上一篇
[Day 03] 淺談 Verilog
下一篇
[Day 05] Blocking & Nonblocking
系列文
RISC-V CPU 設計與實作7
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言