9. uboot 中对 Flash 和 DDR 的管理

本文探讨嵌入式系统中U-Boot与DDR的分区管理,解析分区的重要性及方法,确保系统部署与运行效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

本文内容来自对 《朱有鹏嵌入式linux核心课程》学习总结

1. uboot 阶段 Flash 的分区

  • 所谓分区,就是说对 Flash 进行分块管理。
  • PC 机等产品中,因为大家都是在操作系统下使用硬盘的,整个硬盘由操作系统统一管理,操作系统会使用文件系统帮我们管理硬盘空间。(管理保证了文件之间不会互相堆叠),于是乎使用者不用自己太过在意分区问题。
  • 在 uboot 中是没有操作系统 的,因此我们对 Falsh (相当于硬盘)的管理必须事先使用分区界定(实际上 uboot 中和 kernel 中都有个分区表,分区表就是我们在做系统移植时对 Flash 的整体管理分配方法)。有了这个界定后,我们在部署系统时按照分区界定方法来部署,uboot 和 kernel 的软件中也是按照这个分区界定来工作,就不会错。
  • 分区方法不是一定的,不是固定的,是可以变动的。但是在一个移植中必须事先设计好定死,一般在设计系统移植时就会定好,定的标准是:
    uboot:uboot 必须从 Flash 起始地址开始存放(也许是扇区0,也许是扇区1,也许是其他,取决于 SoC 的启动设计),uboot 分区的大小必须保证 uboot 肯定能放环境变量:环境变量分区一般紧贴着 uboot 来存放,大小为 32kb 或者更多一点。
    kernel:kernel 可以紧贴环境变量存放,大小一般为 3MB 或 5MB 或其他。
    rootfs:…
    剩下的就是自由分区,一般kernel 启动后将自由分区挂载到 rootfs 下使用

总结:
一般规律如下:

  1. 各分区彼此相连,前面一个分区的结尾就是后一个分区的开头。
  2. 整个 flash 充分利用,从开头到结尾。
  3. uboot 必须在 Flash 开头,其他分区相对位置是可变的。
  4. 各分区的大小由系统移植工程师自己来决定,一般定为合适大小(不能太小,太小了容易溢出;不能太大,太大了浪费空间)
  5. 分区在系统移植前确定好,在 uboot 中和 kernel 中使用同一个分区表。将来在系统部署时和系统代码中的分区方法也必须一样。

2. uboot 阶段 DDR 的分区

  • DDR 的分区和 Flash 的分区不同,主要是因为 Flash 是掉电存在的,而 DDR 是掉电消失,因此可以说 DDR 是每次系统运行时才开始部署使用的。
  • 内存的分区主要是在 linux 内核启动起来之前,linux 内核启动后内核的内存管理模块会接管整个内存空间,那时候就不用我们来管理了。
  • 注意内存分区关键就在于内存中哪一块用来干什么必须分配好,以避免各个不同功能使用了同一块内存造成的互相踩踏。譬如说我们 tftp 0x23E00000 zImage 去下载 zImage 到内存的 0x23E00000 处就会出错,因为这个内存处实际是 uboot 的镜像所在。这样下载会导致下载的 zImage 把内存中的 uboot 给冲掉。
在u-boot(统一固件加载器)中,将代码从NorFlash转移到DDR内存通常涉及到配置BootCmd命令,这是u-boot初始化过程中的一部分。这个过程通常用于加快启动速度,因为RAM的速度远快于闪存。 设置步骤可能会因具体的板级支持包(Board Support Package, BSP)而异,但一般包括以下几个步骤: 1. **添加环境变量**:首先,在`conf/local.env`文件中,设置一个环境变量指向NorFlash分区中需要加载到DRAM的映像地址大小,如`IMAGE_DDR_LOCATION=0x80000000` `IMAGE_DDR_SIZE=$(filesize ${IMAGE})`。 2. **创建bootcmd**:在`cmd_fixmap.c`或自定义的`cmd_xxx.c`文件中(`xxx`替换为你特定的加载操作名),编写一个新的bootcmd函数,比如`cmd_load_ddr()`, 其中会涉及读取NorFlash中的内容并复制到DDR开始位置。 ```c int cmd_load_ddr(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { struct image_header header; ulong addr = env_get_ulong("IMAGE_DDR_LOCATION", 0); ulong size = env_get_ulong("IMAGE_DDR_SIZE", 0); if (!image_read_from_file(&header, &argv[0], 0) || image_write_to_memory(addr, &header, size) < 0) { setenv("load_error", "Failed to load DDR image!", 1); return -1; } setenv("loaded_image", "DDR", 1); // 标记已经完成加载 return 0; } ``` 3. **配置启动顺序**:在`cmd_bootm.c`或其他适当的boot命令处理函数中,将新创建的`cmd_load_ddr`加入到boot命令列表中,确保它在执行完传统从NorFlash引导之前运行。 4. **保存配置**:最后,记得更新`config.mk`文件,确保新添加的`cmd_fixmap.c`包含在最终的u-boot内核构建中。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

lzg2021

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值