uboot学习前传

为什么要有uboot

计算机系统的主要部件

  1. 计算机系统的组成部件非常多,不同的计算机系统组成部件也不同。但是所有的计算机系统运行时需要的主要核心部件都是:CPU,存储器,IO。

PC机的启动过程

  1. 典型的PC机的部署:BIOS(Norflash)部署在PC机的主板上(随主板出厂时已经预制了),操作系统部署在硬盘上,内存在掉电时无作用,CPU在掉电时不工作。
  2. 启动过程:PC上电后先执行BIOS程序,BIOS程序负责初始化DDR内存,负责初始化硬盘,然后从硬盘上将OS镜像读取到DDR中,然后跳转到DDR中去执行OS直到启动(os启动后BIOS就无用了)。

典型嵌入式Linux系统启动过程

  1. 嵌入式系统的部署和启动都是参考pc机的。只是设备上有一些差别。
  2. 典型嵌入式系统的部署:uboot程序部署在FLash(能作为启动设备的Flash)上,OS部署在Flash(嵌入式系统中用Flash代替了硬盘)上,内存在掉电时无作用,CPU在掉电时不工作。
  3. 启动过程:嵌入式系统上电后先执行uboot,uboot负责初始化DDR,初始化FLAsh,然后将os从Flash中读取到DDR中,然后启动OS(os启动后uboot就没有用了)。
  4. 嵌入式系统和PC机启动过程几乎没有两样,只是BIOS成了uboot,硬盘成了Flash。

Android系统启动过程

  1. Android系统的启动和linux系统几乎一样。只是在内核启动后加载根文件系统后不同了。
  2. 可以认为启动分为两个阶段:第一个阶段是uboot到os启动;第二个阶段是os启动后到根文件加载到命令行执行;现在我们主要研究第一阶段,Android的启动和linux的差别在第二阶段。

uboot到底是用来做什么的?

  1. uboot主要作用是用来启动操作系统内核的。
  2. uboot还要负责部署整个计算机系统。
  3. uboot中还有操作flash等板子上硬盘的驱动。
  4. uboot还得提供一个命令行界面供人来操作。

为什么是uboot

uboot是从哪里来的

  1. uboot是sourceforge上的开源项目。由一个德国人最早发起的项目,然后整个网络对uboot感兴趣的人共同维护发展而来的一个bootloader。

uboot发展历程

  1. 自己使用的小开源项目。
  2. 被更多人认可使用。
  3. 被SOC厂商默认支持。

uboot版本号问题

  1. 早期的uboot版本号是这样:uboot1.3.4
    后期是这样uboot-2010.06 。
  2. uboot的核心部分几乎没怎么变化,越新的版本支持的开发板越多而已,对于一个老版本的芯片来说,新旧版本的uboot并没有差异。

uboot的可移植性的正确理解

  1. uboot就是universal bootloader(通用的启动代码)。
  2. uboot具有可移植性并不是说uboot在哪个开发板都可以随便用,而是说uboot具有在源代码级别的移植能力,可以针对多个开发板进行移植,移植后就可以在这个开发板上使用了。

uboot必须解决哪些问题

自身可开机直接启动

  1. 一般的Soc都支持多种启动方式:sd卡,norflash等,uboot要能够开机启动,必须根据具体的Soc的启动设计来设计uboot。
  2. uboot必须进行和硬件相对应的代码级别的更改和移植,才能保证可以从相应的启动介质启动。uboot中第一阶段的start.s文件中具体处理了这一块。

能够引导OS内核启动并给内核传参

  1. uboot的终极目标就是启动内核。
  2. linux内核在设计的时候,设计为可以被传参。也就是说我们可以在uboot事先给linux内核准备一些启动参数放在内核中特定位置然后传给内核,内核启动后回到这个特定位置去取uboot传给他的参数,然后在内核中解析这些参数,这些参数将被用来指导linux内核的启动过程。

能提供系统部署功能

  1. uboot必须能够被人借助而完成整个系统在Flash上的烧录下载工作。

能进行Soc级和板级硬件管理

  1. uboot中实现了一部分硬件的控制能力(uboot中初始化了一部分硬件),因为uboot为了完成一些任务必须让这些硬件工作。例如uboot要在刷机时在LCD上显示进度条就必须驱动LCD。
  2. SoC级就是SoC内部外设,板级就是SoC外面开发板上面的硬件(网卡,iNand)。

uboot的“生命周期”

  1. 生命周期就是:uboot什么时候运行,什么时候结束运行。
  2. uboot本质是一个裸机程序(不是操作系统),一旦uboot开始,SoC就会单纯运行uboot 。uboot启动了内核后,uboot自己本身就死了,要想再次看到uboot界面只能重启系统。
  3. uboot的入口和出口。uboot的入口是开机自动启动,唯一出口是启动内核。uboot还可以执行很多其他的任务(例如烧录系统),但是其他任务执行完后都可以回到uboot的命令行继续执行uboot命令,而启动内核命令一旦执行就回不来了。

uboot的工作方式

从逻辑程序镜像uboot.bin说起

  1. uboot的本质就是一个裸机程序,uboot大于16k(一般uboot在180k-400k)。
  2. uboot本身是一个开源项目,由若干个.c和.h文件组成,配置编译之后会生成一个uboot.bin,这就是uboot这个裸机程序的镜像文件。然后这个镜像文件被合理的烧录到启动介质中拿给SoC去启动。在没有运行时,表现为uboot.bin,一般在启动介质中。uboot运行时会被加载到内存中然后一条指令一条指令的拿给Soc去运行。

uboot的命令式shell界面

  1. 普通的裸机程序运行就直接执行了,执行时效果和代码有关。
  2. 有些程序需要和人进行交互,所以程序中实现了一个shell(shell就是提供人机交互的一个界面)。
  3. uboot中的shell工作方式和linux中的终端shell非常像,只是命令集不一样。

掌握uboot使用的两个关键点:命令和环境变量

  1. uboot启动后大部分时间和工作都在shell下完成的(例如uboot在部署系统要在shell下输入命令,设置环境变量也得在命令行下,启动内核也得在命令行下输入命令)。
  2. 命令就是shell中可以识别的各种命令。uboot中有几十个命令,我们还可以根据需要自己给uboot添加命令。
  3. uboot的环境变量和操作系统的环境变量的工作原理和方式几乎完全一样。uboot在设计时借助了操作系统的设计理念(命令行工作方式借鉴了linux终端命令行,环境变量借鉴了操作系统的环境变量,驱动管理几乎完全照抄了linux的驱动框架)。
  4. 环境变量可以被认为是系统的全局变量,环境变量名是系统内置的。系统或者我们自己的程序在运行时可以通过读取环境变量来指导程序的运行。这样设计的好处就是灵活,例如我们要让一个程序更改运行方法,不用去重新修改程序代码再重新编译运行,而只要修改相应的环境变量就可以了。
  5. 环境变量就是运行时的配置属性。

uboot的常用命令1

类似linux终端的行缓存命令行

  1. 行缓存的意思就是:当我们向终端命令行输入命令时,这些命令没有立即被系统识别,而是被缓冲到一个缓冲区,当我们按下回车键后,系统就认为我们输入完了,然后将缓冲区的命令拿去分析处理。
  2. linux终端设计有3种缓冲机制:无缓冲,行缓冲,全缓冲

有些命令有简化的别名

  1. printenv可以简化为print(打印环境变量),setenv可以简化为set。

有些命令会带参数(格式是固定的)

  1. uboot的每个命令都有事先规定好的各种格式。有些命令就是不带参数的(例如printenv/print);而有些命令是带可选参数的(例如help);有些命令必须带参数(例如setenv/set)。

命令中的特殊符号(例如单引号)

  1. 有些命令中间有 ; 需要加单引号

有些命令是一个命令族(movi)

  1. 命令族意思就是好多个命令开头都是用同一个命令关键字的,但是后面的参数不一样,这些命令的功能也不同。
  2. 同一个命令族中所有的命令都要极大的关联,例如movi和movinand操作有关。

第一个命令print

  1. print不用带参数,作用是打印出系统中所有的环境变量。
  2. 环境变量就好像程序中的全局变量一样。程序中任何地方都可以根据需要去调用或更改环境变量,环境变量和全局变量不同之处在于:全局变量的生命周期是在程序一次运行当中,开始运行时诞生,程序结束时死亡,下次运行程序时重头开;但是环境变量被存储在flash的另一块专门区域(环境变量分区),一旦程序中保存了环境变量,那么下次开机时环境变量的值将维持上一次更改保存的值.

uboot的常用命令2

设置(添加/更改)环境变量:setenv/set

  1. set name value

保存环境变量的更改:saveenv/save

  1. save命令不带参数,直接执行,作用是将内存中的环境变量的值同步保存到flash中环境变量的分区。注意:环境变量的保存是整体的覆盖保存,也就是说内存中所有的环境变量都会整体的将flash中环境变量分区中原来的内容全部覆盖。

  2. 总结:彻底更改一个环境变量的值,需要两步:第一步set命令来更改内存中的环境变量,第二步用save命令将其同步到flash中环境变量分区。

网络测试命令:ping

  1. ping ip地址

tftp下载命令:tftp

uboot本身主要目标是启动内核,为了完成启动内核必须要能够部署内核,uboot为了部署内核就需要将内核镜像从主机(windows或者虚拟机linux)中下载烧录到本地开发板Flash中。主要通过fastboot和tftp下载
fastboot的方式是通过USB线进行数据传输。
tftp的方式是通过有线网络下载。

tftp

  1. tftp下载时实际上uboot扮演的是tftp客户端程序角色,主机windows或者linux中必须有一个tftp服务器,然后将下载的镜像文件放在服务器的下载目录中,然后开发板中使用uboot的tftp命令下载即可。

uboot的常用命令3

SD卡/iNand操作命令movi

  1. 开发板如果用SD卡/iNand等作为Flash,则在uboot中操作flash的命令为movi。
  2. movi是一个命令族,有很多子命令。
  3. movi都是movi read 和 movi write一组的,movi read用来读取sd卡到ddr,write将ddr内存内容写入到sd卡。理解这些命令时一定注意涉及到的两个硬件:sd卡和DDR内存。

NandFlash操作命令:nand

内存操作命令:mm,mw,md

  1. DDR中是没有分区的。uboot是一个裸机程序,不像操作系统会由系统整体管理所有内存,系统负责分配和管理。
  2. mm:memory modify,修改(批量逐个修改)内存中的某一块。
  3. md:memory display,用来显示内存中的内容。
  4. mw:memory write,将内容写到内存中。

启动内核命令:bootm,go

  1. bootm:启动内核同时给内核传参。一般情况用这个命令。
  2. go:启动内核不传参。go命令本来不是专门启动内核设计的,go其实就是一个函数指针指向一个内存地址然后直接调用那个函数,go的实质就是PC直接跳转到一个内存地址去运行而已。

uboot的常用环境变量

环境变量如何参与程序运行

  1. 环境变量有2份,一份在flash,一份在ddr中。uboot开机时一次性从flash中读取全部环境变量到ddr中作为环境变量的初始化值,然后使用过程中都是用ddr中这一份,用户可以用save命令将ddr中的环境变量保存到flash中。下次开机时又从flash中读取。
  2. 环境变量在uboot是用字符串表示的,也就是说uboot是按照字符匹配的方式来区分各个环境变量的。

自动运行倒计时:bootdelay

网络设置:ipaddr,serverip

  1. ipaddr是开发板的本地ip地址。
  2. serverip是开发板通过tftp命令去tftp服务器下载东西时,tftp服务器的IP地址。
  3. gatewayip是开发板的本地网关地址。
  4. netmask是子网掩码。
  5. ethaddr是开发板的本地网卡的MAC地址。

自动运行命令设置:bootcmd

  1. uboot启动后会开机倒数bootdelay秒,如果没有人按回车打断倒数,uboot会自动执行启动命令来启动内核。
  2. uboot开机自动启动实际就是在内部执行了bootcmd这个环境变量的值所对应的命令集。

uboot给kernel传参:bootargs

  1. linux内核启动时可接受uboot传递的启动参数,这些启动参数是uboot和内核约定好的,linux内核在启动参数的指导下完成启动过程。这样的设计是为了灵活,为了内核在不重新编译的情况下可以用不同的方式启动。
  2. 内核传参非常重要。在内核移植时需要正确传参。

新建,更改,删除一个环境变量的方法

  1. 新建,更改,删除一个环境变量,使用set命令。
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值