今天主要学习Sdram控制器框架设计
首先来看下整个控制器设计框图
如图1所示
(图1 FPGA内部程序框图)
接下来,分模块来看一下
1.11 实现方式
时钟的输入来源于外部晶振,时钟频率为25MHz,通过PLL产生数据源的时钟62.5MHz和sdram的工作时钟166MHz。另外还需要产生一个相移为180°的166MHz提供给下游芯片sdram,保证时钟在数据中间采样。
1.12 参数设计
参数设计如图2所示
(图2 PLL参数设计)
1.13 接口设计
1.14 重点问题
Locked信号需要等锁相环锁定时钟后,输出的时钟才能有效,此PLL设计使用的是高有效的复位。
1.21 实现方式
数据源产生模块使用PLL倍频出来的62.5MHz时钟,产生数据格式如下:
Addr[8:0] |
0 |
1 |
2 |
… |
253 |
254 |
255 |
Data[31:0] |
0 |
1 |
2 |
… |
253 |
254 |
sum |
1.22 顶层设计
En表示什么时候产生数据,顶层结构如图3所示。
(图3 数据源产生模块顶层设计)
1.23 接口设计
1.24 重点问题
产生的数据是以256为一块,最后一个数是前面所有数据的累加和。
将从sdram读出的数据进行校验,判断是否正确。
1.4.1 实现方式
每次读取256个数据(sdram的一行),将前255个数据的累加和与第256个数据比较,如果相等,则表示无误码,led灯不点亮;否则,led保持亮1s。顶层框图如图5所示,valid表示输入的有效数据,led为1-bit输出点亮灯板。
1.4.2 顶层设计
(图5 数据校验顶层设计)
1.4.3 接口设计
module ResultCheck
#(
parameter ADDRWIDTH = 9 ,
parameter DATAWIDTH = 32 ,
parameter DATALENGTH= 256
)
(
input Clk166M,
input valid,
input [`DQ_BITS-1 :0] data,
output led
);
1.4.4 重点问题
Valid和数据是同时有效进入,然后进行逻辑操作。输出led如果有错,需要延迟1s。
1.5.1 初始化时序
初始化的时序如图6所示:
(图6 sdram初始化时序)
1.5.2 实现方式
初始化流程如下:
Ø 上电后要延时200us
Ø Precharge(预充电)所有bank
Ø 等待Trp时间进行 AUTO REFRESH(自动刷新)命令
Ø 等待Trfc时间再次进行AUTO REFRESH命令
Ø 等待Trfc时间进行load mode register命令
Ø 等待Tmrd时间进行ACTIVE命令
1.5.3 顶层设计
初始化顶层框图设计如图6所示。
(图6 初始化模块顶层设计)
1.5.4 接口设计
module SdramInit
#(
parameter BURST_LENGTH = 3'b000,
parameter BT = 1'b0, //sequential
parameter CAS_LATENCY = 3'b011, //3(166MHz need 3 clocks)
parameter OP_MODE = 2'b00, //standard operation
parameter WRITE_BURST_MODE = 1'b0 //Programmed Burst Length
)
(
input Clk166M ,
output reg [3 :0 ] InitCmd ,
output reg [`ADDR_BITS-1:0 ] InitAddr ,
output reg [`BA_BITS-1 :0 ] InitBa ,
output reg InitDone
);
1.5.5 重点问题
l 按照时序进行初始化设计
l 模式寄存器配置
l 各种命令组合
1.6.1 刷新时序
刷新时序如图7所示:
(图7 刷新时序)
1.6.2 实现方式
查手册可知,每两次刷新的最长时间间隔为15.625us,由此设置刷新计数器如下:
//------------------------------------------------------------------------------
// a row Refresh need 15625ns(max)
// refcnt = 15625ns / 6ns = 2604
// there I select refcnt = 2600
// 10'd2604 = 16'ha28
//------------------------------------------------------------------------------
刷新操作流程如下:
Ø Precharge active bank后
Ø 等待Trp时间进行 AUTO REFRESH(自动刷新)命令
Ø 等待Trfc时间再次进行AUTO REFRESH命令
1.6.3 顶层设计
顶层设计如图8所示,途中RefStart信号连接的是初始化完成信号,当初始化完成刷新计数器开始计数,隔一段进行刷新请求,等待仲裁模块响应。
(图8 刷新模块顶层设计)
1.6.4 接口设计
module SdramRefresh(
input Clk166M ,
output RefReq ,
input RefEn ,
input RefStart ,
output reg [3 : 0] RefCmd ,
output reg [`ADDR_BITS-1: 0] RefAddr ,
output reg [`BA_BITS-1 : 0] RefBa ,
output reg RefDone
);
1.6.5 重点问题
按照刷新的时序进行设计,而且必须保证在15.625us内进行刷新,否则电容掉电就会丢失数据。
1.7.1 写操作时序
Sdram写操作时序如图9所示。
(图9 写操作时序)
1.7.2 实现方式
本模块的功能主要为实现在SDRAM中写入数据, 对于不同的写模式,需要在初始化模块进行配置。
写操作流程如下:
Ø 行激活(ACTIVE)
Ø 等待Trcd时间给出写命令
Ø 写数据
Ø 数据写入完成,Precharge(预充电)所在bank
1.7.3 顶层设计
顶层设计如图10所示,WrTrig信号为外部写请求信号,WrReq信号为写模块向仲裁模块申请,等待WrEn有效才能开始写。
(图10 写模块顶层设计)
1.7.4 接口设计
module SdaramWrite
#(
parameter BURST_LENGTH = 3'b000,
parameter DATALENGTH= 256
)(
input Clk166M ,
input WrTrig ,
input WrEn ,
input [`DQ_BITS-1 : 0] InData ,
input [`DM_BITS-1 : 0] InDataDM,
output Wbusy , //fetch data from ram
output reg [3 : 0] WrCmd ,
output reg [`ADDR_BITS-1: 0] WrAddr ,
output reg [`BA_BITS-1 : 0] WrBa ,
output reg [`DQ_BITS-1 : 0] WrDq ,
output reg [`DM_BITS-1 : 0] WrDqm ,
output WrReq ,
output reg WrDone
);
1.7.5 重点问题
l 数据写完必须进行预充电
l 写操作期间一直发送写命令
1.8.1 读操作时序
Sdram读操作时序如图11所示。
(图11 读操作时序)
1.8.2 实现方式
该模块的功能主要为实现在SDRAM中读出数据。
读流程:
Ø 行激活(ACTIVE)
Ø 等待Trcd时间给出读命令和行地址
Ø 等待Tcl时间数据才能输出(潜伏期)
Ø 读取数据
Ø 数据读取完成,Precharge(预充电)所在bank
1.8.3 顶层设计
顶层设计如图12所示,OutData为数据输出,valid为数据输出有效信号。
(图12 读模块顶层设计)
1.8.4 接口设计
module SdramRead
#(
parameter BURST_LENGTH = 3'b000,
parameter DATALENGTH= 256
)(
input Clk166M ,
input RdTrig ,
input RdEn ,
input [`DQ_BITS-1 : 0] RdDq , //data from sdram
output [`DM_BITS-1 : 0] RdDqm ,
output reg [`DQ_BITS-1 : 0] OutData ,
output valid ,
output Rbusy ,
output reg [3 : 0] RdCmd ,
output reg [`ADDR_BITS-1: 0] RdAddr ,
output reg [`BA_BITS-1 : 0] RdBa ,
output RdReq ,
output reg RdDone
);
1.8.5 重点问题
潜伏期设置(Tcl = 3),本设计的时钟频率166MHz
1.9.1 实现方式
SDRAM 有三种必需的操作: 刷新操作、读操作和写操作。这三种操作之间的协调及相互转换就引入了“仲裁机制”。在需要刷新的时候,给出刷新请求,仲裁模块给出使能信号。在需要读取数据的时候,接收外部的读请求,然后仲裁模块给出响应,写入数据操作类似。如图13所示。
(图13 仲裁设计框图)
1.9.2 顶层设计
(图13 仲裁顶层设计)
1.9.3 接口设计
module SdramArbiter
(
input Clk166M ,
input [3 : 0] InitCmd ,
input [`ADDR_BITS-1: 0] InitAddr,
input [`BA_BITS-1 : 0] InitBa ,
input InitDone,
input RefReq ,
output reg RefEn ,
input [3 : 0] RefCmd ,
input [`ADDR_BITS-1: 0] RefAddr ,
input [`BA_BITS-1 : 0] RefBa ,
input RefDone ,
input WrReq ,
output reg WrEn ,
input [3 : 0] WrCmd ,
input [`ADDR_BITS-1: 0] WrAddr ,
input [`BA_BITS-1 : 0] WrBa ,
input [`DQ_BITS-1 : 0] WrDq ,
input [`DM_BITS-1 : 0] WrDqm ,
input WrDone ,
input RdReq ,
output reg RdEn ,
input [3 : 0] RdCmd ,
input [`ADDR_BITS-1: 0] RdAddr ,
input [`BA_BITS-1 : 0] RdBa ,
output [`DQ_BITS-1 : 0] RdDq ,
input [`DM_BITS-1 : 0] RdDqm ,
input RdDone ,
output reg [3 : 0] Cmd ,
output reg [`ADDR_BITS-1: 0] Addr ,
output reg [`BA_BITS-1 : 0] Ba ,
inout [`DQ_BITS-1 : 0] Dq ,
output reg [`DM_BITS-1 : 0] Dqm
);
1.9.4 重点问题
Ø 双向端口数据处理
Ø 读、写、刷新的仲裁响应
参数设计
parameter tAC = 0.0; //test 6.5
parameter tHZ = 0.0;
parameter tOH = 6;
parameter tMRD = 2.0; // 2 Clk Cycles
parameter tRAS = 42.0;
parameter tRC = 60.0;
parameter tRCD = 18.0;
parameter tRP = 18.0;
parameter tRRD = 12.0;
parameter tWRa = 6.0; // A2 Version - Auto precharge mode only (1 Clk + 7.5 ns)
parameter tWRp = 12.0; // A2 Version - Precharge mode only (15 ns)
本文分享自微信公众号 - 瓜大三哥(xiguazai_tortoise)。
如有侵权,请联系 support@oschina.cn 删除。
本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一起分享。
来源:oschina
链接:https://my.oschina.net/u/4584824/blog/4421157