目录
一、uboot概述
Bootloader
Bootloader基本功能:
二、SD卡启动盘制作
三、uboot的使用
3.1uboot模式
自启动模式
交互模式
3.2uboot帮助命令
3.3uboot环境变量命令
3.4常用环境变量
3.5网络传输命令
3.6u-boot访问存储器命令
3.7 u-boot自启动环境变量(bootcmd)
五、uboot源码结构、配置、编译
1、uboot源码结构
1.1 uboot源码获取
1.2 uboot的特点
1.3 uboot源码结构
2、uboot配置与编译
2.1uboot配置
2.2 uboot编译
六、Linux内核概述
1.1内核与操作系统
1.2Linux层次结构
1.3Linux内核特点
七、Linux内核源码结构
2.1Linux内核源码获取
Linux内核源码下载
Linux内核版本命名
Linux内核版本选择
2.2Linux内核源码结构
八、Linux内核源码的配置和编译
配置交叉编译工具链
读README
配置内核源码支持当前的硬件平台
驱动配置
内核编译
编译:
问题:
解决问题的方法:
测试内核
一、uboot概述
Bootloader
bootloader就相当于类,uboot就相当于对象。嵌入式领域常用的bootloader就是uboot
在操作系统运行之前运行的一小段代码,用于将软硬件环境初始化到一个合适的状态,为操作系统的加载和运行做准备,其本质为一段裸机程序不是操作系统本身
Bootloader基本功能:
- 初始化软硬件环境
- 引导加载linux内核
- 给linux内核传参
- 执行用户命令
注:bootloader是启动引导程序的统称,嵌入式linux常用的bootloader是uboot。
常见的Bootloader
二、SD卡启动盘制作
SD卡的存储以扇区为单位,每个扇区的大小为512Byte, 其中零扇区存储分区表(即分区信息),后续的扇区可自行分区和格式化;若选择SD卡启动,处理器上电后从第一个扇区开始将其中的内容搬移到内存,所以我们把uboot放到从第一个扇区开始之后的空间, 之后的空间根据个人需求可进行分区和格式化
具体制作步骤详情看实验手册-》实验四
三、uboot的使用
3.1uboot模式
自启动模式
uboot启动后若没有用户介入,倒计时结束后会自动执行自启动环境变量(bootcmd)中设置的命令(一般作加载和启动内核)
交互模式
倒计时结束之前按下任意按键uboot会进入交互模式,交互模式下用户可输入uboot命令
3.2uboot帮助命令
help
查看uboot支持的所有命令
help 命令
查看当前命令的使用方法
3.3uboot环境变量命令
printenv
打印uboot中所有的环境变量
setenv
设置指定的环境变量(保存在RAM中)
setenv 环境变量 环境变量的值
saveenv
保存所有环境变量到EMMC中
3.4常用环境变量
ipaddr
uboot的IP地址
serverip
服务器的IP地址(即ubuntu的IP)
bootdelay
进入自启动模式之前倒计时的秒数
3.5网络传输命令
loadb
通过Kermit协议下载文件到指定的内存地址( loadb 地址)
tftp
通过tftp协议下载文件到指定的内存地址( tftp 地址 文件名 )
3.6u-boot访问存储器命令
mmc read
将EMMC中指定扇区中的内容读取到内存中指定的地址( mmc read )
addr: 内存地址
blk#: EMMC中的扇区编号
cnt: 读取的扇区的个数
mmc write
将内存中指定地址中的内容写入到EMMC中指定的扇区
mmc write
3.7 u-boot自启动环境变量(bootcmd)
该环境变量可以设置成一到多个uboot命令的集合(若有多个使用\;分割),自启动模式下uboot就会按照bootcmd中命令的顺序逐条执行
把printenv命令写进去,开机之后不做干预,倒计时结束就会自动打印环境
eg:
setenv bootcmd tftp 40008000 interface.bin\;go 40008000
saveenv
- linux内核的安装与加载
这一章节主要分为两大块一个为产品阶段即:Linux内核、根文件系统、uboot全部存储到硬盘内,另一个为研发阶段,研发阶段因为需要反复调试,所以需要我们把跟文件系统放到NFS内使用共享的方式,Linux内核放到tftp下进行传输,uboot最好使用SD卡的方式。详情见实验手册中实验五,需要注意实验五中的第一个目的是为了练习使用tftp加载文件,这里不会正常进入linux系统。
五、uboot源码结构、配置、编译
1、uboot源码结构
1.1 uboot源码获取
uboot是一个开源的软件。开源有两层含义。一是可以免费用、二是开放源代码
uboot源码下载
http://www.denx.de/wiki/U-Boot/
uboot版本命名:
前期:uboot-1.2.3
现在:uboot-2008.01
08年以前uboot是1.2.几1.3.几这样命名08年开始以年份和月份命名。它的更新是非常频繁的上次更新是两天前。
uboot版本选择
支持对应的硬件平台
相对成熟的版本(资料多)
每当发布新的芯片后uboot就会增加对应芯片的版本。一般和处理器同一时期发布的uboot版本对处理器的支持较好。
1.2 uboot的特点
代码结构清晰
支持丰富的处理器与开发板,易于移植
支持丰富的用户命令
支持丰富的网络协议
支持丰富的文件系统
支持丰富的设备驱动
更新活跃、用户较多、资料丰富
开放源代码
较高的稳定性
不具有通用性(不同的处理器、开发板uboot不可通用)
1.3 uboot源码结构
由于uboot的源码特别多所以是由很多个文件夹组成的,同类型的源码放到一个文件夹里
平台相关代码
即与CPU架构或开发板硬件相关的源码,硬件的改动对应的代码也需要进行修改
arch:与CPU架构相关的源代码
board:与开发板相关的源代码,包含各种官方评估板对应的源码
api: 这个目录下有很多的用户接口
arch: 目录下存储的是架构
board:开发板样例
boards.cfg:这个文件是配置信息
common:这下面全是uboot命令的.c文件
config.mk:也是一个配置文件
COPYING:这是版权文件虽然是开源软件但是也不能乱用
CREDITS:这里是代码贡献者名单包括他们的邮箱
disk:磁盘操作的命令文件夹
readme:一个说明书或者说帮助文档,这个说明书有5000多行都是一些介绍性的的东西。
dos:这里是详细的说明书
drivers:这里面全是驱动文件
dts:设备树文件夹,后面学习驱动时在详细学习。
examples:里面是例程,在不会写的时候可以参考一下
fs:文件系统,这里面每个文件夹内都是文件系统的源代码和makefile文件这里面ext4是嵌入式领域常用的文件系统。
include:这里是头文件
lib:这里是库
makefile:方便我们编译uboot镜像。它这个makefile是层层调用的每个文件夹下都有,使用make命令后总的makefile文件会调用每层的马克file文件来共同编译出uboot镜像。
post:上电自检程序
tools:工具
net:网络文件夹,这里面是uboot支持的一些网络。
2、uboot配置与编译
为了保证uboot适用所有的开发板,uboot把所有的开发板都写出来了,需要哪个编译哪个
2.1uboot配置
1.指定当前使用的硬件平台
make _config(咱们用的是make fs6818_config)
注1:为当前使用的开发板的名字
注2:执行该命令的前提是uboot源码支持该开发板
注3:该命令必须在uboot源码的顶层目录下执行
hqyj@hqyj:u-boot-2014.07-fs6818$ make fs6818_config
Configuring for fs6818 board...
2.指定编译uboot源码使用的编译器
将以下内容(咱们使用的源码是改过的,但是要知道这个流程)
198 ifeq ($(HOSTARCH),$(ARCH))
199 CROSS_COMPILE ?=
200 endif
修改为
198 ifeq (arm,arm)
199 CROSS_COMPILE ?= arm-none-linux-gnueabi-
200 endif
2.2 uboot编译
1.编译uboot
make / make all(编译的时间比较长)
注1:该命令必须在uboot源码的顶层目录下执行
注2:该命令执行后在uboot源码顶层目录下生成u-boot.bin
编译需要大概一分钟。编译完多了几个文件,多了一个system.map文件和那些u-boot开头的。
make在编译的过程中先将.c和.s编译成.o文件。最后把他们链接(ld)成一个可执行文件绿色的那个u-boot。他是elf格式的。我们肯定不能把他刷到板子上。不过在这之后它还会用objcopy把利用elf文件生成bin文件。这里还有一个srec文件这是符合摩托罗拉的二进制文件。
2.清除编译过程中生成的中间文件
make clean
make distclean
注1:该命令必须在uboot源码的顶层目录下执行
这些中间文件就是.o文件。执行make clean只是清除这些.o文件。执行下面那个会把生成的可执行文件和二进制文件也删除。恢复刚下载的源码状态。
编译问题解决
Make的时候可能出现上面问题,出现上面问题,如下方法解决:
六、Linux内核概述
1.1内核与操作系统
内核
内核是一个操作系统的核心,提供了操作系统最基本的功能,是操作系统工作的基础,决定着整个系统的性能和稳定性
操作系统
操作系统是在内核的基础上添加了各种工具集、桌面管理器、库、shell、应用程序等(我们使用的网络协议都是基于TCP/ip或者UDP/IP协议开发的)(我们使用rm、mv、cp。。。这些命令都不是内核提供的)
shell翻译过来就是贝壳,他把内核很好的保护了起来。Linux内核内有文件管理系统。所以可以操作磁盘。那现在我们要操作一些文件就需要去操作内核让内核再去操作文件。但是内核很复杂,我们学到不透的时候一个误操作可能就会把内核搞坏了。所以我们操作shell让shell再去操作内核就会很安全了。
库这些lib也不是内核包含的。
图形化界面也不属于内核,内核本身只支持大黑框
1.2Linux层次结构
进程管理、内存管理、文件系统、网络管理、驱动管理
1.3Linux内核特点
代码结构清晰、模块化设计
支持丰富的硬件平台
较高的稳定性
开很久他都不需要维护。所以一些嵌入式设备比如路由器、基站、充电桩。还有一些大型的服务器都会用Linux。
轻量化及较强的裁剪性,只有2.9MB
开放源代码
更新活跃、用户较多、资料丰富
支持丰富的网络协议,95%服务器都用Linux就是因为他的网络协议非常的丰富。
七、Linux内核源码结构
2.1Linux内核源码获取
Linux内核源码下载
https://www.kernel.org/
Linux内核版本命名
主版本号.次版本号.修订版本
Linux内核版本选择
支持对应的硬件平台
相对成熟的版本(资料多)
稳定版本(次版本号为偶数的版本一般都是稳定版)
内核和uboot是一样的现在很少自己配置了,都是厂家提供了。
2.2Linux内核源码结构
把源码拖到ubuntu里解压
平台相关代码
arch: 与CPU架构相关的源代码
block:磁盘设备的支持 crypto:加密相关
drivers:设备驱动 firmware:固件
fs:文件系统 include:头文件
一般格式化磁盘都格式化成ntfs
init:内核初始化 ipc:进程间通信
共享内存消息队列什么的都是再ipc目录下实现的
kernel:内核核心调度机制等 lib:库 内核的核心算法。
mm:内存管理 net:网络协议
scripts:工具、脚本等 security:安全
usr:打包与压缩 virt:虚拟
COPYING: 版权 gpl版权,GNU开源协议
CREDITS: 内核贡献者
README: 说明文档
Documentation: 帮助文档
Makefile: 编译管理
samples: 示例
tools: 工具
Kconfig:内核自带的图形化界面
... ...
八、Linux内核源码的配置和编译
配置交叉编译工具链
打开内核源码顶层目录的Makefile,搜索CROSS_COMPILE
195 ARCH ?=
196 CROSS_COMPILE ?=
修改为:
195 ARCH ?= arm
196 CROSS_COMPILE ?= arm-none-linux-gnueabi-
读README
拿到内核源码之后,应该先清除,内核源码中的中间文件
make clean
make distclean
make mrproper --》清除更干净
配置内核源码支持当前的硬件平台
方法1:
make help
得到以下信息:
fs6818_defconfig - Build for fs6818
方法2:
进入arch/arm/configs/目录
发现以下文件fs6818_defconfig ,所以PLATFORM=fs6818.
让当前的内核支持自己的硬件平台,应该执行make fs6818_defconfig
驱动配置
执行命令:make menuconfig
实际开发中随内核进行菜单选项的配置,都是使用make menuconfig命令
问题1:
第一次使用make menuconfig 需要安装图形化界面的工具
配置之前需要安装图形图(make meuconfig):
sudo apt-get install libncurses5-dev
问题2:
出现以下错误:
cripts/kconfig/mconf Kconfig
Your display is too small to run Menuconfig!
It must be at least 19 lines by 80 columns.
make[1]: *** [menuconfig] Error 1
make: *** [menuconfig] Error 2
原因:终端的字体太大,缩小一点
内核编译
编译:
make uImage
time make uImage -jx
-time:回显编译的时间
-jx:使用多线程的方式进行编译,x可以是2,4,6,8
问题:
在编译的过程中可能出现如下错误:
"mkimage" command not found - U-Boot images will not be built
make[1]: *** [arch/arm/boot/uImage] Error 1
make: *** [uImage] Error 2
错误的原因:找不到mkimage命令,根据提示分析出来mkimage应该存在uboot源码目录中
uboot源码必须进行编译之后才会有mkimage可执行程序
解决问题的方法:
将uboot源码的tools目录下的mkimage,sudo cp mkimage /usr/bin
拷贝到到ubuntu的/use/bin目录下:
sudo cp ./tools/mkimage /usr/bin
uboot目录 ubuntu目录
再次对内核源码进行编译即可通过。
测试内核
将arch/arm/boot/目录下的uImage拷贝到tftpboot目录下,
测试uImage是否可以正常启动,并且挂载根文件系统(重启开发板,自动方式:先将uImage下载到内存里面,然后bootcmd启动内核,然后给内核传递参数。