U-Boot的移植入门(1)——增加对NorFlash的支持

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

U-Boot的移植入门(1)——增加对NorFlash的支持
U-Boot 的移植入门(1)——增加对NorFlash的支持2010-02-09 02:12:13
分类:嵌入式
第二步、增加对NorFlash的支持
接下来,我们来提供对于Nor Flash的支持。

U-Boot的SMDK2410相关部分是完整的支持AMD的两块NorFlash的,可惜我们的板子上带的是SST39VF1601。

不过,对于NorFlash的支持还是比较简单的。

我们依然来追踪U-Boot的执行流,在lib_arm/board.c文件中我们可以看到:
#ifndef CONFIG_SYS_NO_FLASH
/* configure available FLASH banks */
display_flash_config (flash_init ());
#endif /* CONFIG_SYS_NO_FLASH */
默认情况下,U-Boot实际上支持了Nor Flash的。

追踪flash_init 函数,在board/Samsung/mini2440/mini2440.c文件中可以找到它。

我们的flash移植修改的主要代码也就在这儿了。

首先,修改配置文件中的相关部分。

在include/configs/mini2440.h文件中,将
#define CONFIG_AMD_LV400 1 /* uncomment this if you have a LV400 flash */
#if 0
#define CONFIG_AMD_LV800 1 /* uncomment this if you have a LV800 flash */
#endif
修改为:
#if 0
#define CONFIG_AMD_LV400 1 /* uncomment this if you
have a LV400 flash */
#define CONFIG_AMD_LV800 1 /* uncomment this if you have a LV800 flash */
#endif
然后添加:
#define CONFIG_SST_xF1601 1
#ifdef CONFIG_SST_xF1601
#define PHYS_FLASH_SIZE 0x00200000 /* 2MB */
#define CONFIG_SYS_MAX_FLASH_SECT (32) /* max number of sectors on one chip */
#defne CONFIG_ENV_ADDR (CONFIG_SYS_FLASH_BASE + 1F0000)
这几个宏的意思基本上都还是比较明确的。

接下来来看board/Samsung/mini2440/flash.c文件中的flash_init函数,添加设置flash_id的代码:
#elif defined(CONFIG_SST_VF1601)
(SST_MANUFACT & FLASH_VENDMASK) |
(SST_ID_xF1601 & FLASH_TYPEMASK);
#else
找到了AMD_MANUFACT定义的地方,也就能找到这些我们需要的宏了。

接着,修改设置各个sector起始地址的代码,将原来的循环改为:for (j = 0; j < flash_info[i].sector_count; j++) {
#ifndef CONFIG_SST_VF1601
if (j <= 3) {
/* 1st one is 16 KB */
if (j == 0) {
flash_info[i].start[j] =
flashbase + 0;
}
/* 2nd and 3rd are both 8 KB */
if ((j == 1) || (j == 2)) {
flash_info[i].start[j] =
flashbase + 0x4000 + (j -1) *0x2000;
}
/* 4th 32 KB */
if (j == 3) {
flash_info[i].start[j] =
flashbase + 0x8000;
}
} else {
flash_info[i].start[j] =
flashbase + (j - 3) * MAIN_SECT_SIZE;
}
#else
flash_info[i].start[j] =
flashbase + (j) * MAIN_SECT_SIZE;
#endif
接着修改flash_print_info函数,这个函数很容易理解也很容易修改。

接着来修改用来擦除flash的flash_erase函数。

原来的代码,前面判断如果不是AMD的芯片,它会直接返回,这个地方需要修改。

另外,SST39VF1601的命令和原来带的是不一样的,修改几个命令的宏定义,将原来的改为:
#define MEM_FLASH_ADDR1 (*(volatile u16 *)(CONFIG_SYS_FLASH_BASE + (0x000005555 << 1))) #define MEM_FLASH_ADDR2 (*(volatile u16 *)(CONFIG_SYS_FLASH_BASE + (0x000002AAA << 1))) #define CMD_ERASE_CONFIRM 0x00000050
等待完成的部分也需要做一些小小的改动,注释掉原来的代码,添加:
/* wait until flash is ready */
while(1){
unsigned short i;
i = *((volatile unsigned short *)addr) & 0x40;
if(i != (*((volatile unsigned short *)addr) & 0x40))
continue;
if((*((volatile unsigned short *)addr)) & 0x80)
break;
}
接下来,修改flash的编程函数write_hword。

注意,mini2440的flash编程需要四个步骤,第三个步骤是往MEM_FLASH_ADDR1里写CMD_PROGRAM。

然后修改等待完成的部分,将原来的修改为:/* wait until flash is ready */
while(1){
unsigned short i = *(volatile unsigned short *)addr & 0x40;
if(i != (*(volatile unsigned short *)addr & 0x40)) //D6 == D6 continue;
if((*(volatile unsigned short *)addr & 0x80) == (data & 0x80)){
rc = ERR_OK;
break; //D7 == D7
}
这样,就完成了flash驱动的移植。

可以通过cp命令,往flash中写东西来进行测试。

注意,U-Boot里面用的词sector和手册里面用的词sector指的不是同一个意思,U-Boot里的sector和手册里的block是等价的,是一个更大的单位。

相关文档
最新文档