s3c2440可使用地址空间为1GB(0x00000000到0x40000000)。
1G空间分为8个BANK,每个BANK为128MB。
设27条地址线,和8个片选引脚(nGCS0-nGCS7)。
内存控制器根据地址所在的BANK,自动决定要使用的片选引脚,以使能相应的BANK所连接的设备。
32位CPU不一定用32条地址线。
CPU认为一个地址对应一个字节(8bit)。CPU发出一个地址,要读取内存一个字节的数据(内存在BANK6地址从0x30000000开始),内存控制器操作片选引脚和地址线访问由两个16位内存芯片组成的32位内存时,内存芯片会一次性返回32位数据(4个字节),内存控制器再从中挑出CPU指定的字节。所以这时地址线的[A1:A0]是不用接的。
存储控制器有13个寄存器,地址从0x48000000开始,每个32位(4字节):
BWSCON:总线宽度和等待控制寄存器。[0]保留0值,[2:1]用于设置BANK0的数据宽度,01为16位,10为32位,在Nor起动时使用,由引脚连接状态决定,是只读的,不能软件设置。[3]闲置。
[31:4]共28位,每4位设置一个BANK的参数,比如:
[5:4]设置BANK1的位宽,00表示8bit,01表示16bit,10表示32bit,11保留;
[6]设置BANK1等待使能状态,0 WAIT disable,1WAIT enable;
[7]设置BANK1引脚是否使用UB/LB。
比如设置BWSCON=0x22011110,二进制为0010 0010 0000 0001 0001 0001 0001 0000,这里表示BANK6和BANK7都是32位数据宽度,其他BANK1-BANK5都是16位数据宽度。
BANKCON0-BANKCON5:通过设置6个寄存器的[14:0],分别控制BANK0到BANK5 的时序,用默认值0x0700即可。
BANKCON6和BANKCON7:两个BANK接到内存上,除[14:0]控制时序外,[16:15]用于设置内存类型。根据内存芯片的情况,取值0x00018005。
REFRESH:设置内存刷新
BANKSIZE:设置BANK6/7的内存映射尺寸、电源关闭等,应按内存芯片手册进行设置。
MRSRB6/MRSRB7:SDRAM模式设置寄存器,比如设置行地址、列地址、芯片内bank选择等
设置存储控制器代码如下:
/*
* 设置存储控制器以使用SDRAM
*/
void memsetup(void)
{
volatile unsigned long *p = (volatile unsigned long *)MEM_CTL_BASE;
/* 这个函数之所以这样赋值,而不是像前面的实验(比如mmu实验)那样将配置值
* 写在数组中,是因为要生成”位置无关的代码”,使得这个函数可以在被复制到
* SDRAM之前就可以在steppingstone中运行
*/
/* 存储控制器13个寄存器的值 */
p[0] = 0x22011110; //BWSCON
p[1] = 0x00000700; //BANKCON0
p[2] = 0x00000700; //BANKCON1
p[3] = 0x00000700; //BANKCON2
p[4] = 0x00000700; //BANKCON3
p[5] = 0x00000700; //BANKCON4
p[6] = 0x00000700; //BANKCON5
p[7] = 0x00018005; //BANKCON6
p[8] = 0x00018005; //BANKCON7
/* REFRESH,
* HCLK=12MHz: 0x008C07A3,
* HCLK=100MHz: 0x008C04F4
*/
p[9] = 0x008C04F4;
p[10] = 0x000000B1; //BANKSIZE
p[11] = 0x00000030; //MRSRB6
p[12] = 0x00000030; //MRSRB7
}