-
uImage从何而来?
- 明确:uImage属于嵌入式Linux系统三大软件之一。
-
Linux内核特点:
- Linux内核是全世界最著名的开源软件。
-
Linux内核由BootLoader启动,一旦启动,BootLoader生命结束,Linux内核永驻内存。
-
Linux内核本质就是一个大程序。
-
Linux内核支持多种处理器架构,X86、PowerPC、FPGA、DSP、ARM等等。
-
Linux内核支持多种多样的硬件设备驱动。
-
Linux内核七大子系统:
- 内存管理子系统。
- 进程管理子系统
- 文件系统
- 系统调用
- 设备驱动
- 网络协议
- 平台相关代码
-
目的:获取最终的二进制可执行文件uImage
-
先获取正确的、合适的交叉编译器。
- 切记:Linux内核源码的版本一定要和交叉编译器的版本要一致。
-
然后获取Linux内核源码。
- 切记:一定要从芯片厂家处获取Linux内核源码。
交叉编译X6818开发板的Linux内核源码:
- 获取源码:ftp://porting/kernel.tar.bz2
- 如果上位机的Linux系统是新装系统,还需要额外添加mkimage工具,用此工具来制作uImage。
- 解压缩配置编译:
cp kernel.tar.bz2 /opt/
cd /opt/
tar -xvf kernel.tar.bz2 //得到kernel目录
cd /opt/kernel
make distclean
ls arch/arm/configs/x6818_defconfig //获取配置参数
make x6818_defconfig 只做一次
time make uImage -j4
ls arch/arm/boot/uImage //编译出的内核镜像。
cp arch/arm/boot/uImage /tftpboot
下位机测试:
进入uboot命令执行:
setenv bootargs root=/dev/nfs nfsroot=.......maxcpus=1
saveenv
printenv
ping nfsserver_ip //测试nfs服务器是否能够ping通
tftp 0x48000000 uImage
bootm 0x48000000
-
进入内核源码根目录: cd /opt/kernel
-
生成一个菜单,来配置内核源码:make menuconfig
- 注意:如果是新按照的Ubuntu系统,需要先额外按照ncurses库:sudo apt-get install libncurses5-dev
-
罗列内核源码重要的配置如下:
-
system type ——>系统类型配置选项
- //说明两点:当前内核支持ARM结构,当前内核支持:ARM system type (SLsiAP s5p6818)——>
- 说明当前内核支持X6818开发板,Platform board
- 总结:这就是传说中的三个经典检查,只要有一个不符合内核势必不能运行。
-
boot options——>启动选项配置
- (console=ttySAC0,115200…)//圆括号内的内容是内核给自己传递的启动参数。
- kernel command line type (use bootloader kernel args)//内核到底采用谁传递的启动参数信息呢?
- use bootloader kernel arguments//如果uboot通过bootargs传递启动参数使用uboot传递的启动参数启动。
- extend bootloader kernel arguments。//同时采用内核自己的启动参数和uboot传递的启动参数相结合
- always use the default kernel command strir//只采用内核自己给自己传递的参数信息,即使uboot传递了也不用。
-
Device Drivers ——>//内核支持的硬件设备驱动选项
- memory technology device (MTD) support ——>//MTD就是nand flash和其他存储的总称。
- mapping drivers for chip access (nand flash驱动)
- memory technology device (MTD) support ——>//MTD就是nand flash和其他存储的总称。
-
-
System Type->
//三个检查 -
Boot optios->
//检查内核的启动参数到底用谁的- Device Driver->
//各类硬件外设的驱动- Norflash/Nandflash驱动
- 输入设备驱动
- 键盘
- 触摸屏
- 鼠标
- 游戏摇杆
- 摄像头驱动
- LCD显示屏驱动
- 声卡驱动
- I2C总线驱动
- SPI总线驱动
- 1-Wire总线驱动
- USB驱动
- TF卡/SD卡/EMMC驱动
- Device Driver->
-
File System->
//文件系统- EXT4
- VFAT
- NTFS
- CRAMFS
- UBIFS
- JFFFS2
- YAFFS2
- NFS
如何在内核的make menuconfig菜单中添加自己的配置选项?
- 搞定这个事情需要两个文件:Kconfig和Makefile。
Kconfig文件
-
明确以下常用关键字:
- config:用于生成一个选项,例如:config HELLO_WORLD,表示将来生成的选项名称叫:CONFIG_HELLO_WORLD,别忘记加“CONFIG”。
- bool:表示这个配置选项将来的操作方式有两种:按Y键选择为*,表示将对应的源代码和uImage编译在一起,按N表示不选择,表示不编译。按M键表示将对应的源文件和uImage分开单独编译。
- help:提供配置选项的帮助信息。
-
语法格式:
config 配置选项名称
(TAB键)tristate/bool “菜单的提示信息”
(TAB键)help:
额外的帮助信息
(TAB键)其余关键字。
例如:
config HELLO_WORLD
tristate "hello, world"
help:
this is a test msg
- CONFIG_HELLO_WORLD到底给谁使用呢?
- 在Makefile文件中根据config的配置进行编译。
Makefile文件
- 功能:决定源文件如何编译。
- 语法格式: obj-$(配置选项名称) += 源文件.o
- 例如:obj-$(CONFIG_HELLO_WORLD) += helloworld.o
- 结论:按Y键,CONFIG_HELLO_WORLD = Y,展开。
- 按N键,不编译。
向内核添加LED驱动代码,采用LED驱动。
-
上位机执行:
- 获取LED驱动代码——led_drv.rar
- led_drv.c //led的Linux系统驱动程序。
- led_test.c //led的UC应用测试程序。
-
继续执行:
cd /opt/kernel
vim drvers/char/Kconfig 文件添加:
config TAREAN_LED
tristate "tarena led driver"
help:
this is a x6818 board led driver
//保存退出
vim drivers/char/Makefile 文件中添加:
obj-$(CONFIG_TARENA_LED) += led_drv.o
//保存退出
- 配置Linux内核:
cd /opt/kernel
make menuconfig
#按"/‘’搜索刚刚添加的TAREAN_LED,得到配置菜单的位置。按Y键选择为*,保存退出。
make uImage -j4
cp arch/arm/boot/uImage /tftpboot ,将新编译的内核复制到uImage 中。
- 交叉编译LED测试程序
cp led_test.c /opt/rootfs/
cd /opt/rootfs/
arm...gcc -o led_test led_test.c
- 下位机测试:
tftp 0x48000000 uImage
bootm 0x48000000
下位机启动完毕执行led_test。
如果从内核配置的角度修改内核,结果在板子上还是不能运行,接下来需要修改Linux内核源码。
- 注意:3.8版本的Linux内核之前,只需要修改内核源码中一个跟硬件有关的源文件即可。但是3.8版本之后的Linux内核,采用新的技术:设备树来替代硬件信息的源文件内容,设备树就是一个文件,以.dts文件后缀结尾,此文件定义了大量的硬件信息,没有软件结构体变量之类的信息,例如:
- <memory : 0x48000000, 0x4000000>
- 如果采用源文件的形式描述硬件信息,则此文件位于内核源码/arch/arm/plat-s6p6818/x6818/device.c,只需要根据硬件差异修改此文件即可,此文件给设备驱动程序使用,后续驱动课还需要研究此文件。