Chinaunix首页 | 论坛 | 博客
  • 博客访问: 26528
  • 博文数量: 29
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 10
  • 用 户 组: 普通用户
  • 注册时间: 2014-05-28 13:44
文章分类
文章存档

2014年(29)

我的朋友

分类: LINUX

2014-10-19 22:25:56

 1.安装交叉编译器
这里选择一个比较新的版本:ARM-Linux-gcc 4.5.1
在/usr/local目录下新建一个目录arm,把4.5.1版本拷贝到这里。
然后设置环境变量:在/root/.bashrc文件最后一行添加如下内容:
export PATH=$PATH:/usr/local/arm/4.5.1/bin
保存后注销系统,重新登录后可以用export命令查看是否生效:
root@ubuntu:/# export

declare -x PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/arm/4.5.1/bin"
可以看到设置有效,接下来可以试一下编译Uboot.
2.初试Uboot编译
 先做个简单的编译试一下前面安装的交叉编译器是否能用。
   2.1.把U-boot-2012.10版本解压到/Home/my/smdk6410目录下,
   2.2.修改U-boot-2012.10目录下的Makefile文件
在CROSS_COMPILE ?=这里上面增加两行:
CROSS_COMPILE =/usr/local/arm/4.5.1/bin/arm-linux-
export CROSS_COMPILE
保存后编译:
  root@ubuntu:/home/my/smdk6410/u-boot-2012.10# make clean
这时如果没有提示出错的话说明交叉编译器安装成功了,接下来:
  root@ubuntu:/home/my/smdk6410/u-boot-2012.10# make smdk6400_config
  root@ubuntu:/home/my/smdk6410/u-boot-2012.10# make 
.
3.Uboot移植到smdk6410上

  因为是板级移植,所以我们先复制一份SMDK6400改为smdk6410。

 3.1.需要拷贝的文件&目录有:
    3.1.1.拷贝board/samsung/smdk6400 到board/samsung/smdk6410
    3.1.2.拷贝nand_spl/board/samsung/smdk6400 到 nand_spl/board/samsung/smdk6410
    3.1.3.拷贝include/configs/smdk6400.h 到include/configs/smdk6410.h
    3.1.4.拷贝include/asm/arch/s3c6400.h 为 include/asm/arch/s3c6410.h

  3.2.需要更改名称的文件有:
    3.2.1.更改board/samsung/smdk6410目录下smdk6400.c 为smdk6410.c ,

    3.2.2.更改smdk6400_nand_spl.c为smdk6410_nand_spl.c 
    3.2.3.更改nand_spl/board/samsung/smdk6410目录下smdk6400_nand_spl.c为smdk6410_nand_spl.c

 3.3.需要修改内容的文件有:
  3.3.1. board/samsung/smdk6410/Makefile
  把其中有SMDK6400的相关字符换成smdk6410
   3.3.2. nand_spl/board/samsung/smdk6410/Makefile
  把其中有SMDK6400的相关字符换成smdk6410
   3.3.3. u-boot-2011.12目录下Makefile
  找到ARM1176 Systems部分,把smdk6400都换成smdk6410
   3.3.4. 把所有#include 都改为#include
   3.3.5. arch/arm/cpu/arm1176/s3c64xx/Makefile
把COBJS-$(CONFIG_S3C6400)改为COBJS-$(CONFIG_S3C6410)
   3.3.6. include/configs/smdk6410.h
把#define CONFIG_S3C6400 1 改为 #define CONFIG_S3C6410 1
把#define CONFIG_SMDK6400 1 改为 #define CONFIG_SMDK6410 1

好了,在u-boot-2011.12目录下
  make smdk6410_config 
  make

编译通过,说明复制成功了,但这时的u-boot还是SMDK6400的,所以我们还要修改,才能在OK6410板上运行起来。

4.配置板上资源使uboot能够在板上运行。

   这里说的运行指的是下载到SDRAM后能够跑起来。

   4.1.修改/include/configs/smdk6410.h

         4.1.1 #define CONFIG_S3C6410        1    /* in a SAMSUNG S3C6400 SoC */

         4.1.2 #define CONFIG_SMDK6410     1    /* on a SAMSUNG SMDK6400 Board */   

         4.1.3 #define CONFIG_SYS_PROMPT "SMDK6410 # " /* Monitor Command Prompt */

         4.1.4#define CONFIG_NR_DRAM_BANKS 2 //2个128M的chip
         4.1.5#define PHYS_SDRAM_1 CONFIG_SYS_SDRAM_BASE /* SDRAM Bank #1 */
         4.1.6#define PHYS_SDRAM_1_SIZE 0x08000000 /* 128 MB in Bank #1 */
        //zxd-->
         4.1.7#define PHYS_SDRAM_2 (CONFIG_SYS_SDRAM_BASE+PHYS_SDRAM_1_SIZE)/* SDRAM Bank #1 */
         4.1.8#define PHYS_SDRAM_2_SIZE 0x08000000 /* 128 MB in Bank #1 */
        //<--

 这里4.1.4到4.1.8暂时不修改也可以,但运行后显示SDRAM 128M。或者把4.1.6中的0x08000000改为0x10000000再配合后面的修改也可以显示256M的SDRAM。

         4.1.9#define CONFIG_IDENT_STRING    " for SMDK6410"

         4.1.10#define CONFIG_SYS_NAND_PAGE_SIZE 4096//2048
         4.1.11#define CONFIG_SYS_NAND_BLOCK_SIZE (512 * 1024)//128
         4.1.12#define CONFIG_SYS_NAND_PAGE_COUNT 128//64。

这里4.1.10到4.1.12暂时不修改也可以,改它是为了后面NAND驱动的都写都能正常

  4.2.修改/board/samsung/smdk6410/lowlevel_init.S

         4.2.1修改LED显示

                   /* LED on only #8 */
                        ldr r0, =ELFIN_GPIO_BASE
                        ldr r1, =0x00111111
                        str r1, [r0, #GPMCON_OFFSET]

                        ldr r1, =0x00000555
                        str r1, [r0, #GPMPUD_OFFSET]

                        ldr r1, =0x0027
                        str r1, [r0, #GPMDAT_OFFSET]

        4.2.2修改这段This was unconditional in original Samsung sources.......屏蔽掉宏定义

//#ifndef CONFIG_S3C6410
ldr r1, [r0, #OTHERS_OFFSET]
bic r1, r1, #0xC0
orr r1, r1, #0x40
str r1, [r0, #OTHERS_OFFSET]

wait_for_async:
ldr r1, [r0, #OTHERS_OFFSET]
and r1, r1, #0xf00
cmp r1, #0x0
bne wait_for_async
//#endif

         4.2.3修改这句

#elif !defined(CONFIG_S3C6400)为

#elif !defined(CONFIG_S3C6410)
/* According to 661558um_S3C6400X_rev10.pdf 0x20 is reserved */

          4.2.4要想正确显示SDRAM大小,除了上面4.1.6外还要在这里修改MMU关于内存这部分:

/* 128MB for SDRAM 0xC0000000 -> 0x50000000 */
.set __base, 0x500
.rept 0xD00 - 0xC00    //.rept 0xc80 - 0xC00
FL_SECTION_ENTRY __base, 3, 0, 1, 1
.set __base, __base + 1
.endr

/* access is not allowed. */
.rept 0x1000 - 0xD00  //.rept 0x1000 - 0xc80
.word 0x00000000
.endr

5.下载uboot到SDRAM中运行

    5.1  先使用IROM_Fusing_Tool.exe把OK6410_SDboot.nb0烧录到SD卡中

    5.2 设置开发板从SD卡启动。打开DNW,设置下载地址为0x57e00000,启动开发板后通过DNW把编译好的u-boot.bin下载到SDRAM中,下载后DNW窗口显示:

U-Boot 2012.10 (Nov 05 2012 - 17:29:28) for SMDK6410
CPU: S3C6410@533MHz
Fclk = 533MHz, Hclk = 133MHz, Pclk = 66MHz (ASYNC Mode)
Board: SMDK6410
DRAM: 256 MiB


然后。。。。。。系统重启了:
6.调试
跟踪发现board.c(/arch/arm/lib)中有两个函数board_init_f和board_init_r。显示SDRAM: 256 MiB就是在board_init_f函数中实现,而board_init_r会接着初始化FLASH等,查看这个函数发现显示FLASH及NAND大小都是在这个函数中实现。但为什么会没有打印信息而是直接重启了呢?难道系统还没有走到这个board_init_r函数就发生了错误?为了验证这个猜想,在这个board_init_r函数开头弄串字符输出看看,把puts("I am here! ");这句话放在board_init_r函数的开头,重新编译出现:
U-Boot 2012.10 (Nov 05 2012 - 23:52:29) for SMDK6410
CPU: S3C6410@533MHz

Fclk = 533MHz, Hclk = 133MHz, Pclk = 66MHz (ASYNC Mode)

Board: SMDK6410

DRAM: 256 MiB

I am here! WARNING: Caches not enabled

Flash: *** failed ***

### Error ### Please RESET the Board ###

这说明board_init_r这个函数还是有执行的。后面测试发现无论把puts("I am here! ");放在board_init_f或board_init_r中都可以输出
。。。。。。

WARNING: Caches not enabled

Flash: *** failed ***

### Error ### Please RESET the Board ###
程序到这里就停住了。

再看看board_init_r函数里到底有什么吧。
。。。。。。。
#if !defined(CONFIG_SYS_NO_FLASH)
puts("Flash: ");

flash_size = flash_init();
if (flash_size > 0) {
# ifdef CONFIG_SYS_FLASH_CHECKSUM
char *s = getenv("flashchecksum");

print_size(flash_size, "");
/*
* Compute and print flash CRC if flashchecksum is set to 'y'
*
* NOTE: Maybe we should add some WATCHDOG_RESET()? XXX
*/
if (s && (*s == 'y')) {
printf(" CRC: %08X", crc32(0,
(const unsigned char *) CONFIG_SYS_FLASH_BASE,
flash_size));
}
putc('\n');
# else /* !CONFIG_SYS_FLASH_CHECKSUM */
print_size(flash_size, "\n");
# endif /* CONFIG_SYS_FLASH_CHECKSUM */
} else {
puts(failed);
hang();
}
#endif

#if defined(CONFIG_CMD_NAND)
puts("NAND: ");
nand_init(); /* go init the NAND */
#endif
。。。。。。
显然“*** failed ***”就是puts(failed)这个函数干的。而“### Error ### Please RESET the Board ###”又是谁出的主意呢?调查hang()发现:
void hang(void)
{
puts("### ERROR ### Please RESET the board ###\n");
for (;;);
}
元凶在此,OK6410开发板上并没有这个FLASH,所以先屏蔽掉hang()试试吧,也把测试的那句puts("I am here! ")去掉,下载后DNW显示如下:
U-Boot 2012.10 (Nov 05 2012 - 23:52:29) for SMDK6410

CPU: S3C6410@533MHz

Fclk = 533MHz, Hclk = 133MHz, Pclk = 66MHz (ASYNC Mode)

Board: SMDK6410

DRAM: 256 MiB

WARNING: Caches not enabled

Flash: *** failed ***

NAND: raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

No oob scheme defined for oobsize 218

2048 MiB

*** Warning - bad CRC, using default environment


In: serial

Out: serial

Err: serial

Net: CS8900-0

Hit any key to stop autoboot: 0


NAND read: device 0 offset 0x60000, size 0x1c0000

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught

raise: Signal # 8 caught
。。。。。(后面是不停地打印raise: Signal # 8 caught)。
OK,关于“Signal # 8 caught”的问题后面再解决,但怎么也想不明白屏蔽hang()之前加上测试
puts("I am here! ")就可以让程序正常的运行呢?

元芳,你怎么看?










阅读(286) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~