微波EDA网,见证研发工程师的成长!
首页 > 硬件设计 > 嵌入式设计 > ARM DDR SDRAM 初始化

ARM DDR SDRAM 初始化

时间:11-10 来源:互联网 点击:
目录: 1.DDR SDRAM 简介

2.DDR 控制器初始化以及DDR SDRAM初始化流程

3.ARM编程初始化DRAM Controller 和DDR SDRAM细节details

备注: 由于DDR SDRAM时序比较复杂,具体时序细节在未来的另一篇博文用FPGA来设计DDR SDRAM控制器中记录。 用FPGA来设计DDR SDRAM控制器相对于直接使用ARM片上的DRAM Controller 要复杂的多。

1.DDR SDRAM introduction

DDR SDRAM本质上就是一个存储器件。它是易失性存储器件。掉电后数据就消失。 你可以把它想象成和简单的单端口RAM和双端口RAM功能一样,可以通过读,写命令,以及对应的地址来访问内部数据。但是它又不像普通的RAM。

(1)首先>> DDR SDRAM在使用前要做一系列的初始化工作。初始化工作包括使能时钟,预充电,自刷新,等待200clks ,设置模式寄存器以及扩展模式寄存器等。初始化完成后,才能进入读写数据状态 。 而且在工作工程中要定期进行刷新,防止电荷丢失掉。

(2)其次>> DDR SDRAM 芯片本身有很多参数需要来设置。

2.1 比如,在写操作时,你先要设定行(row),然后过一段时间再设定列(column)。这段时间就叫RCD (Row Column Delay )

2.2 还有,在读操作时,读命令发出之后数据不会立即被读出,要经过一定的时钟周期。 而这段延时就叫CAS Latency(Column Address Strobe latency)

2.3 自动刷新时间的设置:Ddrsdram芯片一般来说是每64ms刷新一次,刷新是整个bank都要刷新,即有多少行需要来刷新,如果行地址为A12-A0,即有2.*(13)=8192行,即刷新一行需要64ms/8192时间。

还有一些参数,如有时间,今后更新博客中完善。

(3)再者>> DDR SDRAM的行地址和列地址共用同一地址总线,不过这个地址总线何时被用来做行地址或列地址,可以翻看DDR 数据手册,时序是关键。

(4)数据读写时,是在时钟上升沿和下降沿都会有数据传输。这就是DDR SDRAM速度快于SDRAM的原因,这也是名字的由来(Double Data rate SDRAM)。

2.DDR 控制器初始化以及DDR SDRAM初始化流程

见图:

3.ARM编程初始化DRAM Controller 和DDR SDRAM细节details

按着上图所示操作流程,依次写下即可,设置好相关寄存器的值,参考S3C6410手册以及你板子上所用DDR SDRAM芯片手册。sdram初始化子函数如下。

int sdram_init( void )

{

// tell dramc to configure

set_val( MEMCCMD, 0x4 );

// set refresh period

set_val( P1REFRESH, nstoclk(7800) );

// set timing para

set_val( P1CASLAT, ( 3 < 1 ) );

set_val( P1T_DQSS, 0x1 ); // 0.75 - 1.25

set_val( P1T_MRD, 0x2 );

set_val( P1T_RAS, nstoclk(45) );

set_val( P1T_RC, nstoclk(68) );

u32 trcd = nstoclk( 23 );

set_val( P1T_RCD, trcd | (( trcd - 3 ) < 3 ) );

u32 trfc = nstoclk( 80 );

set_val( P1T_RFC, trfc | ( ( trfc-3 ) < 5 ) );

u32 trp = nstoclk( 23 );

set_val( P1T_RP, trp | ( ( trp - 3 ) < 3 ) );

set_val( P1T_RRD, nstoclk(15) );

set_val( P1T_WR, nstoclk(15) );

set_val( P1T_WTR, 0x7 );

set_val( P1T_XP, 0x2 );

set_val( P1T_XSR, nstoclk(120) );

set_val( P1T_ESR, nstoclk(120) );

// set mem cfg

set_nbit( P1MEMCFG, 0, 3, 0x2 ); /* 10 column address */

/* set_nbit: 把从第bit位开始的一共len位消零,然后把这几位设为val */

set_nbit( P1MEMCFG, 3, 3, 0x2 ); /* 13 row address */

set_zero( P1MEMCFG, 6 ); /* A10/AP */

set_nbit( P1MEMCFG, 15, 3, 0x2 ); /* Burst 4 */

set_nbit( P1MEMCFG2, 0, 4, 0x5 );

set_2bit( P1MEMCFG2, 6, 0x1 ); /* 32 bit */

set_nbit( P1MEMCFG2, 8, 3, 0x3 ); /* Mobile DDR SDRAM */

set_2bit( P1MEMCFG2, 11, 0x1 );

set_one( P1_chip_0_cfg, 16 ); /* Bank-Row-Column organization */

// memory init

set_val( P1DIRECTCMD, 0xc0000 ); // NOP

set_val( P1DIRECTCMD, 0x000 ); // precharge

set_val( P1DIRECTCMD, 0x40000 );// auto refresh

set_val( P1DIRECTCMD, 0x40000 );// auto refresh

set_val( P1DIRECTCMD, 0xa0000 ); // EMRS

set_val( P1DIRECTCMD, 0x80032 ); // MRS

set_val( MEM_SYS_CFG, 0x0 );

// set dramc to "go" status

set_val( P1MEMCCMD, 0x000 );

// wait ready

while( !(( read_val( P1MEMSTAT ) & 0x3 ) == 0x1));

}

时间仓促,该文章还需完善。


Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top