ARM存储器控制器的使用


把代码从steppingstone拷贝到sdram中运行,大小为4kb
学习存储器寄存器的配置。
参考s3c2440和sdram的datasheet,很容易地把寄存器配置好,就可以使用SDRAM了

存储控制器的寄存器总共有13个:SWSCON, BANKCONx (x=0~7),  REFRESH, BANKSIZE, MRSRB6, MRSRB7

SDRAM只需配置好SWSCON, BANKCON6,, BANKCON7, REFRESH, BANKSIZE, MRSRB6, MRSRB7, 一共7个寄存器

1.BWSCON位宽和等待控制寄存器
 每4位控制一个BANK。最高4位控制bank7,递减类推。
 STx: 内存为SDRAM,此位为0,SRAM的为1
 WSx:通常设为0
 DWx:用两位来设置位宽,0b00为八位,0b01为16位,0b10为32位,0b11为保留
 
 我的开发板上是MT48LC16M16A2P型号的16位SDRAM,由2片组成32为的SDRAM,所以我设置的高4位为0b0010,。BANK6与BANK7的设置需相

同,不管你用不用到BANK7,所以这里设子和为BWSCON=0x22000000
 
BANKCON6与BANKCON7
  MT[16:15]: 设置bank外接的存储器类型,0b00为SRAM,0b11为SDRAM
 设置为0b00的sram,其他位的设置与bank[1:5]的类似,设置为SDRAM的,其他未进行如下设置:
 Trcd[3:2]: RAS to CAS delay, 我使用保守值:0b10
 Scan[1:0]: SDRAM的列地址位数,0b00表示8位,0b01表示9位,0b10表示10位。查阅内存的datasheet得知,我的开发板上的是9

位,
所以,本开发板的bank6,bank7都设置为BANKCONx=0x00018005

刷新控制REFRESH
  R_CNT[10:0]: 由公式R_CNT=2^11 + 1 - SDRAM频率(MHz) * SDRAM刷新周期(us)
查阅内存datasheet,我的是64ms 8,192-cycle refresh,所以刷新周期=64ms/8192=7.8125us
这里我还没使用PLL,sdram频率为晶振频率12MHz,
计算R_CNT=2^11 + 1 - 12 * 7.8125 = 1955
所以我的REFRESH设置为0x008c0000(其他位的固定设置) + 1955 = 0x008c07a3

BANKZIZE
 Bk76map[2:0]: bank6,7的大小,0b001为65mb
我这里设置为0xb1
SDRAM模式设置
只需修改为CL[6:4],这是时序时间参数,我用保守值MRSRB67=0X30

设置好这些寄存器,内存就可以使用了。

TQ2440开发板
编译环境:
 Arm-linux-gcc 3.4.5(编译器版本不同可能出错)
硬件配置:
 ARM: S3C2440A
 MEM: MT48LC16M16A2
 
资料:S3C2440官方文档与MT48LC16M16A2的datasheet

附录源码:
源码文件如下
启动代码:
@******************************************************************
@ file:2440init.S
@ set SDRAM, copy code to SDRAM, and run it
@******************************************************************

.equ BWSCON,  0x48000000
.equ SDRAM_BASE, 0x30000000
.equ WTCON,  0x53000000

.extern  main
.text
.global start
start:
 bl  disable_watch_dog   @关闭看门狗
 bl  memsetup     @设置内存寄存器
 bl copy_steppingstone_to_sdram
 ldr pc, =on_sdram    @转跳到SDRAM中执行代码
 @程序连接时设置开头为0x30000000,这里使pc等于绝对地址,就到SDRAM里执行去了

@******************************************************************
on_sdram:
 ldr sp, =0x34000000    @设置栈
 bl main

@******************************************************************
halt_loop:
 b halt_loop

@******************************************************************
disable_watch_dog:
 mov r1, #WTCON
 mov r2, #0x0
 str r2, [r1]
 mov pc, lr @返回

@******************************************************************
copy_steppingstone_to_sdram:
 @把steppingstone的4kb数据全部复制到sdram中
 @ 0x00000000   ==>   0x30000000
 
 mov r1, #0x00000000
 ldr r2, =SDRAM_BASE
 mov r3, #1024*4
copyloop:
 ldr r4, [r1], #4
 str r4, [r2], #4
 cmp r1, r3
 bne copyloop
 mov pc, lr
 
 
@******************************************************************
memsetup:
 mov r1, #BWSCON    @MEM 13个寄存器的开始地址
 adrl r2, mem_conf  
 add r3, r1, #52    @13 * 4 = 52
memloop:
 ldr r4, [r2], #4
 str r4, [r1], #4
 cmp r1, r3
 bne memloop
 mov pc, lr

.align 4
mem_conf:
 @13个MEM寄存器设置值
 .long 0x22000000 @BWSCN
 .long 0x00000700 @BANKCON0
 .long 0x00000700 @BANKCON1
 .long 0x00000700 @BANKCON2
 .long 0x00000700 @BANKCON3
 .long 0x00000700 @BANKCON4
 .long 0x00000700 @BANKCON5
 .long 0x00018005 @BANKCON6
 .long 0x00018005 @BANKCON7
 .long 0x008c07a3 @REFRESH
 .long 0x000000b1 @BANKSIZE
 .long 0x00000030 @MRSRB6
 .long 0x00000030 @MRSRB7

C文件:
/* 
 * file:  led.c
 * 功能:流水灯(学习io的使用)
 * 硬件:GPB[5:8] 对应led[1:4],低电平点亮
 * 多功能IO口的寄存器有3个:(查阅ARM芯片资料)
  GPxCON:选择引脚功能,两位对应一根引脚,00输入,01输出,10特殊功能,11保留
  GPxDAT: 用于读写引脚
  GPxUP:  上拉电阻,0使用上拉电阻,1禁止上拉电阻
 * crazyleen <[email protected]> 2010/10/14 10:59:42
 */

//sfr
#define GPBCON      (*(volatile unsigned long *)0x56000010)
#define GPBDAT      (*(volatile unsigned long *)0x56000014)

//0b01,选择输出功能
#define GPB5_OUT (1 << (5 * 2))
#define GPB6_OUT (1 << (6 * 2))
#define GPB7_OUT (1 << (7 * 2))
#define GPB8_OUT (1 << (8 * 2))

void delay(void)
{
 int i;
 for(i = 50000; i > 0; i--);
}

void ledplayer()
{
  unsigned int led = (1 << 5);
  for( ; led < (1 << 10); led <<= 1){ 
   GPBDAT = ~led;
   delay();
  }
  GPBDAT = 0; 
  delay();
  GPBDAT = ~0; 
  delay();
}

int main()
{
    GPBCON = GPB5_OUT | GPB6_OUT | GPB7_OUT | GPB8_OUT; //初始化GPB[5:8],输出功能
 
 while(1){
  ledplayer();
 }
    return 0;
}

Makefile文件:
sdram_led.bin: 2440init.S led.c
 arm-linux-gcc -g -c -o 2440init.o 2440init.S
 arm-linux-gcc -g -c -o led.o led.c
 arm-linux-ld -Ttext 0x30000000 -g 2440init.o led.o -o sdram_led_elf
 arm-linux-objcopy -O binary -S sdram_led_elf sdram_led.bin
 arm-linux-objdump -D -m arm sdram_led_elf > sdram_led.dis
clean:
 rm -f *.o sdram_led_elf sdram_led.dis sdram_led.bin

你可能感兴趣的:(c,File,存储,makefile,编译器,delay)