uboot移植——使用三星官方的uboot进行移植
2017-04-16 16:26
232 查看
以下内容源于朱有鹏嵌入式课程的学习,如有侵权,请告知删除。
参考资料:http://www.cnblogs.com/biaohc/p/6460902.html
总结的思维导图下载地址:https://pan.baidu.com/s/1nvilb6L
由于我们使用210的cpu,因此选择三星的210开发板的配置。
(1)board目录下:把不相关的开发板的文件全部删除只保留:board->samsung->common文件夹以及board->samsung->smdkc110文件夹;
每个文件夹代表一个开发板。
(2)cpu目录下:只保留s5pc11x文件夹,其他全部删除;
(3)include目录下:asm-开头的文件只保留asm-arm;asm-arm目录下arch-开头的文件只保留s5pc11x;
(4)include/configs目录下:只保留smdkv210single.h文件;每一个开发板对应一个.h文件。
(5) lib_ 开头的文件夹保留lib_arm、lib_generic 。
然后在用sourceinsight生成project。
(2)把生成的uboot.bin文件烧录到sd卡中。
首先注意的是烧写时要在uboot根目录下,烧写命令:./sd_fusing.sh /dev/sdb;
注意sd_fusing脚本中,烧写的内容是不是uboot.bin、uboot.bin的路径对不对,..在此表示 ~/uboot/;
利用file mkbl1查看mkbl1是不是32bit的,如果不是,则需要在sd_fusing目录下执行make clean,然后再make。
sd_fusing.sh文件中,/mkbl1 ../u-boot.bin SD-bl1-8k.bin 8192表示将uboot的前8k复制到SD-bl1-8k.bin文件中;
执行此sd_fusing.sh脚本即可把bl1、uboot.bin烧录到sd卡中。
(3)启动开发板,发现电源置锁,只有一句SD checksum Error,没有打印出ok。
分析:uboot中串口最早的输出“OK”,在lowlevel_init.S中初始化串口时打印出来的;串口无输出"O"说明在打印"O"之前代码已经死掉了;开发板供电锁存在lowlevel_init.S中,开发板供电锁存成功说明这个代码之前的部分是没问题的。
结论:错误发生在开发板供电锁存代码和串口初始化打印"O"代码。
在lowlevel_ini t函数中,PMIC_InitIp函数是用来管理电源的。由于210开发板没有用到这个功能,所以程序卡在此函数中。只要把此函数注释掉即可。
(1)开始打印U-BOOT的版本号,由display_banner 这个函数中实现。
想要修改“for SMDKV210”这个信息,只需在smdkv210single.h中修改这个宏定义CFG_PROMPT即可。如下
(2)时钟信息是对的。
时钟信息是在print_cpuinfo这个函数中打印出来的。
时钟部分的代码在lowlevel_init.S中的bl system_clock_init调用的函数中。
函数的代码部分是没任何问题的,不需要改动。
如果时钟部分要更改,关键是去更改头文件中的宏定义。
三星移植时已经把210常用的各种时钟配置全都计算好用宏开关来控制了。只要打开相应的宏开关就能将系统配置为各种不同的频率。
(3)下面的信息是在checkboard函数中打印的
如果要修改这个信息,可以在这个函数中修改。
在board\samsung\smdkc110.c文件中
首先,看一下原来的DRAM中的配置信息(在smdkv210single.h中进行配置):
可知,这里有两块DRAM,大小均为512M(故总显示为1GB),但实际我们x210开发板只有512MB。
因此修改如下:#define SDRAM_BANK_SIZE 0x10000000 /* 256 MB */
其次,DRAM0和DRAM1的地址,分别为0x20000000~0x2FFFFFFF(256MB),0x40000000~0x4FFFFFFF(256MB)。
我们希望起始内存的地址为0x3000_0000~0x4FFF_FFFF,因此需要DDR地址另外配置。
步骤1:更改寄存器的值(可看做硬件配置部分的修改)
(1)根据裸机中DDR初始化部分的课程,和uboot中DDR初始化部分的代码的课程,得出结论
DDR的初始化代码部分是在lowlevel_init.S中写的,是不动的,代码部分就是对相应寄存器做相应值的初始化;
要动的是值,而uboot为了具有可移植性把值都宏定义在include/configs/xxx.h中了。
因此我们只需要去这个配置头文件中更改配置值即可。
(2)#define DMC0_MEMCONFIG_00x20E01323 改为:#define DMC0_MEMCONFIG_00x30E01323
实际发现还是运行不了,需要改为 #define DMC0_MEMCONFIG_00x30F01323
步骤2:软件配置值更改
寄存器的值改了后相当于是硬件配置部分做了更改。但是uboot中DDR相关的一些,还在原来位置,所以要去更改。
在include\configs\smdkv210single.h中,将#defineMEMORY_BASE_ADDRESS0x20000000 改为 #define MEMORY_BASE_ADDRESS0x30000000。
步骤3:[b]虚拟地址映射表中相应修改[/b]
(1)uboot中开启了MMU对内存进行了段式映射,有一张内存映射表。
(2)修改发生在lowlevel_init.S中的mmu_table标签这块内容里。
(2)经过实际分析,发现这个内存映射只是把20000000开始的256MB映射到C0000000开头的256MB。我们更改方法是将2改成3。
步骤4:修改虚拟地址到物理地址的映射函数
修改uboot/board/samsung/smdkc110/smdkc110.c中的virt_to_phy_smdkc110,将其中的20000000改为30000000即可。
(1)从打印出来的错误信息中挑选一个关键词,然后去源代码中搜索这个关键词,通过这种搜索的方法定位问题。通过搜索将问题定位在drivers/mmc/mmc.c的818行。
(2)在下面这个函数中,读取版本号如果版本号>5的话打印下面信息,我们直接把5修改为8。
这个函数是在读取SD/iNand的ext_csd寄存器的值。通过浏览代码结合出错地方,可以判断出:从sd卡中读取ext_csd寄存器是成功的,并且从读取结果中拿到了SD卡的版本号信息。然后代码对版本号进行了判断,并且如果版本号大于5就会报错并且函数错误退出。这就是问题所正。
当前板子上有一个iNand接在SD0上,有一个外置SD卡接在SD2上,那uboot中初始化的是iNand而不是SD卡。
c35e
也就是说uboot中实际用的是SD0而不是SD2。因为find_mmc_device(0),这里的0指的是SD0,可以改为1。
使用外置SD卡时,这个版本号的问题不会出现。从这里可以推测出SD卡和iNand的区别,SD卡版本低,iNand的版本比较高。
(2)网卡驱动在uboot/drivers/net/dm9000x.c和dm9000x.h
此驱动源于linux kernel源代码,可以在uboot中直接使用,无需更改。
(3)驱动本身具有可移植性
linux驱动设计中,数据和代码是分开的。
这里的代码主要指uboot/drivers/net/dm9000x.c和dm9000x.h。
而数据是由硬件开发板中的接法决定的,数据由一定的数据结构来提供。
移植DM9000驱动时,dm9000x.c和h不需要改动,要动的是头文件的数据。
(2)只要将网卡芯片正确的初始化了,则网卡芯片就能工作(意思是网卡驱动dm9000x.c和dm9000x.h依赖于这里的初始化)。
(3)dm9000初始化的代码在start_armboot最开始初始化的一堆函数数组中的board_init函数中,其中调用的是dm9000_pre_init这个函数。
步骤1:三个寄存器的修改
(1)从三星版本的代码中可以看出,它操作的是bit20-bit23,对照数据手册中寄存器定义,可以看出三星的开发板DM9000是接在Bank5上的。
而我们接在bank1上的,因此我们需要操作的bit位是bit4-bit7。
(2)三个寄存器的修改,主要是因为三星的开发板DM9000接在bank5,而我们接在了bank1上,因此要做一些修改。
步骤2:基地址的配置(在smdkv210single.h中)
(1)CONFIG_DM9000_BASE是DM9000网卡通过SROM bank映射到SoC中地址空间中的地址。
这个地址的值取决于硬件接到哪个bank,这个bank的基地址是SoC自己定义好的。
譬如我们这里接到了bank1上,bank1的基地址是0x88000000(但实际写的是0x88000300)。
(2)
DM9000_IO表示访问芯片IO的基地址,直接就是CONFIG_DM9000_BASE;
DM9000_DATA表示我们访问数据时的基地址,因为DM9000芯片的CMD引脚接到了ADDR2,因此这里要+4(0b100,对应ADDR2)
(3)0x300跟DM9000网卡芯片型号版本有关,是DM9000网卡本身的问题,其内部寄存器就有一个0x300的一个偏移量。
参考资料:http://www.cnblogs.com/biaohc/p/6460902.html
总结的思维导图下载地址:https://pan.baidu.com/s/1nvilb6L
由于我们使用210的cpu,因此选择三星的210开发板的配置。
1、删除无关的文件
在开始移植之前我们首先要把不相关的cpu、board、lib目录删除:(1)board目录下:把不相关的开发板的文件全部删除只保留:board->samsung->common文件夹以及board->samsung->smdkc110文件夹;
每个文件夹代表一个开发板。
(2)cpu目录下:只保留s5pc11x文件夹,其他全部删除;
(3)include目录下:asm-开头的文件只保留asm-arm;asm-arm目录下arch-开头的文件只保留s5pc11x;
(4)include/configs目录下:只保留smdkv210single.h文件;每一个开发板对应一个.h文件。
(5) lib_ 开头的文件夹保留lib_arm、lib_generic 。
然后在用sourceinsight生成project。
2、直接编译三星移植版uboot尝试运行
(1)在uboot根目录下进行配置make smdkv210single_config(对应include/configs/smdkv210single.h头文件),然后make,生成uboot.bin文件。(2)把生成的uboot.bin文件烧录到sd卡中。
首先注意的是烧写时要在uboot根目录下,烧写命令:./sd_fusing.sh /dev/sdb;
注意sd_fusing脚本中,烧写的内容是不是uboot.bin、uboot.bin的路径对不对,..在此表示 ~/uboot/;
利用file mkbl1查看mkbl1是不是32bit的,如果不是,则需要在sd_fusing目录下执行make clean,然后再make。
sd_fusing.sh文件中,/mkbl1 ../u-boot.bin SD-bl1-8k.bin 8192表示将uboot的前8k复制到SD-bl1-8k.bin文件中;
执行此sd_fusing.sh脚本即可把bl1、uboot.bin烧录到sd卡中。
(3)启动开发板,发现电源置锁,只有一句SD checksum Error,没有打印出ok。
分析:uboot中串口最早的输出“OK”,在lowlevel_init.S中初始化串口时打印出来的;串口无输出"O"说明在打印"O"之前代码已经死掉了;开发板供电锁存在lowlevel_init.S中,开发板供电锁存成功说明这个代码之前的部分是没问题的。
结论:错误发生在开发板供电锁存代码和串口初始化打印"O"代码。
在lowlevel_ini t函数中,PMIC_InitIp函数是用来管理电源的。由于210开发板没有用到这个功能,所以程序卡在此函数中。只要把此函数注释掉即可。
3、uboot的版本号和时钟配置
输出如下:(1)开始打印U-BOOT的版本号,由display_banner 这个函数中实现。
想要修改“for SMDKV210”这个信息,只需在smdkv210single.h中修改这个宏定义CFG_PROMPT即可。如下
(2)时钟信息是对的。
时钟信息是在print_cpuinfo这个函数中打印出来的。
时钟部分的代码在lowlevel_init.S中的bl system_clock_init调用的函数中。
函数的代码部分是没任何问题的,不需要改动。
如果时钟部分要更改,关键是去更改头文件中的宏定义。
三星移植时已经把210常用的各种时钟配置全都计算好用宏开关来控制了。只要打开相应的宏开关就能将系统配置为各种不同的频率。
(3)下面的信息是在checkboard函数中打印的
如果要修改这个信息,可以在这个函数中修改。
在board\samsung\smdkc110.c文件中
4、DDR的配置
下面所显示的信息是错误的首先,看一下原来的DRAM中的配置信息(在smdkv210single.h中进行配置):
可知,这里有两块DRAM,大小均为512M(故总显示为1GB),但实际我们x210开发板只有512MB。
因此修改如下:#define SDRAM_BANK_SIZE 0x10000000 /* 256 MB */
其次,DRAM0和DRAM1的地址,分别为0x20000000~0x2FFFFFFF(256MB),0x40000000~0x4FFFFFFF(256MB)。
我们希望起始内存的地址为0x3000_0000~0x4FFF_FFFF,因此需要DDR地址另外配置。
步骤1:更改寄存器的值(可看做硬件配置部分的修改)
(1)根据裸机中DDR初始化部分的课程,和uboot中DDR初始化部分的代码的课程,得出结论
DDR的初始化代码部分是在lowlevel_init.S中写的,是不动的,代码部分就是对相应寄存器做相应值的初始化;
要动的是值,而uboot为了具有可移植性把值都宏定义在include/configs/xxx.h中了。
因此我们只需要去这个配置头文件中更改配置值即可。
(2)#define DMC0_MEMCONFIG_00x20E01323 改为:#define DMC0_MEMCONFIG_00x30E01323
实际发现还是运行不了,需要改为 #define DMC0_MEMCONFIG_00x30F01323
步骤2:软件配置值更改
寄存器的值改了后相当于是硬件配置部分做了更改。但是uboot中DDR相关的一些,还在原来位置,所以要去更改。
在include\configs\smdkv210single.h中,将#defineMEMORY_BASE_ADDRESS0x20000000 改为 #define MEMORY_BASE_ADDRESS0x30000000。
步骤3:[b]虚拟地址映射表中相应修改[/b]
(1)uboot中开启了MMU对内存进行了段式映射,有一张内存映射表。
(2)修改发生在lowlevel_init.S中的mmu_table标签这块内容里。
(2)经过实际分析,发现这个内存映射只是把20000000开始的256MB映射到C0000000开头的256MB。我们更改方法是将2改成3。
步骤4:修改虚拟地址到物理地址的映射函数
修改uboot/board/samsung/smdkc110/smdkc110.c中的virt_to_phy_smdkc110,将其中的20000000改为30000000即可。
5、SD卡版本号问题
(1)从打印出来的错误信息中挑选一个关键词,然后去源代码中搜索这个关键词,通过这种搜索的方法定位问题。通过搜索将问题定位在drivers/mmc/mmc.c的818行。
(2)在下面这个函数中,读取版本号如果版本号>5的话打印下面信息,我们直接把5修改为8。
这个函数是在读取SD/iNand的ext_csd寄存器的值。通过浏览代码结合出错地方,可以判断出:从sd卡中读取ext_csd寄存器是成功的,并且从读取结果中拿到了SD卡的版本号信息。然后代码对版本号进行了判断,并且如果版本号大于5就会报错并且函数错误退出。这就是问题所正。
当前板子上有一个iNand接在SD0上,有一个外置SD卡接在SD2上,那uboot中初始化的是iNand而不是SD卡。
c35e
也就是说uboot中实际用的是SD0而不是SD2。因为find_mmc_device(0),这里的0指的是SD0,可以改为1。
使用外置SD卡时,这个版本号的问题不会出现。从这里可以推测出SD卡和iNand的区别,SD卡版本低,iNand的版本比较高。
6、网卡驱动的移植
A、背景知识
(1)uboot中提供了很多网卡芯片的驱动程序,所以uboot中是移植而不是编写。(2)网卡驱动在uboot/drivers/net/dm9000x.c和dm9000x.h
此驱动源于linux kernel源代码,可以在uboot中直接使用,无需更改。
(3)驱动本身具有可移植性
linux驱动设计中,数据和代码是分开的。
这里的代码主要指uboot/drivers/net/dm9000x.c和dm9000x.h。
而数据是由硬件开发板中的接法决定的,数据由一定的数据结构来提供。
移植DM9000驱动时,dm9000x.c和h不需要改动,要动的是头文件的数据。
B、网卡移植的关键:初始化
(1)uboot在第二阶段init_sequences中进行了一系列的初始化,其中就有网卡芯片的初始化。(2)只要将网卡芯片正确的初始化了,则网卡芯片就能工作(意思是网卡驱动dm9000x.c和dm9000x.h依赖于这里的初始化)。
(3)dm9000初始化的代码在start_armboot最开始初始化的一堆函数数组中的board_init函数中,其中调用的是dm9000_pre_init这个函数。
C、移植步骤
见博客http://blog.csdn.net/oqqhutu12345678/article/details/72547924步骤1:三个寄存器的修改
(1)从三星版本的代码中可以看出,它操作的是bit20-bit23,对照数据手册中寄存器定义,可以看出三星的开发板DM9000是接在Bank5上的。
而我们接在bank1上的,因此我们需要操作的bit位是bit4-bit7。
(2)三个寄存器的修改,主要是因为三星的开发板DM9000接在bank5,而我们接在了bank1上,因此要做一些修改。
步骤2:基地址的配置(在smdkv210single.h中)
(1)CONFIG_DM9000_BASE是DM9000网卡通过SROM bank映射到SoC中地址空间中的地址。
这个地址的值取决于硬件接到哪个bank,这个bank的基地址是SoC自己定义好的。
譬如我们这里接到了bank1上,bank1的基地址是0x88000000(但实际写的是0x88000300)。
(2)
DM9000_IO表示访问芯片IO的基地址,直接就是CONFIG_DM9000_BASE;
DM9000_DATA表示我们访问数据时的基地址,因为DM9000芯片的CMD引脚接到了ADDR2,因此这里要+4(0b100,对应ADDR2)
(3)0x300跟DM9000网卡芯片型号版本有关,是DM9000网卡本身的问题,其内部寄存器就有一个0x300的一个偏移量。
相关文章推荐
- uboot移植——使用官方uboot进行移植
- 嵌入式linux开发uboot移植(七)——三星官方uboot的移植
- S5PV210-uboot移植-从三星官方uboot开始移植
- uboot移植(九)——移植三星官方uboot(三)
- 嵌入式linux开发uboot移植(七)——三星官方uboot的移植
- uboot移植(八)——移植三星官方uboot(二)
- S5PV210-uboot移植-从uboot官方的uboot进行移植
- u-boot移植随笔:使用svn进行版本控制
- u-boot移植随笔:继续使用svn进行版本控制(合并分支实例)
- uboot移植-从三星官方源码开始移植过程总结
- uboot移植(七)——移植三星官方uboot(一)
- 三星官方uboot移植实战1
- 移植U-BOOT之裁剪和修改默认参数(易用性)启动内核,以及对uboot进行分区
- 网上学习新课程--使用开发板动手进行uboot、内核以及驱动移植
- 从三星官方移植uboot
- uboot的移植2-从uboot官方标准uboot开始移植
- 2.12.uboot的移植2-从uboot官方标准uboot开始移植
- uboot 命令使用教程(uboot参数设置)
- 移植u-boot-2010.09到三星SC32442平台(二):nand读写和ax88180以太网支持
- 移植u-boot-2010.09到三星SC32442平台(三):yaffs2文件系统写入支持