该博客主要记录和总结我在工作中遇到的问题和积累的经验。如有错误之处,谢请指正。
共享资源,欢迎转载:http://blog.youkuaiyun.com/fzu_dianzi
一、环境
目标板:mini2440
u-boot版本:u-boot-2009.08
交叉编译器:arm-linux-gcc-4.3.2
操作系统:Linux(Ubuntu-11.10)
二、目的
修改cpu/arm920t/start.s包括时钟部分、中断部分、看门狗
修改cpu/arm920t/
增加mini2440的板子定义
三、步骤
1、 注释LED跳转
cpu/arm920t/start.s第117行,这部分的LED初始化代码是为AT91RM9200DK开发板写的。这里我们注释掉跳转语句
blcoloured_LED_init
blred_LED_on
@bl coloured_LED_init
@bl red_LED_on
2、 添加板子宏定义
在include/configs/mini2440.h 文件中去掉s3c2410的宏定义,修改为:
#define CONFIG_S3C2440 1 /*in a SAMSUNG S3C2440 SoC */
3、 CPU频率定义
S3c2440比s3c2410的频率要高,为405MHZ。所以我们必须要修改CPU频率设置的代码。
#if defined(CONFIG_S3C2400)|| defined(CONFIG_S3C2410)
/* turn off the watchdog */
# ifdefined(CONFIG_S3C2400)
# define pWTCON 0x15300000
# define INTMSK 0x14400008 /* Interupt-Controller base addresses */
# define CLKDIVN 0x14800014 /* clockdivisor register */
#else
# define pWTCON 0x53000000
# define INTMSK 0x4A000008 /* Interupt-Controller base addresses */
# define INTSUBMSK 0x4A00001C
# define CLKDIVN 0x4C000014 /* clockdivisor register */
# endif
修改为
#ifdefined(CONFIG_S3C2400) || defined(CONFIG_S3C2410) || defined(CONFIG_S3C2440)
/* turn off the watchdog */
# ifdefined(CONFIG_S3C2400)
# define pWTCON 0x15300000
# define INTMSK 0x14400008 /* Interupt-Controller base addresses */
# define CLKDIVN 0x14800014 /* clockdivisor register */
#else
# define pWTCON 0x53000000
# define INTMSK 0x4A000008 /* Interupt-Controller base addresses */
# define INTSUBMSK 0x4A00001C
# define CLKDIVN 0x4C000014 /*clock divisor register */
# endif
#define CLK_CTL_BASE 0x4c000000
#define MDIV_405 0x7f << 12
#define PSDIV_405 0x21
#define MDIV_200 0xa1 << 12
#define PSDIV_200 0x31
由于S3C2410和S3C2440的MPLL、UPLL计算公式不一样,所以get_PLLCLK函数也需要修改
get_PLLCLK函数在cpu\arm920t\s3c24x0\speed.c
static ulongget_PLLCLK(int pllreg)
{
S3C24X0_CLOCK_POWER * const clk_power =S3C24X0_GetBase_CLOCK_POWER();
ulong r, m, p, s;
if (pllreg == MPLL)
r = clk_power->MPLLCON;
else if (pllreg == UPLL)
r = clk_power->UPLLCON;
else
hang();
m = ((r & 0xFF000) >> 12) + 8;
p = ((r & 0x003F0) >> 4) + 2;
s = r & 0x3;
#ifdefined(CONFIG_S3C2440)
if(pllreg == MPLL)
{
return((CONFIG_SYS_CLK_FREQ * m * 2) /(p << s));
}
#endif
return((CONFIG_SYS_CLK_FREQ * m) / (p<< s));
}
由于S3C2410和S3C2440的设置方法也不一样,所以get_HCLK函数也需要修改
get_HCLK函数在cpu\arm920t\s3c24x0\speed.c
ulong get_HCLK(void)
{
S3C24X0_CLOCK_POWER * const clk_power =S3C24X0_GetBase_CLOCK_POWER();
#ifdefined(CONFIG_S3C2440)
return(get_FCLK()/4);
#endif
return((clk_power->CLKDIVN & 0x2) ?get_FCLK()/2 : get_FCLK());
}
4、 中断部分修改
2410的datasheet上,INTSUBMSK有11位可用,而2440的INTSUBMSK有15位可用
# ifdefined(CONFIG_S3C2410)
ldr r1, =0x3ff
ldr r0, =INTSUBMSK
str r1, [r0]
# endif
修改为
# ifdefined(CONFIG_S3C2410)
ldr r1, =0x7ff
ldr r0, =INTSUBMSK
str r1, [r0]
# endif
# ifdefined(CONFIG_S3C2440)
ldr r1, =0x7fff
ldr r0, =INTSUBMSK
str r1, [r0]
# endif
5、 时钟部分修改
/* FCLK:HCLK:PCLK = 1:2:4 */
/* default FCLK is 120 MHz ! */
ldr r0, =CLKDIVN
mov r1, #3
str r1, [r0]
#endif /* CONFIG_S3C2400 || CONFIG_S3C2410 ||CONFIG_S3C2440*/
修改为
#ifdefined(CONFIG_S3C2440)
/* FCLK:HCLK:PCLK = 1:4:8 */
ldr r0, =CLKDIVN
mov r1, #5
str r1, [r0]
mrc p15, 0, r1, c1, c0, 0
orr r1, r1, #0xc0000000
mrc p15, 0, r1, c1, c0, 0
mov r1, #CLK_CTL_BASE
mov r2, #MDIV_405
add r2, r2, #PSDIV_405
str r2, [r1, #0x04]
#else
/* FCLK:HCLK:PCLK = 1:2:4 */
/* default FCLK is 120 MHz ! */
ldr r0, =CLKDIVN
mov r1, #3
str r1, [r0]
mrc p15, 0, r1, c1, c0, 0
orr r1, r1, #0xc0000000
mrc p15, 0, r1, c1, c0, 0
mov r1, #CLK_CTL_BASE
mov r2, #MDIV_200
add r2, r2, #PSDIV_200
str r2, [r1, #0x04]
#endif
#endif /* CONFIG_S3C2400 || CONFIG_S3C2410 ||CONFIG_S3C2440*/
6、 对一些编译选项添加宏定义CONFIG_s3c2440
Ø include/common.h[496行]
#ifdefined(CONFIG_S3C2400) || defined(CONFIG_S3C2410) || \
defined(CONFIG_LH7A40X) || defined(CONFIG_S3C6400)
修改为
#ifdefined(CONFIG_S3C2400) || defined(CONFIG_S3C2410) || \
defined(CONFIG_LH7A40X) || defined(CONFIG_S3C6400) || defined (CONFIG_S3C2440)
Ø cpu\arm920t\s3c24x0\interrupts.c[36行]
#elifdefined(CONFIG_S3C2410)
修改为
#elifdefined(CONFIG_S3C2410) ||defined(CONFIG_S3C2440)
Ø cpu\arm920t\s3c24x0\usb_ohci.c[43行]
#elifdefined(CONFIG_S3C2410)
修改为
#elif defined(CONFIG_S3C2410) || defined(CONFIG_S3C2440)
Ø cpu\arm920t\s3c24x0\usb.c[27行]
# ifdefined(CONFIG_S3C2400) || defined(CONFIG_S3C2410)
修改为
# ifdefined(CONFIG_S3C2400) || defined(CONFIG_S3C2410) || defined(CONFIG_S3C2440)
[31行]
#elifdefined(CONFIG_S3C2410)
修改为
#elifdefined(CONFIG_S3C2410) ||defined(CONFIG_S3C2440)
Ø cpu\arm920t\s3c24x0\timer.c[33行]
#ifdefined(CONFIG_S3C2400) || defined (CONFIG_S3C2410) || defined (CONFIG_TRAB)
修改为
#ifdefined(CONFIG_S3C2400) || defined (CONFIG_S3C2410) || defined (CONFIG_TRAB) || defined (CONFIG_S3C2440)
[37行]
#elifdefined(CONFIG_S3C2410)
修改为
#elifdefined(CONFIG_S3C2410) || defined(CONFIG_S3C2440)
Ø cpu\arm920t\s3c24x0\speed.c[33行]
#ifdefined(CONFIG_S3C2400) || defined (CONFIG_S3C2410) || defined (CONFIG_TRAB)
修改为
#if defined(CONFIG_S3C2400)|| defined (CONFIG_S3C2410) || defined (CONFIG_TRAB) || defined (CONFIG_S3C2440)
[37行]
#elifdefined(CONFIG_S3C2410)
修改为
#elifdefined(CONFIG_S3C2410) || defined(CONFIG_S3C2440)
Ø drivers\serial\serial_s3c24x0.c[24行]
#elif defined(CONFIG_S3C2410)
修改为
#elifdefined(CONFIG_S3C2410) ||defined(CONFIG_S3C2440)
Ø drivers\rtc\s3c24x0_rtc.c[35行]
#elifdefined(CONFIG_S3C2410)
修改为
#elifdefined(CONFIG_S3C2410) ||defined(CONFIG_S3C2440)
7、 具体平台相关修改
修改board/Samsung/mini2440/lowlevel_init.S
在128行后添加
#ifdefined(CONFIG_S3C2440)
#define Trp 0x2
#define REFCNT 1012
#else
#define Trp 0x0
#define REFCNT 0x0459
#endif
修改2440板初始化函数,board\samsung\mini2440\mini2440.c
在board_init函数里面修改板子型号
gd->bd->bi_arch_number= MACH_TYPE_S3C2440;
四、成果
编译u-boot。将编译生成的u-boot.bin通过J-Flash烧写到NorFlash。终端输出了信息,移植工作成功了小一部分~~很是开心。