上篇讲了如何移植 uboot 到 I.MX6ULL开发板上,现在开始学习如何移植 Linux 内核。
| 获取Linux 内核
Linux 由 Linux 基金会管理与发布,所以你想获取最新的Linux 版本就可以在这个网站上下载;
4.x 版本的 Linux 和 5.x 版本没有本质上的区别,5.x 更多的是加入了一些新的平台、新的外设驱动而已。
NXP 会从 https://www.kernel.org 下载某个版本的 Linux 内核,然后将其移植到自己的 CPU上,测试成功以后就会将其开放给 NXP 的 CPU 开发者。
开发者下载 NXP 提供的 Linux 内核,然后将其移植到自己的产品上。
NXP 提供的 Linux 源码可以在原子公开资料包中找到,路径如下:
开发板光盘->1、例程源码->4、NXP 官方原版 Uboot和 Linux-> linux-imx-rel_imx_4.1.15_2.1.0_ga.tar.bz2
| 编译Linux内核
编译内核之前需要先在 ubuntu 上安装 lzop 库,否则内核编译会失败!命令如下:
sudo apt-get install lzop // 下面两个库如果没安装也需要安装一下 sudo apt-get install build-essential sudo apt-get install libncurses5-dev // 查看是否安装 dpkg -s build-essential dpkg -s libncurses5-dev
新建一个文件夹(nxp_linux),然后将linux内核压缩包拷贝到文件夹中并解压,解压命令为:
tar -vxf linux-imx-rel_imx_4.1.15_2.1.0_ga.tar.bz2
解压后的文件如下:
编译Linux内核之前要先配置Linux内核。每个板子都有其对应的默认配置文件,这些配置文件保存在“arch/arm/configs”目录中。
imx_v7_defconfig和imx_v7_mfg_defconfig都可以作为NXP官方开发板IMX6ULL EVK的默认配置文件,但是一般都使用后者,因为后者编译出来的zImage可以通过NXP官方提供的MfgTool工具进行烧写;
在目录下新建一个脚本文件(build.sh),然后在这个 shell 脚本里面输入如下所示内容:
#!/bin/sh #编译之前先清理 make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- distclean #配置Linux内核 make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- imx_v7_mfg_defconfig #编译Linux内核 make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- all -j16
给予该脚本可执行权限,命令如下:
chmod 777 build.sh
运行脚本编译内核,命令如下:
. build.sh
编译完成后,会得到两个重要文件:
Linux内核镜像文件: 存放路径为 arch/arm/boot/zImage IMX6ULL EVK开发板对应的设备树文件: 存放路径为 arch/arm/boot/dts/imx6ull-14x14-evk.dtb
vmlinux 、Image ,zImage 、uImage 的区别:
vmlinux是ELF格式的文件,是编译出来的最原始的内核文件,编译出来 差不多有16MB,是未压缩的。在实际中我们不会使用vmlinux,而是使用zImage或uImage这样的 Linux 内核镜像文件。 Image是Linux内核镜像文件,但是Image仅包含可执行的二进制数据。Image就是使用objcopy取消掉vmlinux中的一些其他信息,比如符号表什么的。但是 Image 是没有压缩过的,Image保存在arch/arm/boot目录下,其大小大概在12MB 。 zImage是经过gzip压缩后的Image,经过压缩以后其大小大概在6MB左右。 uImage是老版本uboot专用的镜像文件,uImag是在zImage前面加了一个长度为 64字节的“头” ,这个头信息描述了该镜像文件的类型、加载位置、生成时间、大小等信息。但是新的uboot已经支持了 zImage 启动!所以已经很少用到uImage了
| 内核启动测试
将生成的zImage和imx6ull-14x14-evk.dtb这两个文件下载到IMX6U开发板上进行测试。
首先检查uboot中的环境变量bootargs,如果环境变量异常请看上一篇推文配置:
然后拷贝zImage和imx6ull-14x14-evk.dtb这两个文件到Ubuntu的tftp目录下:
最后启动开发板,进入uboot命令行模式,输入如下命令以上两个文件下载到开发板中并启动:
tftp 80800000 zImage tftp 83000000 imx6ull-14x14-evk.dtb bootz 80800000 - 83000000
启动成功,但是触摸不能使用
| 根文件系统缺失错误
Linux内核启动以后是需要根文件系统的,根文件系统存在哪里是由uboot的 bootargs环境变量指定,bootargs会传递给Linux内核作为命令行参数 。
上一篇推文设置root=/dev/mmcblk1p2,也就是说根文件系统存储在/dev/mmcblk1p2 中,也就是 EMMC 的分区2中。
在实际的工作中开发一个产品,这个产品的第一版硬件出来以后我们是没有对应的根文件系统可用的,必须要自己做根文件系统。
在构建出对应的根文件系统之前 Linux 内核是没有根文件系统可用的,此时 Linux 内核启动以后会出现下面提示:
Kernel panic - not syncing: VFS: Unable to mount root fs on unknown-block(0,0)也就是提示内核崩溃,因为 VFS(虚拟文件系统)不能挂载根文件系统,因为根文件系统目录不存在。
先压缩备份NXP编译出来的内核源码文件,避免操作有误重新编译内核,毕竟编译一次内核比较耗时间;
添加开发板默认配置文件
将arch/arm/configs目录下的imx_v7_mfg_defconfig重新复制一 份, 命名 为imx_myboard_emmc_defconfig,命令如下:
cd arch/arm/configs cp imx_v7_mfg_defconfig imx_myboard_emmc_defconfig
添加开发板对应的设备树文件
添加适合正点原子 EMMC 版开发板的设备树文件,进入目录 arch/arm/boot/dts 中,复制一份 imx6ull-14x14-evk.dts,然后将其重命名为 imx6ull-myboard-emmc.dts,命令如下:
cd arch/arm/boot/dts cp imx6ull-14x14-evk.dts imx6ull-myboard-emmc.dts
.dts 是设备树源码文件,编译 Linux 的时候会将其编译为.dtb 文件。imx6ull-myboard-emmc.dts创 建 好 以 后还 需 要 修 改 文 件Makefile;
路径:arch/arm/boot/dts/Makefile找到“ dtb-$(CONFIG_SOC_IMX6ULL)”配置项,在此配置项中加入“imx6ull-myboard-emmc.dtb” ,如下所示:
这样编译 Linux 的时候就可以从imx6ull-myboard-emmc.dts编译出 imx6ull-myboard-emmc.dtb 文件了。
添加新的脚本
新建一个脚本文件(build_myboard.sh),脚本内容如下:
#!/bin/sh #编译之前先清理 make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- distclean #配置Linux内核 make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- imx_myboard_emmc_defconfig #编译Linux内核 make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- all -j16
给予该脚本可执行权限,命令如下:
chmod 777 build_myboard.sh
运行脚本编译内核,命令如下:
. build_myboard.sh
编译完成后,会得到两个重要文件:
Linux内核镜像文件: 存放路径为 arch/arm/boot/zImage IMX6ULL EVK开发板对应的设备树文件: 存放路径为 arch/arm/boot/dts/imx6ull-myboard-emmc.dtb
然后下载到开发板,启动内核即可,显示登陆提示就说明内核启动成功。
审核编辑:刘清
全部0条评论
快来发表一下你的评论吧 !