查看MAX II器件的Chip Planner:
其左下角這塊黑色區域是用戶不可用資源區,而在這片不可用區域里有一塊綠色的方塊是可用的。這塊不可用的黑色區域叫做CFM block(配置Flash存儲區),而那個綠色方塊叫做UFM(用戶可用的Flash存儲區)。對于后者是我們今天討論的重點,先看以下官方對此存儲區作用的描述:
MAX II devices feature a single UFM block, which can be used like a serial EEPROM for storing non-volatile information up to 8,192 bits. The UFM block connects to the logic array through the MultiTrack interconnect,allowing any LE to interface to the UFM block. Figure 2–15 shows the UFM block and interface signals. The logic array is used to create customer interface or protocol logic to interface the UFM block data outside of the device. The UFM block offers the following features:
■ Non-volatile storage up to 16-bit wide and 8,192 total bits
■ Two sectors for partitioned sector erase
■ Built-in internal oscillator that optionally drives logic array
■ Program, erase, and busy signals
■ Auto-increment addressing
■ Serial interface to logic array with programmable interface
也就是說,MAX II其實是內嵌了一塊8Kbit的Flash。這個Flash原則上是不占用MAX II的其它可用邏輯資源的,不過這有個大前提:用戶讀寫這塊存儲區使用altera本身的串行接口(遵循特定的通信協議)。但是這個協議也太繁瑣了(個人感覺),因此,對于這塊存儲區讀寫接口altera提供了三種通用的接口供用戶選擇。
■ I2C
■ SPI
■ Parallel
■ None (Altera Serial Interface)
最后一種就是不需要占用器件額外邏輯資源的接口,上面三種是需要消耗器件邏輯資源的接口。筆者添加了一個并行接口做測試,占用了EMP240內部86個LEs,對于資源比較緊張的應用還是很劃不來的。
更多詳細的關于UFM的信息請大家參考altera提供的MAX II datasheet。下面介紹一個使用并行接口讀寫UFM的實例,以及功能仿真。
新建一個工程,名為ufmtest,頂層模塊ufmtest.v,代碼如下:
module ufmtest(
databus,addr,
nerase,nread,nwrite,
data_valid,nbusy
);
inout[15:0] databus; //Flash數據總線
input[8:0] addr; //Flash地址總線
input nerase; //擦除Flash某一扇區信號
input nread; //讀Flash信號
input nwrite; //寫Flash信號
output data_valid; //Flash數據輸出有效信號
output nbusy; //Flash忙信號
assign databus = nwrite ? dataout:16‘hzzzz; //寫信號有效時,Flash數據總線作為輸入
assign datain = databus; //寫入Flash數據總線連接
wire[15:0] datain; //Flash寫入數據
wire[15:0] dataout; //Flash讀出數據
//例化UFM(Flash)模塊
para_ufm para_ufm_inst (
.addr ( addr ),
.datain ( datain ),
.nerase ( nerase),
.nread ( nread ),
.nwrite ( nwrite),
.data_valid ( data_valid ),
.dataout ( dataout ),
.nbusy ( nbusy )
);
endmodule
但是在例化UFM模塊之前,大家需要先在MegaWizard Plug-In Manager里添加一個Flash模塊。步驟如下:
1,點擊菜單欄里的ToolsàMegaWizard Plug-In Manager。彈出如下,點擊next。
2,接著選擇Memory Compiler下的Flash Memory,然后在What name do you want for the output file?下路徑的最后添加輸出文件名為para_ufm,點擊next.
3,接下來一路Next,需要更改設置的地方如下(我也不多廢話,大家一看都明白):
完成上面步驟以后編譯工程,編寫testbench如下:
`timescale 1ns/1ns
module tb_ufmtest();
//inout
wire[15:0] databus; //Flash數據總線
//input
wire data_valid; //Flash數據輸出有效信號
wire nbusy; //Flash忙信號
//output
reg[8:0] addr; //Flash地址總線
reg nerase; //擦除Flash某一扇區信號
reg nread; //讀Flash信號
reg nwrite; //寫Flash信號
reg[15:0] databus_r; //測試模塊數據總線寄存器
reg[15:0] rdback_data; //測試模塊數據總線數據回讀寄存器
assign databus = nwrite ? 16’hzzzz:databus_r;
ufmtest ufmtest(
.databus(databus),
.addr(addr),
.nerase(nerase),
.nread(nread),
.nwrite(nwrite),
.data_valid(data_valid),
.nbusy(nbusy)
);
parameter DELAY_600US = 600_000, //600us延時
DELAY_2US = 2_000, //2us延時
DELAY_5US = 5_000; //5us延時
initial begin
nerase = 1;
nread = 1;
nwrite = 1;
addr = 0;
databus_r = 0;
#DELAY_600US; //0地址寫入數據99
databus_r = 99;
addr = 9‘d0;
nwrite = 0;
#DELAY_5US;
nwrite = 1;
@ (posedge nbusy);
#DELAY_5US; //0地址讀出數據,保存到寄存器rdback_data中
databus_r = 16’hff;
addr = 9‘d0;
nread = 0;
#DELAY_5US;
nread = 1;
@ (posedge data_valid);
rdback_data = databus;
#DELAY_600US;
$stop;
end
endmodule
仿真波形如下:
-
模塊
+關注
關注
7文章
2725瀏覽量
47610
發布評論請先 登錄
相關推薦
評論