日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

SDRAM控制器操作时序

發(fā)布時(shí)間:2024/3/24 编程问答 35 豆豆
生活随笔 收集整理的這篇文章主要介紹了 SDRAM控制器操作时序 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

此為學(xué)習(xí)http://dengkanwen.com/137.html整理的筆記,侵刪!

SDRAM工作原理

內(nèi)部的狀態(tài)跳轉(zhuǎn)圖

我們所需關(guān)注的幾個(gè)地方:

1)粗黑線表示在該狀態(tài)下會(huì)自動(dòng)跳轉(zhuǎn)到另一個(gè)狀態(tài),細(xì)黑線表示需要給命令才會(huì)跳轉(zhuǎn)。

2)我們重點(diǎn)關(guān)注的幾個(gè)地方:

IDLE 狀態(tài)到WRITE 狀態(tài):
? 1) 在IDLE 狀態(tài)需要先給ACT 命令激活某一行,此時(shí)處于Row Active 狀態(tài);
? 2) 在Row Active 狀態(tài)之后,給Write 命令則會(huì)進(jìn)入WRITE 狀態(tài);
? 3) 在WRITE 狀態(tài)后,再給一次Write 命令,就可以繼續(xù)寫(xiě)入數(shù)據(jù)。
WRITE 狀態(tài)到IDLE 狀態(tài):
? 1) 在WRITE 狀態(tài)給PRE 命令,則SDRAM 將跳出WRITE 狀態(tài)進(jìn)入Precharge狀態(tài);
? 2) 在Precharge 狀態(tài)后,就會(huì)自動(dòng)進(jìn)入IDLE 狀態(tài)了。

? 要從WRITE 狀態(tài)跳到IDLE 狀態(tài)的一個(gè)原因是,我們需要進(jìn)行刷新操作,進(jìn)
入刷新操作,必須從IDLE 狀態(tài)進(jìn)入。
? 另外一點(diǎn),可能有些朋友看到了WRITE 狀態(tài)下邊還有一個(gè)WRITEA 狀態(tài),的
確,但是細(xì)心的你有沒(méi)有發(fā)現(xiàn)當(dāng)處于WRITEA 狀態(tài)時(shí),它會(huì)自動(dòng)的進(jìn)入Precharge 狀態(tài)。也就是說(shuō)WRITEA 比在WRITE 狀態(tài)的工作效率要低很多,所以在某些對(duì)數(shù)據(jù)交互速度較快的場(chǎng)景中,我們使用WRITE 狀態(tài)。在本套教程中,我們也只講WRITE 狀態(tài)。速度快的都能搞定,那速度慢的操作也是不在話下的。

SDRAM 初始化模塊

首先看一下官方數(shù)據(jù)手冊(cè)給出的初始化時(shí)序圖

初始化過(guò)程

1)首先需要有200us 的一個(gè)延時(shí)(對(duì)應(yīng)圖中左下方的T),

2)在延時(shí)滿足之后,給一次Precharge 命令,同時(shí)需要指定A10及Bank地址;(如果A10為高(All Banks),就意味著是給所有的Bank進(jìn)行預(yù)充電,此時(shí)不需要給Bank地址,如果A10為低(SINGLE BANK),就需要指定某一個(gè)bank的地址。一般為高)

3)然后再過(guò)“tRP”的時(shí)間,給“AutoRefresh”命令,然后再過(guò)“tRC”的時(shí)間,再給“Auto Refresh”命令,(不需要指定bank地址的(大家注意看右下角有說(shuō)明,灰色部分的數(shù)據(jù)我們是不需要關(guān)心的)。

4)然后再經(jīng)過(guò)“tRP”的時(shí)間進(jìn)行模式寄存器設(shè)置。進(jìn)行模式寄存器設(shè)置的時(shí)候,需要給的指令會(huì)稍微復(fù)雜一點(diǎn),手冊(cè)上顯示A0~A11及BA0,BA1都用到了,下面我們來(lái)看下模式寄存器應(yīng)該怎么進(jìn)行設(shè)置,如圖:

? 這里解釋一下突發(fā)讀寫(xiě):突發(fā)長(zhǎng)度(A2~A0)設(shè)置為4,在我們進(jìn)行寫(xiě)操作的時(shí)候,數(shù)據(jù)是每4個(gè)數(shù)據(jù)寫(xiě)一次的,就是說(shuō)我們給一次寫(xiě)指令,就會(huì)向SDRAM寫(xiě)進(jìn)去4個(gè)數(shù)據(jù),而且四個(gè)地址是連續(xù)的(如果突發(fā)類型設(shè)置的是非連續(xù),則地址不會(huì)連續(xù),需要我們寫(xiě)一個(gè)數(shù)據(jù)給一次地址,比較耗內(nèi)存)

初始化時(shí)序圖中的幾個(gè)問(wèn)題

1)tRC、tRP、tMRD的時(shí)間是多少,幾個(gè)時(shí)鐘周期?

參照官方數(shù)據(jù)手冊(cè)ML0006 0012-2中的AC ELECTRICAL CHARACTERISTICS部分給出

tRC:63ns

tRP:20ns

tMRD:2cycle

若fpga內(nèi)部頻率為50MHZ,正好是20ns。(4clk、1clk)

2)時(shí)序圖中幾個(gè)command命令的參數(shù)怎樣設(shè)置

上述就是整個(gè)初始化過(guò)程,我們最后以kevin畫(huà)的時(shí)序圖作為一個(gè)總結(jié)

具體代碼為sdram_init;

SDRAM 刷新模塊

我們還是先看一下官方數(shù)據(jù)手冊(cè)給出的刷新時(shí)序圖

刷新操作的時(shí)序圖分析與前面類似。

刷新時(shí)序圖中的幾個(gè)問(wèn)題

1)兩次刷新時(shí)間間隔有多久呢?

? SDRAM內(nèi)部電容保存數(shù)據(jù)的最長(zhǎng)時(shí)間是64ms,而我們一個(gè)BANK有4096行,64ms/4096~=15us,也就是說(shuō)為了保證SDRAM內(nèi)部的數(shù)據(jù)不被丟失,兩次刷新之間的最大時(shí)間間隔為15us,所以為了能讓SDRAM有更多的時(shí)間進(jìn)行讀或者寫(xiě),我們就設(shè)定SDRAM刷新的周期為15us.(若按系統(tǒng)時(shí)鐘50MHZ,就是計(jì)750個(gè)數(shù))

? SDRAM每進(jìn)行一次刷新,是對(duì)每一行進(jìn)行操作的,并不是單獨(dú)針對(duì)每一個(gè)電容進(jìn)行充電,所以每進(jìn)行一次刷新,該行中的電容進(jìn)行充電我們可以理解為是同步發(fā)生的

2)在每次自動(dòng)刷新時(shí),我們需要給一個(gè)“Precharge”命令,這個(gè)命令有什么作用呢?

大家可以看下開(kāi)頭的那張狀態(tài)圖,如果此時(shí)SDRAM正處于“WRITE”或“READ”狀態(tài)時(shí),這個(gè)“Precharge”命令可以使SDRAM跳出“WRITE”或“READ”狀態(tài)從而入“IDLE”狀態(tài)。接下來(lái),過(guò)“tRP”的時(shí)間,給一個(gè)“Auto-Refresh”命令可以進(jìn)入刷新?tīng)顟B(tài)。

但此時(shí)的Precharge命令我們?cè)趯?xiě)狀態(tài)模塊中給出。在刷新模塊中不需要Precharge命令。

SDRAM仲裁模塊

在介紹仲裁模塊前我們先考慮一個(gè)問(wèn)題:

? 如果我正在讓SDRAM寫(xiě)數(shù)據(jù),是不是SDRAM刷新的時(shí)間到了,我就必須是讓SDRAM馬上執(zhí)行刷新操作嗎?這樣的話肯定不是現(xiàn)實(shí)的,那必然會(huì)把還沒(méi)寫(xiě)的剩下的數(shù)據(jù)丟失。不能讓我們的數(shù)據(jù)丟失,又要保證SDRAM進(jìn)行刷新來(lái)保證我們整個(gè)SDRAM相應(yīng)BANK中的數(shù)據(jù)不被丟失,我們應(yīng)該怎么來(lái)寫(xiě)代碼呢?

我們可以考慮這樣來(lái)做:如果刷新的時(shí)間到了,先讓寫(xiě)操作把正在寫(xiě)的4個(gè)數(shù)據(jù)(突發(fā)長(zhǎng)度為4)寫(xiě)完,然后再去進(jìn)行刷新操作。而如果在執(zhí)行讀操作也遇到需要刷新的情況,我們也可以這樣來(lái)做,先讓數(shù)據(jù)讀完,再去執(zhí)行刷新操作。

為了解決各個(gè)模塊之間不方便控制的情況,我們引入一個(gè)新的機(jī)制 ——“仲裁”機(jī)制。“仲裁”用來(lái)干什么呢?在這里邊,“仲裁”相當(dāng)于我們這個(gè)SDRAM控制器的老大,對(duì)SDRAM的各個(gè)操作統(tǒng)一協(xié)調(diào):讀、寫(xiě)及自動(dòng)刷新都由“仲裁”來(lái)控制。

仲裁模塊狀態(tài)機(jī)示意圖:

仲裁模塊和其他各模塊之間的連線:

注:一定要搞清楚說(shuō)的是模塊之間連線的關(guān)系還是狀態(tài)機(jī)之間跳轉(zhuǎn)的關(guān)系哦。

仲裁模塊分析

1)初始化操作完成之后便進(jìn)入到了“ARBIT”仲裁狀態(tài),只有處于仲裁狀態(tài)的時(shí)候,“仲裁老大”才能進(jìn)行下命令。

2)當(dāng)狀態(tài)機(jī)處于“WRITE”寫(xiě)狀態(tài)時(shí),如果SDRAM刷新的時(shí)間到了,刷新模塊同時(shí)向?qū)懩K和仲裁模塊發(fā)送刷新請(qǐng)求ref_req信號(hào)。

3)當(dāng)寫(xiě)模塊接受到ref_req之后,寫(xiě)模塊在寫(xiě)完當(dāng)前4個(gè)數(shù)據(jù)(突發(fā)長(zhǎng)度為4)之后,寫(xiě)模塊的寫(xiě)結(jié)束標(biāo)志flag_wr_end拉高,然后狀態(tài)機(jī)進(jìn)入“ARBIT”仲裁狀態(tài)。

4)處于仲裁狀態(tài)之后,此時(shí)有刷新請(qǐng)求ref_req,然后狀態(tài)機(jī)跳轉(zhuǎn)到“AREF”狀態(tài)并且仲裁模塊發(fā)送ref_en刷新使能,刷新模塊將刷新請(qǐng)求信號(hào)ref_req拉低并給sdram發(fā)送刷新的命令。

5)等刷新完畢之后,刷新模塊給仲裁模塊發(fā)送flag_ref_end刷新結(jié)束標(biāo)志,狀態(tài)機(jī)跳轉(zhuǎn)到“ARBIT”仲裁狀態(tài)。

注意了,當(dāng)刷新完跳轉(zhuǎn)到“ARBIT”仲裁狀態(tài)之后,如果之前我們的全部數(shù)據(jù)仍然沒(méi)有寫(xiě)完(Kevin指的是全部數(shù)據(jù),并不是一個(gè)突發(fā)長(zhǎng)度的4個(gè)數(shù)據(jù)哦),那么此時(shí)我們?nèi)匀灰o仲裁模塊寫(xiě)請(qǐng)求“wr_req”,然后仲裁模塊經(jīng)過(guò)一系列判斷之后,如果符合寫(xiě)操作的時(shí)機(jī),那就給寫(xiě)模塊一個(gè)寫(xiě)使能信號(hào)“wr_en”,然后跳轉(zhuǎn)到“WRITE”寫(xiě)狀態(tài)并且寫(xiě)模塊開(kāi)始工作。

SDRAM寫(xiě)模塊

官方數(shù)據(jù)手冊(cè)給出的寫(xiě)操作時(shí)序圖

該時(shí)序圖的分析可以參照前面初始化過(guò)程的分析。

現(xiàn)在我們考慮另一個(gè)問(wèn)題:假設(shè)我們現(xiàn)在需要往SDRAM 中寫(xiě)入兩行數(shù)據(jù),那什么時(shí)候可以退出仲裁狀態(tài)機(jī)的寫(xiě)狀態(tài):
1) 數(shù)據(jù)已經(jīng)寫(xiě)完;若我們還想要再寫(xiě),就需要外部的Wr_trig觸發(fā)
2) SDRAM 需要進(jìn)行刷新操作;外部有一個(gè)刷新請(qǐng)求信號(hào),并且本次數(shù)據(jù)已經(jīng)寫(xiě)完;轉(zhuǎn)到外部仲裁模塊去執(zhí)行刷新操作,如果刷新完畢需要繼續(xù)寫(xiě),寫(xiě)模塊請(qǐng)求,仲裁模塊使能。
3) 數(shù)據(jù)未寫(xiě)完,需要激活下一行繼續(xù)寫(xiě)。本行寫(xiě)完標(biāo)志,重新輸入act命令去寫(xiě)下一行

我們將這三個(gè)狀態(tài)化成一個(gè)狀態(tài)機(jī)。如圖所示:

注意上圖中的IDLE狀態(tài)和前面的初始化中的IDLE狀態(tài)不要搞混。這個(gè)IDLE就是寫(xiě)模塊中狀態(tài)機(jī)的初始化部分。

S_WR:if(wr_data_end == 1'b1) state <= S_PRE; else if(ref_req == 1'b1 && burst_cnt_t == 'd2 && flag_wr == 1'b1) state <= S_PRE; else if(sd_row_end == 1'b1 && flag_wr == 1'b1)state <= S_PRE; S_PRE:if(ref_req == 1'b1 && flag_wr == 1'b1) state <= S_REQ;else if(flag_pre_end == 1'b1 && flag_wr == 1'b1) state <= S_ACT;else if(flag_wr == 1'b0) state <= S_IDLE;

我們由以上所述畫(huà)出寫(xiě)模塊時(shí)序圖:

分析寫(xiě)模塊中五個(gè)狀態(tài)機(jī):

1)IDLE:外部Wr_trig觸發(fā)寫(xiě)信號(hào),進(jìn)入S_REQ狀態(tài)。寫(xiě)模塊將Flag_wr拉高直到數(shù)據(jù)完全寫(xiě)完結(jié)束。

2)S_REQ:Flag_wr信號(hào)拉高,S_REQ狀態(tài)向外部仲裁發(fā)出請(qǐng)求寫(xiě)信號(hào)wr_req,外部仲裁模塊判斷可以進(jìn)行寫(xiě)操作了并向?qū)懩K發(fā)出wr_en 使能信號(hào),告訴寫(xiě)模塊可以開(kāi)始寫(xiě)了。進(jìn)入S_ACT狀態(tài)。

3)S_ACT:寫(xiě)模塊在S_ACT狀態(tài),發(fā)出ACT命令(command),并且指定bank的行地址。ACT命令結(jié)束發(fā)出Flag_act_end結(jié)束標(biāo)志。進(jìn)入S_WR狀態(tài)。

4)S_WR:發(fā)出寫(xiě)命令開(kāi)始寫(xiě)數(shù)據(jù),此時(shí)需要指定列地址

一行數(shù)據(jù)寫(xiě)完發(fā)出Sd_row_end標(biāo)志信號(hào)。刷新請(qǐng)求出現(xiàn)時(shí),該組數(shù)據(jù)寫(xiě)完發(fā)出Flag_wr_end標(biāo)志信號(hào)。所有數(shù)據(jù)寫(xiě)完返回Wr_data_end信號(hào)標(biāo)志。

5)S_PRE:預(yù)充電命令 ,進(jìn)入預(yù)充電狀態(tài),充電完畢返回Flag_pre_end標(biāo)志信號(hào)。

SDRAM讀模塊

SDRAM讀模塊與寫(xiě)模塊一樣在此不再詳述。

讀模塊時(shí)序圖:

有一個(gè)問(wèn)題需要注意:

我們?cè)俳o出讀命令后,數(shù)據(jù)延時(shí)了兩個(gè)周期給出,這個(gè)時(shí)間段叫潛伏期CAS。

寫(xiě)代碼技巧:

1)先寫(xiě)主狀態(tài)機(jī)

2)把時(shí)序圖中用到的時(shí)序信號(hào)標(biāo)志定義出來(lái);

reg flag_wr ; reg [ 4:0] state ; //----------------------------------------------- reg flag_act_end ; reg flag_pre_end ; reg sd_row_end ; reg [ 1:0] burst_cnt ; reg [ 1:0] burst_cnt_t ; reg wr_data_end ; //----------------------------------------------- reg [ 3:0] act_cnt ; reg [ 3:0] break_cnt ; reg [ 6:0] col_cnt ; //----------------------------------------------- reg [11:0] row_addr ; wire [ 8:0] col_addr ;

3)然后按照這個(gè)表寫(xiě)出每個(gè)標(biāo)志信號(hào)產(chǎn)生的代碼

總結(jié)

以上是生活随笔為你收集整理的SDRAM控制器操作时序的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。