前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >S3C2440移植uboot之裁剪和修改默认参数

S3C2440移植uboot之裁剪和修改默认参数

作者头像
嵌入式与Linux那些事
发布2021-05-20 10:35:18
8280
发布2021-05-20 10:35:18
举报
文章被收录于专栏:嵌入式与Linux那些事

uboot的环境参数

  首先,uboot会去校验(CRC)存放环境变量的一段空间 ,若CRC有效则使用该空间里的环境变量,无效则用默认的环境变量.   而我们移植的uboot,由于一直没有使用save,所以没有读不出CRC校验,使用的默认环境变量,如下图所示:

修改uboot的默认环境变量

搜索using default environment,发现这句话是在set_default_env()函数

   default_environment这个变量,这是个全局字符数组,从字面上就可知道,这个是默认环境变量数组,里面保存了各个环境值

查看 default_environment[]

  bootargs="(环境变量里最重要的一个),是传递给内核的环境变量,里面会保存文件系统位置,控制台console等等。   其他宏的含义如下

代码语言:javascript
复制
"bootcmd=", 用来启动内核的命令
"bootdelay=",uboot启动的倒计时,默认值为5S,只有设置了bootcmd,该倒计时才有用
"baudrate=",波特率,默认为115200
"ethaddr=",网卡的MAC地址(也叫物理地址)
"ipaddr=",ip地址
"serverip=",使用tftp时的服务器地址
"netmask=",掩码, 默认值为255.255.255.0
"mtdparts=",mtd分区表

  更改smdk2440.h里面与环境相关的宏   设置默认环境变量宏(位于include/configs/smdk2440.h):

代码语言:javascript
复制
#define CONFIG_BOOTARGS "noinitrd root=/dev/mtdblock3 init=/linuxrc console=ttySAC0"   //bootargs
#define CONFIG_BOOTCOMMAND "nand read  0x30000000 0x60000 0x200000; bootm 0x30000000" //bootcmd
#define CONFIG_BOOTDELAY       5                      //uboot 倒计时      
#define CONFIG_NETMASK         255.255.255.0           //掩码
#define CONFIG_IPADDR          192.168.2.110           //本机IP
#define CONFIG_SERVERIP        192.168.2.1           //电脑IP
#define CONFIG_ETHADDR         08:00:3c:26:0b:5b       //MAC地址

  其中bootcmd是随意写的,因为此时的内核位置还不确定放在哪(后面配置mtdparts命令后,会在后面修改)   由于nand中要划分bootload空间、环境变量空间、内核空间、系统空间 而uboot就有400多k,所以我们需要裁剪uboot,裁剪后再来划分内存分区

裁剪uboot

  进入smdk2440.h,把不需要的功能的宏去掉,比如usb,文件系统,rtc等   1)去掉usb支持

代码语言:javascript
复制
/************************************************************
// * USB support (currently only works with D-cache off)
// ************************************************************/

//#define CONFIG_USB_OHCI
//#define CONFIG_USB_KEYBOARD
//#define CONFIG_USB_STORAGE
//#define CONFIG_DOS_PARTITION

  2)去掉rtc支持

代码语言:javascript
复制
/************************************************************
// * RTC
// ************************************************************/

//#define CONFIG_RTC_S3C24X0

  3)去掉BOOTP选项

代码语言:javascript
复制
/*
// * BOOTP options
// */

//#define CONFIG_BOOTP_BOOTFILESIZE
//#define CONFIG_BOOTP_BOOTPATH
//#define CONFIG_BOOTP_GATEWAY
//#define CONFIG_BOOTP_HOSTNAME

  4)去掉部分不需要的命令行配置

代码语言:javascript
复制
// #define CONFIG_CMD_DHCP     //动态主机配置协议命令行
// #define CONFIG_CMD_USB      //USB命令行

  5)去掉文件系统

代码语言:javascript
复制
/*
// * File system
// */

//#define CONFIG_CMD_FAT
//#define CONFIG_CMD_EXT2
//#define CONFIG_CMD_UBI
//#define CONFIG_CMD_UBIFS
//#define CONFIG_CMD_MTDPARTS
//#define CONFIG_MTD_DEVICE
//#define CONFIG_MTD_PARTITIONS
//#define CONFIG_YAFFS2
//#define CONFIG_RBTR

解决rtc_xxx,cmd_date.c 错误

由于屏蔽的宏在其它文件也会用到,而make在之前用过,再次make只会编译修改过的文件.   所以输入:

代码语言:javascript
复制
make clean                  
make smdk2440_config
make     

  make后,打印以下错误:

  上面的cmd_date.c文件以及出错变量rtc_xxx,从字面上来看显然是与RTC有关,我们直接屏蔽该文件   通过Makefile,找到需要屏蔽宏CONFIG_CMD_DATE(宏定义位于include/configs/smdk2440.h):

屏蔽后,make成功,可以看到uboot只有200kb了:

设置分区

  每次启动内核时,都会打印以下分区信息:

代码语言:javascript
复制
Creating 4 MTD partitions on "NAND 256MiB 3,3V 8-bit":
0x00000000-0x00040000 : "bootloader"            //存放uboot
0x00040000-0x00060000 : "params"                //存放环境变量
0x00060000-0x00260000 : "kernel"                //存放内核
0x00260000-0x10000000 : "root"                  //存放文件系统

  所以,我们新的uboot,还是照着这个来分区   所以我们通过sava -help命令,看它位于哪个文件,找到save命令相关宏 如下图所示:

  然后在si里搜索saveenv   搜索如下图所示:

  可以发现,在env_flash.c 和env_nand.c这两个文件都有saveenv()函数.   显然env_flash.c的作用是,通过save命令将环境变量保存在nor flash.而env_nand.c,是将环境变量保存在nand flash里.   接下来在common/Makefile搜索,看看这两个文件依赖哪两个宏   如下图所示:

  然后在smdk2440.h搜索这两个宏,看看板卡默认配置的是不是env_nand.c   如下图所示:

  可以看到,smdk2440.h是将环境变量保存在nor flash,由于2440在nand启动下是无法支持nor,所以我们需要屏蔽这三处宏,重新设置宏

设置save相关宏

  在其它板卡里搜索CONFIG_ENV_IS_IN_NAND,看看别人是怎么通过宏配置save的,然后在env_nand.c文件里搜索宏,来看宏是怎么用的   最终宏修改为如下所示(位于include/configs/smdk2440.h):

代码语言:javascript
复制
//#define CONFIG_ENV_ADDR                    (CONFIG_SYS_FLASH_BASE + 0x070000)
//#define CONFIG_ENV_IS_IN_FLASH
//#define CONFIG_ENV_SIZE               0x10000

#define CONFIG_ENV_SIZE                 0x20000       //环境变量空间大小
#define CONFIG_ENV_IS_IN_NAND
#define CONFIG_ENV_OFFSET               0x40000          //位于0x40000~(0X40000+0x20000)
#define CONFIG_ENV_RANGE                CONFIG_ENV_SIZE  //环境变量的擦除范围,要>=SIZE

  上面的CONFIG_ENV_RANGE宏,其实不定义,内核也会自动定义(位于env_nand.c):

  然后重新编译新的uboot,就可以使用save命令保存环境变量了.   接着我们烧写内核:

代码语言:javascript
复制
tftp 30000000 uImage
nand erase 60000 200000                         
nand write 30000000 60000 200000        //保存在内核分区里
bootm 30000000                         //启动内核

  从这里,看出烧个内核还需要记录这些分区空间地址,非常麻烦 设置mtdparts命令(在旧版uboot里,是mtd命令)

设置mtdparts命令

  其实,我们可以使用mtdparts命令,通过分区名字来代替这些地址,比如以前的uboot,直接输入:

代码语言:javascript
复制
nand erase kernel              //这个kernel名字就等于: 60000 200000 
nand write  30000000 kernel    //这个kernel名字就等于: 60000 200000 

  由于smdk2440板卡里没有配置mtdparts命令,所以步骤如下所示:   1)搜索mtdparts,发现位于common/cmd_mtdparts.c   2) 在common/Makefile搜索,找到cmd_mtdparts.c文件依赖 CONFIG_CMD_MTDPARTS宏

  3)在其它板卡里搜索CONFIG_CMD_MTDPARTS,看看别人是怎么通过宏配置nand的,别人写的配置如下所示:

(PS:当执行mtdparts default命令时,uboot就会检测是否有CONFIG_CMD_MTDPARTS宏,然后再根据上面的MTDPARTS_DEFAULT宏保存的mtd   4)设置mtdparts相关宏

  接下来,便复制上面的宏到smdk2440.h中,改为:

代码语言:javascript
复制
/*-----------------------------------------------------------------------
 * mtdparts
 */
#define CONFIG_CMD_MTDPARTS
#define CONFIG_MTD_DEVICE
#define MTDIDS_DEFAULT           "nand0=smdk2440-0"  
#define MTDPARTS_DEFAULT       "mtdparts=smdk2440-0:256k(u-boot),"      \ 
                                          "128k(params),"            \         
                                          "2m(kernel),"  \      
                                          "-(rootfs)"        \

  编译报错

  提示get_mtd_device_nm未定义,但是我们在Mtdcore.c中已经定义了,所以有可能是这个Mtdcore.c没有被编译进内核。   查看 drivers/mtd/Makefile中的定义部分,需要定义CONFIG_MTD_DEVICE 宏

  重新编译烧写测试 以前擦除:nand erase 60000 200000 现在擦除:nand erase kernel 发现报错了

  执行 help medparts

  我们先执行mtdparts defaults,再执行nand erase kernel,成功了。

  接着我们把这条命令添加到代码中去自动执行。   在board_init_r()函数里的for(;;)前面添加(位于arch/arm/lib/board.c):

代码语言:javascript
复制
  run_command("mtdparts default", 0);       //添加此处代码
 
       for (;;) {
              main_loop();
       }

  这样uboot每次启动时,都会执行一次mtdparts default命令,使它根据默认参数来自动分区.   mtdparts命令就此设置好了   然后重新修改,之前设置的环境参数bootcmd(位于smdk2440.h):   将

代码语言:javascript
复制
#define CONFIG_BOOTCOMMAND "nand read  0x30000000 0x60000 0x200000; bootm 0x30000000" //bootcmd

  改为:

代码语言:javascript
复制
#define CONFIG_BOOTCOMMAND "nand read  0x30000000 kernel; bootm 0x30000000"    //bootcmd

测试mtdparts分区

  输入mtdparts,查看默认分区名称:

  如上图所示,接下来我们便可以直接使用kernel名字来擦除kernel分区,并烧写内核了   步骤如下:

代码语言:javascript
复制
tftp 30000000 uImage
nand erase.part kernel      //等于nand erase 200000    60000
nand write 30000000 kernel  //从sdram拷贝到nand 
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2020/04/28 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • uboot的环境参数
  • 修改uboot的默认环境变量
  • 查看 default_environment[]
  • 裁剪uboot
  • 解决rtc_xxx,cmd_date.c 错误
  • 设置分区
  • 设置save相关宏
  • 设置mtdparts命令
  • 测试mtdparts分区
相关产品与服务
命令行工具
腾讯云命令行工具 TCCLI 是管理腾讯云资源的统一工具。使用腾讯云命令行工具,您可以快速调用腾讯云 API 来管理您的腾讯云资源。此外,您还可以基于腾讯云的命令行工具来做自动化和脚本处理,以更多样的方式进行组合和重用。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档