尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

U-Boot 移植(1)

U-Boot 移植(1) 1. U-Boot 移植技术概述U-BootUniversal Boot Loader是嵌入式 Linux 系统中负责引导内核的启动加载程序。其核心任务包括初始化关键硬件如时钟、DDR、总线、加载操作系统内核与设备树映像至内存、并建立引导参数传递机制。1.1 为什么要进行移植U-Boot 虽然提供了通用的初始化框架但不同开发板的硬件参数存在差异。当开发板的 DDR 时序、存储器类型EMMC/NAND、外设驱动接口如网络 PHY、LCD 屏幕参数与 U-Boot 官方提供的参考板Reference Board不一致时必须进行移植。移植的本质是通过修改板级配置文件Defconfig、头文件Header files和驱动源码使 U-Boot 正确初始化目标硬件环境。1.2移植的主要内容构建系统适配在configs/和board/目录下添加自定义板级配置通过修改Makefile和Kconfig建立独立的编译入口。硬件驱动适配外设驱动根据硬件原理图修改网络 PHY 寄存器地址及复位 GPIO 时序调整 LCD 时序参数以适配物理面板。设备树配置在.dts文件中更新引脚复用IOMUX和外设节点属性。参数传递机制配置通过环境变量bootcmd,bootargs设定内核加载路径与启动参数确保 U-Boot 在倒计时结束后能够将 Linux 内核与设备树搬运至 DDR 对应地址并将设备树物理首地址写入 CPU 的r2寄存器完成控制权移交。2. 移植流程2.1 了解 U-Boot 的三种来源源码种类维护主体技术侧重定位社区通用版 (Mainline)U-Boot 社区追求架构的标准化、通用性与前沿特性支持。嵌入式开发的基准线用于技术预研与架构追踪。原厂内核版 (Vendor SDK)SoC 厂商 (NXP, ST, TI等)针对特定 SoC 系列优化包含完善的内存初始化(DDR)驱动、时钟拓扑及外设控制器驱动。硬件产品的开发基准确保 CPU 核心特性的稳定性。板级工程版 (Board Support)开发板/硬件方案商基于原厂代码进行具体的引脚复用(IOMUX)、存储介质适配及外设时序微调。交付终端用户的实际可用代码直接匹配物理电路板。社区通用版Mainline技术演进的观测窗核心价值它是 U-Boot 最新的设计理念来源。开发者研究 Mainline 可以获知最新的驱动模型DM、设备树绑定规范DT Binding以及安全引导Secure Boot技术演进。局限性由于适配范围太广它往往不包含特定硬件平台的最新补丁或特定 SoC 的专有 IP 驱动直接移植难度大。原厂内核版Vendor SDK硬件适配的稳定锚点核心价值半导体厂商在开发 SoC 的同时会维护一份与其配套的 U-Boot 源码。它不仅包含核心的芯片驱动还通常附带了原厂参考板EVK/EVB的完整配置。移植策略在移植工作中原厂版本是最稳妥的基准线。绝大多数的内存控制逻辑、SoC 总线驱动均从此版本继承。开发板工程版Board Support最终产品的适配层核心价值它是对原厂版本进行“裁剪”和“修正”的产物。在工程实践中开发板厂商的主要工作是物理映射引脚映射确保板卡上的 GPIO 连线与寄存器映射一致。电气参数校准调整特定 LCD 屏的时序参数、调整 PHY 芯片的复位时序。裁剪冗余移除工程板不需要的调试功能减小固件体积缩短冷启动时间。2.2 U-Boot 源码的选择在实际工程开发中这三种 U-Boot 源码的选择依据主要取决于硬件平台与参考设计Reference Design的匹配度社区通用版 (Mainline)在商业项目与定制硬件开发中基本不作为首选。由于其缺乏特定 SoC 厂商的专有补丁与底层高频调校对具体芯片的外设支持较弱。原厂内核版 (Vendor SDK) 与 板级工程版 (Board Support)这是工业界最常用的两种源码来源。使用半导体厂商评估板如 NXP 官方 EVK 板直接使用半导体厂商维护的 U-Boot 源码。使用第三方标准开发板如韦东山的 I.MX6ULL 开发板首选使用开发板厂商提供的 U-Boot 源码。该源码已由厂商基于原厂 U-Boot 针对其特定电路板完成了引脚复用和外设驱动的闭环适配。自主设计板卡企业产品研发通常以半导体厂商提供的 U-Boot 为基础基准线。若硬件电路参考了第三方开发板的设计如延续了韦东山开发板的电源与网络拓扑则会结合两者的源码进行裁剪。在第三方开发板上直接换用原厂 U-Boot由于部分外设如网络 PHY 芯片型号、LCD 屏时序、电源管理 PMIC存在硬件电路差异部分驱动将无法直接运行必须进行代码级修改以完成适配——这一过程即标准的U-Boot 移植。3. 韦东山 IMX6ULL 开发板的 U-Boot 移植本文采用 NXP 半导体场上的 U-Boot 进行移植原因如下维度使用厂商正点原子/韦东山U-Boot使用 NXP 原厂 U-Boot 移植你的选择带来的核心学习好处驱动开发深度核心驱动如 LAN8720A 网络、时钟已由厂商重写完毕开发者只需修改 GPIO 引脚编号。必须亲手剔除原厂公版的复杂外设逻辑如 74LV595 扩展芯片并根据芯片手册手写物理电平的复位与延时时序。真正掌握物理层驱动编写与硬件总线时序控制。构建系统认知直接在已有单板目录下修补代码较少触及底层的配置与编译规则。必须完整执行大厂标准的“立门户”流程新建单板目录、配置 Kconfig 菜单、编写 Makefile、定制 defconfig。彻底吃透嵌入式 Linux 系统的条件编译与自动打包机理。调试Debug锻炼硬件适配度高编译烧写后基本直接点亮缺乏排错机会。原厂代码与目标板硬件存在天然冲突必然高频遭遇网口不通、开机卡死、屏幕花屏等故障。逼迫自己学会对比原理图、分析时钟信号流向、读写底层寄存器建立解决死机 Bug 的高级排错能力。3.1 NXP 官方 U-Boot 编译3.1.1 版本确定由于开发板的资料是 Uboot-2017.03所以我们去 GitHub 下载对应的版本NXP官方 uboot 源码下载3.1.2 编译链确定从韦东山开发板的参考手册可以得知编译链为arm-buildroot-linux-gnueabihf-3.1.3 默认配置文件选择进入 configs/ 目录搜索 mx6ull*列出相关的默认配置文件第一步核对芯片型号与封装14x14 还是 9x914x14 与 9x9 的含义这代表 i.MX6ULL 芯片的物理封装尺寸单位是毫米即 14mm×14mm 或 9mm×9mm。不同封装的芯片其引脚Pin数量和球位引脚分布完全不同。如何选择打开韦东山开发板的核心板原理图查看 CPU 型号或者直接拿放大镜看你板子中间那颗 NXP 芯片上的丝印。韦东山的 i.MX6ULL 开发板采用的是最常用的 MAPBGA 289 针脚封装其物理尺寸正是 14x14 毫米。结论直接过滤掉所有带 9x9 的文件锁定 mx6ull_14x14_…。第二步核对板型evk 还是 arm2evk 的含义Evaluation Kit官方评估板。NXP 官方公版开发板的名字就叫 i.MX6ULL EVK。arm2 的含义NXP 内部用于特定验证或早期硅片测试的板卡通常外设极少不适合用来做应用开发。结论锁定 evk。第三步判定启动与存储介质驱动适配的关键这是最关键的一步U-Boot 需要知道它自己将被烧写到哪里以及从哪里加载 Linux 内核。mx6ull_14x14_evk_nand_defconfig适用于板载存储器为 NAND Flash 颗粒的开发板。mx6ull_14x14_evk_emmc_defconfig适用于板载存储器为 eMMC 芯片的开发板。目前市面上百问网韦东山主推的 i.MX6ULL 开发板绝大多数都是 eMMC 版本板载一颗 8GB 或 4GB 的 eMMC 芯片。因此选择mx6ull_14x14_evk_emmc_defconfig3.1.4 编译过程#1.彻底清理工程清除之前由于用错编译器留下的错误缓存这步非常关键 make ARCHarm CROSS_COMPILEarm-buildroot-linux-gnueabihf-distclean #2.配置基线载入 NXP 官方 I.MX6ULL EMMC 评估板的默认配置文件 make ARCHarm CROSS_COMPILEarm-buildroot-linux-gnueabihf-mx6ull_14x14_evk_emmc_defconfig #3.全速编译调用虚拟机12个线程全速编译 U-Boot 源码 make ARCHarm CROSS_COMPILEarm-buildroot-linux-gnueabihf--j12核心镜像文件用于烧写启动这是编译出来的终极目标也是唯一需要传到板子上运行的文件u-boot-dtb.imx (核心中的核心)作用直接用于烧写到 SD 卡或 eMMC 的最终镜像。本质它是把 u-boot.bin编译出的可执行文件和 u-boot.dtb编译出的设备树文件合并后在头部加上了 i.MX6ULL 芯片专属的启动头信息IVT、DCD 等用于初始化内存参数。3.1.5 烧录 imx 文件至 SD卡维度通用 dd 命令imxdownload 工具安全性高风险。不带设备检查一旦把盘符 sdb 错打成系统盘 sda会直接擦除 Ubuntu 系统致其瘫痪。高安全防呆。内部自带防误杀机制会自动校验目标盘符属性拒绝向系统盘写入数据。烧写参数繁琐易错。每次必须手动输入 bs1k seek1 来指定跳过前 1KB 字节漏掉或写错参数板子就无法启动。一键傻瓜化。将“跳过 1KB 绝对扇区”的硬件规则直接写死在源码中开发者无需记忆复杂的偏移参数。文件兼容性单一。只能原封不动地平铺数据无法处理没有芯片启动头DCD/IVT的纯裸机 .bin 文件。智能双模。如果是纯 led.bin会自动帮其补齐 3KB 的芯片启动头再烧写如果是已带头的 u-boot.imx则直接烧写。先手写并编译一个 imxdownload1.新建 C 文件cd~/Desktop/uboot_plant/uboot-imx-nxp-imx_v2017.03_4.9.11_1.0.0_ga gedit imxdownload.c2.粘贴通用源码把下面这段标准的 imxdownload 开源核心 C 语言代码完整复制粘贴到刚才弹出的 gedit 窗口中保存并关闭#includestdio.h#includestdlib.h#includestring.h#includeunistd.h#includefcntl.h#includesys/stat.h#includesys/types.hintmain(intargc,char*argv[]){FILE*fp_src;intfd_dst;unsignedcharbuf[512];intnread;if(argc!3){printf(\n);printf(I.MX6U Embedded Processor Download Tool (Lite)\n);printf(Usage: ./imxdownload source_bin sd_device\n);printf(Example: ./imxdownload u-boot-dtb.imx /dev/sdb\n);printf(\n);return-1;}// 打开源镜像文件fp_srcfopen(argv[1],rb);if(fp_srcNULL){printf(Error: Cannot open source file %s\n,argv[1]);return-1;}// 打开 SD 卡物理设备fd_dstopen(argv[2],O_WRONLY);if(fd_dst0){printf(Error: Cannot open device %s. Please check sudo permission.\n,argv[2]);fclose(fp_src);return-1;}// 核心逻辑绝对寻址定位到物理 SD 卡 1KB 偏移处第2个扇区if(lseek(fd_dst,1024,SEEK_SET)0){printf(Error: lseek failed\n);close(fd_dst);fclose(fp_src);return-1;}printf(Flashing Bootloader %s to %s ...\n,argv[1],argv[2]);// 开始物理扇区平铺写入while((nreadfread(buf,1,sizeof(buf),fp_src))0){write(fd_dst,buf,nread);}fsync(fd_dst);close(fd_dst);fclose(fp_src);printf(Done! Flash successfully.\n);return0;}3.现场编译成工具在终端使用 Ubuntu 本地编译器编译它并赋予执行权限gcc imxdownload.c-oimxdownloadchmodx imxdownload4.使用新生成的工具烧写现在可以直接使用 imxdownload 进行烧写了sudo./imxdownload u-boot-dtb.imx /dev/****** 是 实际 SD 卡盘符输入 lsblk 查看我的 TF卡 是16G的实际容量和sdb的14.6G相符所以 *** 换成 sdb 进行烧写3.1.6 启动开发板验证切换到 SD/TF卡 启动并连接串口启动开发板查看信息 LCD 屏幕问题汇总现状体检U-Boot 识别参数480 × 272 480 \times 272480×272分辨率TFT43AB 4.3寸低清屏。实际物理硬件通常为1024 × 600 1024 \times 6001024×6007寸屏。物理现象上电倒计时 3 秒内屏幕黑屏、白屏或无任何有效画面。底层根本原因LCD 驱动的本质是“对表”。U-Boot 驱动此时发出的像素时钟频率Pixel Clock以及行同步/场同步时序参数HBP, HFP, VBP, VFP完全是按照 4.3 寸低清屏设计的。屏幕控制 IC 收到这些错误的电信号后无法锁定帧频导致硬件直接拒绝显示。后续移植修改靶心核心文件board/freescale/mx6ullevk/mx6ullevk.c修改动作在源码中找到 displays 数组下的 struct display_info_t 结构体将原本 TFT43AB 的参数依照你物理屏幕的数据手册Datasheet精确修改为适配你当前屏幕的分辨率与时序参数。 网络Ethernet问题汇总现状U-Boot 报错提示Net: No ethernet found.未找到以太网设备。物理现象无法使用 ping 命令无法通过 tftp 或 nfs 远程下载内核网络功能完全瘫痪。底层根本原因这是典型的外围控制电路不匹配导致网络物理层PHY无法工作。NXP 官方原厂设计使用 KSZ8081 PHY 芯片且网口的复位引脚由一颗外扩的 74LV595 串转并芯片来间接控制。百问网实际硬件设计使用 LAN8720A PHY 芯片且网口的复位引脚直接连接在 i.MX6ULL CPU 的物理 GPIO 上无 74LV595 芯片。冲突点U-Boot 启动时试图通过 I2C/SPI 去驱动那个压根不存在的 74LV595 芯片来释放网口复位导致 LAN8720A 芯片始终处于死机复位状态MDIO 总线根本找不到网络物理层设备。后续移植修改靶心核心文件board/freescale/mx6ullevk/mx6ullevk.c引脚复用与物理复位逻辑include/configs/mx6ullevk.h网络宏定义与 PHY 地址配置修改动作在 mx6ullevk.c 中彻底剔除 74LV595 的驱动代码。写入纯粹的 GPIO 操作代码在上电时给 LAN8720A 的复位引脚拉低再拉高完成硬件复位。在 mx6ullevk.h 中将 PHY 芯片的地址CONFIG_FEC_MXC_PHYADDR修改为你的单板实际物理地址通常是 0x0 或 0x1。
返回列表