目錄
2、Block Memory Generator Feature
2.2、Selectable Memory Algorithm
2.3、Configurable Width and Depth
2.4、Selectable Operating Mode per Port
2.5、Selectable Port Aspect Ratios
2.6、Optional Byte-Write Enable
1、BRAM 簡介
XILINX 系列的 FPGA ,如果想要做一個 RAM,有兩種方式:
1、使用邏輯資源組成分佈式 RAM,即 Distributed RAM
2、使用 XILINX 專用的 Block RAM,即 BRAM
前者是由 CLB 的 SLICEM 的 LUT 組合而成,構成 RAM 後,可能分佈在不同的地方,具有一定的延遲;
後者是 Block RAM 是內嵌專用的 RAM,是 XILINX 做進 FPGA 內的專用資源,具有更好的時序性能;
這裏我們以 ZYNQ-7000 爲例:
可以看到紅色方框中,標識出了此款 FPGA 的 BRAM 資源,我們也可以瞭解到,一個 BRAM 資源大小爲 36Kbits(注意,這裏是 bits),紅色方框的這款含有 140 個這樣的 BRAM,也就是一共含有 36Kbits * 140 = 4.9Mbits 大小的 BRAM 資源;
在 XILINX 的官方文檔上,介紹這部分的文檔是:
pg058-blk-mem-gen.pdf
有興趣的可以下載來看下;
針對 BRAM 資源的接口形式,主要分爲兩種:
Native:本地 BRAM
AXI4:與 AXI4 總線互聯的 BRAM
這裏更多的來了解一下 Native 類型的 BRAM,等到要用到 BRAM 掛到 AXI 上的時候,再來仔細分析 AXI Interface 的 BRAM;
較爲新的 XILINX 介紹這部分的內容叫 BMG(Block Memory Generator)
2、Block Memory Generator Feature
2.1 Type
按照 BRAM 可以構成的器件類型來分,主要可以分爲如下幾種:
• Single-port RAM : 單口 RAM
• Simple Dual-port RAM:僞雙口 RAM
• True Dual-port RAM:真雙口 RAM
• Single-port ROM :單口 ROM
• Dual-port ROM:雙口 ROM
2.1.0、Signals Descriptions
首先進行信號的描述,常用到信號含義如下表所示:
Signal Name | Direction | Description |
---|---|---|
clka | Input | Port A 的同步時鐘信號 |
addra | Input | Port A 的地址信號 |
dina | Input | Port A 寫操作時候的輸入數據信號 |
douta | Output | Port A 讀操作時候的輸出數據信號 |
ena | Input | Port A 的使能信號,在讀,寫,Rst 的時候需要此信號 |
wea | Input | Port A 的寫使能信號 |
rsta | Input | Port A 的復位信號 |
regcea | Input | Port A 的可選後級輸出寄存器信號 |
clkb | Input | Port B 的同步時鐘信號 |
addrb | Input | Port B 的地址信號 |
dinb | Input | Port B 寫操作時候的輸入數據信號 |
doutb | Output | Port B 讀操作時候的輸出數據信號 |
enb | Input | Port B 的使能信號,在讀,寫,Rst 的時候需要此信號 |
web | Input | Port B 的寫使能信號 |
rstb | Input | Port B 的復位信號 |
regceb | Input | Port B 的可選後級輸出寄存器信號 |
sbiterr | Output | Single-Bit Error 信號 |
dbiterr | Output | Double-Bit Error 信號 |
injectsbiterr | Input | Inject Single-Bit Error: Available only for Zynq-7000 and 7 series ECC configurations. |
rdaddrecc | Output | Read Address for ECC Error output: Available only for Zynq-7000 and 7 series ECC configurations |
eccpipece | Input | ECC Pipe Line Register Clock Enable: Available only for UltraScale architecture-based devices. |
sleep | Input | 動態功耗調整: If sleep pin is High , the Block Memory Generator core is in power saving mode. Available only for UltraScale architecture-based devices |
2.1.1、Single-port RAM
XILINX 官方的 pg058 部分描述了 Single-port RAM 的典型應用,可用於處理器暫存數據的 RAM,或者作爲查找表等;它的圖解如下所示,斜槓的信號爲可選信號,其餘的是必選信號;
CLKA 爲輸入的時鐘信號,時鐘上升沿對數據進行寫入/讀出
DINA 爲寫入的數據總線
DOUTA 爲讀出的數據總線
ADDRA 爲地址總線
ENA 爲使能端,當 ENA 爲 1 的時候,可進行讀寫操作,ENA 爲 0 的時候,無法進行讀寫
WEA 爲寫使能,當 ENA 爲 1 同時 WEA 爲 0 的時候,爲讀操作;當 ENA 和 WEA 同時爲 1 的時候,爲寫操作;
由於只有一組地址總線,故,單口的 RAM 是無法同時進行讀寫操作的,只能讀、寫分開進行;
2.1.2、Simple Dual-port RAM
XILINX 官方的 pg058 部分描述了 Simple Dual-port RAM 的典型應用:Content addressable memories, FIFOs
它的圖解如下所示:
與單口 RAM 不同的是,僞雙口 RAM 輸入有兩路時鐘 : CLKA/CLKB ,獨立的兩組地址信號 ADDRA/ADDRB,Port A 提供 DINA 寫數據總線,作爲數據寫入的入口;Port B 僅僅提供數據讀的功能,讀出的數據爲 DOUTB;
所以僞雙口 RAM 能夠提供同時讀寫 RAM 的功能
2.1.3、True Dual-port RAM
XILINX 官方的 pg058 部分描述了 True Dual-port RAM 的典型應用:多處理器存儲方案,Multi-processor storage
它的圖解如下所示:
真雙口 RAM 提供了獨立的 Port A 和 Port B 的讀寫功能,既可以同時處在讀,也可以同時寫,也可以一個讀一個寫;
2.1.4、Single-port ROM
BRAM 也可以做成 ROM,典型應用是:Program code storage, initialization ROM,如下圖所示
與 Single-port RAM 幾乎相同,唯一不同的是,沒有 DINA 信號,因爲是 ROM,所有不提供寫入;
2.1.5、Dual-port ROM
BRAM 也可以做成 ROM,典型應用是:Single ROM shared between two processors/systems
雙口的 ROM,提供 Port A 和 Port B 兩路讀;
2.2、Selectable Memory Algorithm
使用 XILINX 的 BMG 生成上述類型的 RAM/ROM 的時候,有一個可選項叫做生成的算法,這裏有三種可選的算法:
Minimum Area Algorithm : 面積最優
Low Power Algorithm:功耗最低
Fixed Primitive Algorithm:固定原語
2.3、Configurable Width and Depth
在使用 BMG 生成 RAM 的時候,位寬支持配置從 1 bits ~ 4608 bits,深度支持大於等於 2,具體最大能夠配置出多少 RAM,需要查看當前的器件手冊中包含的 BRAM 的個數;
2.4、Selectable Operating Mode per Port
BRAM 組成 RAM 後的讀寫模式可以分爲三種,並且 Port A 和 Port B 可以獨立配置:
1. Write First Mode
2. Read First Mode
3. No Change Mode
這些 mode 是針對一個 Port 來說的;
2.4.1、Write First Mode
這種模式下,寫操作的優先級高於讀操作,它的時序如下所示:
這個時序很生動的描述了這種 mode :
1、剛剛開始,ENA 信號一直爲 0,即,沒有使能;
2、第一個虛線,也就是 CLKA 的上升沿位置,採到 ENA 爲 1,同時 WEA 爲 0,則代表爲 READ 時序,同時,在這個上升沿,採集到 ADDRA 上爲 aa(ADDRA 爲並行地址總線),那麼就會在獲取到 aa 這個地址中的值後(經過了一點延時),將數據打到 DOUTA[15:0] 上,所以這裏可以看到 DOUTA 上是 MEM(aa),也就是 aa 這個 RAM 地址中存儲的數據;
3、第二個虛線,CLKA 上升沿的時候,同樣會檢測 ENA 和 WEA,此刻,它們都爲 1,則代表 WRITE 時序來了,此刻採集到寫入數據總線 DINA 上的數據爲 1111,地址總線上是 bb,那麼此刻是將地址 bb 的值放到 DOUTA 上呢,還是直接將 DINA 的值放到 DOUTA 上呢,這個 Operating Mode 就是解決這個問題的,在 Write First Mode 的情況下,DINA 的 1111 數據直接被送到了 DOUTA 總線上,同時,MEM(bb) 的內容被寫入 1111,;
4、第三個虛線,CLKA 上升沿的時候,同理,2222 數據被直接寫到 MEM(cc),同時被輸出到 DOUTA 上
5、第四個虛線,CLKA 上升沿的時候,WEA 信號被拉到 0,但是 ENA 信號還是 1,說明當前不存在 WRITE了,只有 READ 時序,那麼會將 ADDRA 上採集到的 dd 地址的數據讀出到 DOUTA 上;
2.4.2、Read First Mode
這種模式下,讀操作的優先級高於寫操作,它的時序如下所示:
有了 Write First Mode 的分析過程,分析這個也不算困難:
1、剛剛開始,ENA 信號一直爲 0,即,沒有使能;
2、第一個虛線,也就是 CLKA 的上升沿位置,採到 ENA 爲 1,同時 WEA 爲 0,則代表爲 READ 時序,同時,在這個上升沿,採集到 ADDRA 上爲 aa(ADDRA 爲並行地址總線),那麼就會在獲取到 aa 這個地址中的值後(經過了一點延時),將數據打到 DOUTA[15:0] 上,所以這裏可以看到 DOUTA 上是 MEM(aa),也就是 aa 這個 RAM 地址中存儲的數據;
3、第二個虛線,CLKA 上升沿的時候,同樣會檢測 ENA 和 WEA,此刻,它們都爲 1,則代表 WRITE 時序來了,此刻採集到寫入數據總線 DINA 上的數據爲 1111,地址總線上是 bb,由於是在 Read First Mode 的情況下,DOUTA 讀出的數據是 bb 地址的數據,讀操作完成後同時,MEM(bb) 的內容更新爲 1111,;
4、第三個虛線,CLKA 上升沿的時候,DOUTA 讀出的數據是 cc 地址的數據,讀操作完成後同時,MEM(cc) 的內容更新爲 2222;
5、第四個虛線,CLKA 上升沿的時候,WEA 信號被拉到 0,但是 ENA 信號還是 1,說明當前不存在 WRITE了,只有 READ 時序,那麼會將 ADDRA 上採集到的 dd 地址的數據讀出到 DOUTA 上;
2.4.3、No Change Mode
還有一個 No Change Mode,這個 No Change 指的是當在寫的時候, DOUTA 讀的數據總線數據保持不變,也就是 No Change;
可以看到,當在往 RAM 裏面寫的時候,DOUTA 讀出的數據保持了不變,即,一直爲 aa 的內容,直到 WEA 被拉低,重新進入 READ 模式;
綜上所述,這幾種模式,主要都是針對的是讀數據總線的行爲,是直接讀出 DINA 呢?還是讀出舊的內存地址的數據呢?還是在寫的時候被拉住;
2.5、Selectable Port Aspect Ratios
支持 Port A 和 Port B 配置不同的位寬,甚至同一個 Port 配置 Read 和 Write 的位寬不同;
2.6、Optional Byte-Write Enable
BMG 支持可選的一個叫做 Byte-Write 模式,這是一個針對 Write 的模式,在這個模式下,WEA 信號由之前的 1 bit 擴展爲了 N 個 bit,在這 N 個 bit 中,1 代表對應的 DINA 中對應 Bytes 會被更新到 ADDRA 對應的地址上去,如果 N bit 中,0 代表對應的 DINA 對應的 Byte 不會被更新到 ADDRA 對應的地址上去,有點拗口,下面是一個基於 Singal-port RAM,輸入數據總線 DINA 爲 24 bits 寬度,也就是 3 個 Bytes,WEA 爲 3 個 bit 寬度,直接看 Timing
DINA 的每個 Byte,對應到 WEA 的每一個 bit,可以看到:
1、第一個虛線 CLKA 上升沿,WEA[2:0] 是 3b'011,ADDRA 是 0x0000 地址,DINA[23:0] 是 FF EE DD,那麼他的行爲是,由於 WEA=011,代表控制器會去將 DINA 的 後面兩個 Bytes 更新到 RAM ADDRA 對應的地址上去,也就是 EE DD 被更新到 0000 的對應位置;
2、第二個虛線 CLKA 上升沿,WEA[2:0] 是 3b'010,ADDRA 還是 0x0000 地址,DINA[23:0] 是 CC BB AA,那麼它的含義是,將 BB 更新進去,也就是看到 RAM Contents 內容爲 00 BB DD
3、第三個虛線 CLKA 上升沿,WEA[2:0] 是 3b'101,ADDRA 還是 0x0000 地址,DINA[23:0] 是 99 88 77,那麼它的含義是,將 99 和 77 按照位置定義關係更新進去,也就是看到 RAM Contents 內容爲 99 BB 77
4、第四個虛線 CLKA 上升沿,WEA[2:0] 是 3b'000,所以即便是 DINA 有數據,那麼 RAM 內容也不會被更新進去;
5、第五個虛線 CLKA 上升沿,WEA[2:0] 是 3b'110,ADDRA 還是 0x0000 地址,DINA[23:0] 是 33 22 11,那麼它的含義是,將 33 和 22 按照位置定義關係更新進去,也就是看到 RAM Contents 內容爲 33 22 77
6、第六個虛線 CLKA 上升沿,WEA[2:0] 是 3b'010,ADDRA 還是 0x0000 地址,DINA[23:0] 是 00 FF 00,那麼它的含義是,將 FF 按照位置定義關係更新進去,也就是看到 RAM Contents 內容爲 33 FF 77
2.7、Collisions
既然是支持多 Port 同時寫入,那麼就會存在這個衝突的問題,在衝突發生的時候,存儲內容不可預知;
衝突主要出現在一下場景:
- 兩個 Port 的異步時鐘,一個 port 正在往一個地址寫數據,另一個 port 在指定時間內,必須不能夠去讀寫這個地方;
- 兩個 Port 同步時鐘的情況下,兩個 Port 同時企圖寫同一個 memory 的情況下;
- 使用 Byte-Writes 的時候,正好同時寫到了同一個地方的情況下;
2.7.1、Write-Write Collision
以 Byte-Writes 爲例,假設 Port A 和 Port B 的 ADDR 都是 0x0000;
如上圖所示:
1、第一個虛線時鐘上升沿,WEA 是 1100,WEB 是 0011,所以寫入的內容正好錯開,並不衝突
2、第二個虛線時鐘上升沿,WEA 是 0101,WEB 是 1010,所以寫入的內容正好錯開,也不衝突
2、第三個虛線時鐘上升沿,WEA 是 1110,WEB 是 0011,第三個 bit 衝突,往同一個地址寫內容,所以看到的是 7777 XX00,其中的 XX 是不可預知的內容;
後面的分析類似,不在贅述;
2.7、Optional Output Registers
BMG 允許可選的在輸出級增加一級寄存器,來改善輸出性能;
可以選擇在兩個輸出的地方增加寄存器:
1、在每個 Block RAM 輸出的地方增加寄存器;
2、在整個 BMG Core 輸出的地方增加寄存器;
這兩個配置都可以針對 Port A 和 Port B 進行單獨的配置;
Notes:增加一級輸出寄存器,會增加一個 Clock Cycle 的延時;
如果是使用每個 Block RAM 輸出端增加 Register,這個觸發器是屬於 BRAM 的內部資源,不會佔用其他的 FPGA 資源;如下圖所示:
Block RAM 中的那個寄存器就是指的第一種在輸出端增加寄存器;
Core Output Register 那個寄存器,就是第二種,在整個 BMG 輸出端增加 Register 的方式;