此为学习http://dengkanwen.com/137.html整理的笔记,侵删!

SDRAM工作原理

内部的状态跳转图

我们所需关注的几个地方:

1)粗黑线表示在该状态下会自动跳转到另一个状态,细黑线表示需要给命令才会跳转。

2)我们重点关注的几个地方:

IDLE 状态到WRITE 状态:
​ 1) 在IDLE 状态需要先给ACT 命令激活某一行,此时处于Row Active 状态;
​ 2) 在Row Active 状态之后,给Write 命令则会进入WRITE 状态;
​ 3) 在WRITE 状态后,再给一次Write 命令,就可以继续写入数据。
WRITE 状态到IDLE 状态:
​ 1) 在WRITE 状态给PRE 命令,则SDRAM 将跳出WRITE 状态进入Precharge状态;
​ 2) 在Precharge 状态后,就会自动进入IDLE 状态了。

​ 要从WRITE 状态跳到IDLE 状态的一个原因是,我们需要进行刷新操作,进
入刷新操作,必须从IDLE 状态进入。
​ 另外一点,可能有些朋友看到了WRITE 状态下边还有一个WRITEA 状态,的
确,但是细心的你有没有发现当处于WRITEA 状态时,它会自动的进入Precharge 状态。也就是说WRITEA 比在WRITE 状态的工作效率要低很多,所以在某些对数据交互速度较快的场景中,我们使用WRITE 状态。在本套教程中,我们也只讲WRITE 状态。速度快的都能搞定,那速度慢的操作也是不在话下的。

SDRAM 初始化模块

首先看一下官方数据手册给出的初始化时序图

初始化过程

1)首先需要有200us 的一个延时(对应图中左下方的T),

2)在延时满足之后,给一次Precharge 命令,同时需要指定A10及Bank地址;(如果A10为高(All Banks),就意味着是给所有的Bank进行预充电,此时不需要给Bank地址,如果A10为低(SINGLE BANK),就需要指定某一个bank的地址。一般为高)

3)然后再过“tRP”的时间,给“AutoRefresh”命令,然后再过“tRC”的时间,再给“Auto Refresh”命令,(不需要指定bank地址的(大家注意看右下角有说明,灰色部分的数据我们是不需要关心的)。

4)然后再经过“tRP”的时间进行模式寄存器设置。进行模式寄存器设置的时候,需要给的指令会稍微复杂一点,手册上显示A0~A11及BA0,BA1都用到了,下面我们来看下模式寄存器应该怎么进行设置,如图:

​ 这里解释一下突发读写:突发长度(A2~A0)设置为4,在我们进行写操作的时候,数据是每4个数据写一次的,就是说我们给一次写指令,就会向SDRAM写进去4个数据,而且四个地址是连续的(如果突发类型设置的是非连续,则地址不会连续,需要我们写一个数据给一次地址,比较耗内存)

初始化时序图中的几个问题

1)tRC、tRP、tMRD的时间是多少,几个时钟周期?

参照官方数据手册ML0006 0012-2中的AC ELECTRICAL CHARACTERISTICS部分给出

tRC:63ns

tRP:20ns

tMRD:2cycle

若fpga内部频率为50MHZ,正好是20ns。(4clk、1clk)

2)时序图中几个command命令的参数怎样设置

上述就是整个初始化过程,我们最后以kevin画的时序图作为一个总结

具体代码为sdram_init;

SDRAM 刷新模块

我们还是先看一下官方数据手册给出的刷新时序图

刷新操作的时序图分析与前面类似。

刷新时序图中的几个问题

1)两次刷新时间间隔有多久呢?

​ SDRAM内部电容保存数据的最长时间是64ms,而我们一个BANK有4096行,64ms/4096~=15us,也就是说为了保证SDRAM内部的数据不被丢失,两次刷新之间的最大时间间隔为15us,所以为了能让SDRAM有更多的时间进行读或者写,我们就设定SDRAM刷新的周期为15us.(若按系统时钟50MHZ,就是计750个数)

​ SDRAM每进行一次刷新,是对每一行进行操作的,并不是单独针对每一个电容进行充电,所以每进行一次刷新,该行中的电容进行充电我们可以理解为是同步发生的

2)在每次自动刷新时,我们需要给一个“Precharge”命令,这个命令有什么作用呢?

大家可以看下开头的那张状态图,如果此时SDRAM正处于“WRITE”或“READ”状态时,这个“Precharge”命令可以使SDRAM跳出“WRITE”或“READ”状态从而入“IDLE”状态。接下来,过“tRP”的时间,给一个“Auto-Refresh”命令可以进入刷新状态。

但此时的Precharge命令我们在写状态模块中给出。在刷新模块中不需要Precharge命令。

SDRAM仲裁模块

在介绍仲裁模块前我们先考虑一个问题:

​ 如果我正在让SDRAM写数据,是不是SDRAM刷新的时间到了,我就必须是让SDRAM马上执行刷新操作吗?这样的话肯定不是现实的,那必然会把还没写的剩下的数据丢失。不能让我们的数据丢失,又要保证SDRAM进行刷新来保证我们整个SDRAM相应BANK中的数据不被丢失,我们应该怎么来写代码呢?

我们可以考虑这样来做:如果刷新的时间到了,先让写操作把正在写的4个数据(突发长度为4)写完,然后再去进行刷新操作。而如果在执行读操作也遇到需要刷新的情况,我们也可以这样来做,先让数据读完,再去执行刷新操作。

为了解决各个模块之间不方便控制的情况,我们引入一个新的机制 ——“仲裁”机制。“仲裁”用来干什么呢?在这里边,“仲裁”相当于我们这个SDRAM控制器的老大,对SDRAM的各个操作统一协调:读、写及自动刷新都由“仲裁”来控制。

仲裁模块状态机示意图:

仲裁模块和其他各模块之间的连线:

注:一定要搞清楚说的是模块之间连线的关系还是状态机之间跳转的关系哦。

仲裁模块分析

1)初始化操作完成之后便进入到了“ARBIT”仲裁状态,只有处于仲裁状态的时候,“仲裁老大”才能进行下命令。

2)当状态机处于“WRITE”写状态时,如果SDRAM刷新的时间到了,刷新模块同时向写模块和仲裁模块发送刷新请求ref_req信号。

3)当写模块接受到ref_req之后,写模块在写完当前4个数据(突发长度为4)之后,写模块的写结束标志flag_wr_end拉高,然后状态机进入“ARBIT”仲裁状态。

4)处于仲裁状态之后,此时有刷新请求ref_req,然后状态机跳转到“AREF”状态并且仲裁模块发送ref_en刷新使能,刷新模块将刷新请求信号ref_req拉低并给sdram发送刷新的命令。

5)等刷新完毕之后,刷新模块给仲裁模块发送flag_ref_end刷新结束标志,状态机跳转到“ARBIT”仲裁状态。

注意了,当刷新完跳转到“ARBIT”仲裁状态之后,如果之前我们的全部数据仍然没有写完(Kevin指的是全部数据,并不是一个突发长度的4个数据哦),那么此时我们仍然要给仲裁模块写请求“wr_req”,然后仲裁模块经过一系列判断之后,如果符合写操作的时机,那就给写模块一个写使能信号“wr_en”,然后跳转到“WRITE”写状态并且写模块开始工作。

SDRAM写模块

官方数据手册给出的写操作时序图

该时序图的分析可以参照前面初始化过程的分析。

现在我们考虑另一个问题:假设我们现在需要往SDRAM 中写入两行数据,那什么时候可以退出仲裁状态机的写状态:
1) 数据已经写完;若我们还想要再写,就需要外部的Wr_trig触发
2) SDRAM 需要进行刷新操作;外部有一个刷新请求信号,并且本次数据已经写完;转到外部仲裁模块去执行刷新操作,如果刷新完毕需要继续写,写模块请求,仲裁模块使能。
3) 数据未写完,需要激活下一行继续写。本行写完标志,重新输入act命令去写下一行

我们将这三个状态化成一个状态机。如图所示:

注意上图中的IDLE状态和前面的初始化中的IDLE状态不要搞混。这个IDLE就是写模块中状态机的初始化部分。

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;  

我们由以上所述画出写模块时序图:

分析写模块中五个状态机:

1)IDLE:外部Wr_trig触发写信号,进入S_REQ状态。写模块将Flag_wr拉高直到数据完全写完结束。

2)S_REQ:Flag_wr信号拉高,S_REQ状态向外部仲裁发出请求写信号wr_req,外部仲裁模块判断可以进行写操作了并向写模块发出wr_en 使能信号,告诉写模块可以开始写了。进入S_ACT状态。

3)S_ACT:写模块在S_ACT状态,发出ACT命令(command),并且指定bank的行地址。ACT命令结束发出Flag_act_end结束标志。进入S_WR状态。

4)S_WR:发出写命令开始写数据,此时需要指定列地址

一行数据写完发出Sd_row_end标志信号。刷新请求出现时,该组数据写完发出Flag_wr_end标志信号。所有数据写完返回Wr_data_end信号标志。

5)S_PRE:预充电命令 ,进入预充电状态,充电完毕返回Flag_pre_end标志信号。

SDRAM读模块

SDRAM读模块与写模块一样在此不再详述。

读模块时序图:

有一个问题需要注意:

我们再给出读命令后,数据延时了两个周期给出,这个时间段叫潜伏期CAS。

写代码技巧:

1)先写主状态机

2)把时序图中用到的时序信号标志定义出来;

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)然后按照这个表写出每个标志信号产生的代码

SDRAM控制器操作时序相关推荐

  1. SDRAM控制器设计

    SDRAM控制器设计 SDRAM 器件引脚示意图和功能框图如下: SDRAM 器件有如下的特性 通常情况下, SDRAM 存储器工作在 3.3V 的电压下(需要注意的是 DDR DRAM工作电压是 2 ...

  2. 学习FPGA有必要写SDRAM控制器吗?

    在学习FPGA的过程中,注意是在学习过程中,联系FPGA的使用技巧,强烈建议尝试设计一个SDRAM控制器,不要使用IP核. 学习SDRAM控制器设计,能让你掌握很多知识. 更好的使用状态机去精准控制时 ...

  3. 手把手带你实现SDRAM控制器(带Verilog代码)

    上篇博客,我们了解了SDRAM的控制命令以及寻址方式,SDRAM芯片需要配合专门的控制电路使用才能发挥功能,这一节我们将一步步分析,使用Verilog搭建一个SDRAM驱动控制器. 目录 学习目标 问 ...

  4. FPGA之SDRAM控制器设计(三)

    FPGA之SDRAM控制器设计(三):写 由于已经涉及了上电刷新,写三个大的状态转移,先把状态转移图给出.主控状态转移图是基于手册上描述来的.在代码注释中会给出每个状态的意义解释. 写时序图 写状态转 ...

  5. 基于FPGA的SDRAM控制器设计(二)

    基于FPGA的SDRAM控制器设计(二) 1. SDRAM理论基础 2. SDRAM初始化模块以及仿真 3.TOP模块的仲裁机制 4. SDRAM刷新模块代码以及仿真 5.代码 6.参考资料 1. S ...

  6. 基于Qsys的SDRAM控制器

    1.Intel FPGA中SDRAM控制器IP示意图 相比LED/数码管等简单外设,SDRAM芯片配置显得复杂许多,当然可以自行编写状态机实现初始化和读写控制,但是为了加快开发速度,可以借助Intel ...

  7. 基于FPGA的SDRAM控制器设计(1)

    基于FPGA的SDRAM初始化配置 SDRAM简述 SDRAM的引脚及作用 SDRAM初始化时序控制 SDRAM上电时序代码 SDRAM测试模块的代码 仿真测试结果 参考文献 总结 SDRAM简述 S ...

  8. 内存信号测试软件,基于AVIA9700的SDRAM控制器实现内存时序测试软件工具的设计...

    图2 AVIA9700访问SDRAM时序示意图 要正确访问SDRAM,建立时间和保持时间很关键.建立时间在触发器采样之前,在这段时间,数据必须保持有效的时间,否则会产生setup violation; ...

  9. SDRAM控制器说明/altera/northwest logic

    经验参考:CSDN-基于Northwest Logic控制器的SDR SDRAM读写实验 原文档下载/write paper altera家 用到的sdram Northwest Logic 学习注解 ...

最新文章

  1. 科幻电影里的超能力?那不就是并发嘛!
  2. python官网下载步骤linux-linux如何安装python
  3. cdoj841-休生伤杜景死惊开 (逆序数变形)【线段树 树状数组】
  4. 【华为云技术分享】STM32L476移植华为LiteOS系列教程---开发前的准备 2
  5. git pull git add git commit git branch git更新代码git提交git分支管理
  6. 启动go服务_go微服务框架go-micro深度学习 rpc方法调用过程详解
  7. 【Nodejs开发】第2章 网站首页的布局
  8. cvSaveImage用法
  9. 复选框式查询 例题租房子
  10. 基于python的电商评论分析_Python实现爬取并分析电商评论
  11. Joint Discriminative and Generative Learning for Person Re-identification论文翻译
  12. Day5-ESP8266模块——百问网7天物联网智能家居
  13. SQL高级——PLSQL数据库编程
  14. Gamma、Linear、sRGB 和Unity Color Space,你真懂了吗?
  15. SD-Host SD_CLK模块
  16. EEG脑电公开数据库大盘点
  17. PWM脉宽调制信号转直流电压电流模拟信号输出隔离变送器5v10v4-20ma
  18. 嵌入式算法7---CRC校验算法模板
  19. WinForm DataGridView实时更新表格数据
  20. Linux常用命令全集

热门文章

  1. python列表的嵌套_Python-嵌套列表list的全面解析
  2. 微型计算机能不能玩lol,微机课才能玩的3款“单机游戏”,CS上榜,没玩过的别说有童年...
  3. 使用函数求Fibonacci数 C语言PTA
  4. Navicat Premium 15 无法导出excel格式的文件
  5. 干货!智能制造数字工厂的规划设计
  6. 奶爸日记25 - 笛子
  7. RHCS + GNBD实现基于multipath上的GFS文件系统
  8. (sklearn)lasso回归linear_model.Lasso()方法
  9. TiDB 源码阅读系列文章(六)Select 语句概览 1
  10. 邓应海:4.2本周黄金提前休市,下周开盘需警惕