一、 Fastboot定义及功能
fastboot协议是一种通过USB连接与bootloader通讯的机制。它被设计的非常容易实现,适用于Linux、Windows或者macOS等多种平台。fastboot是Android系统提供的一种较recovery更底层的通过USB更新文件系统的方式。
Android开发包提供了fastboot.exe工具用于与Android系统通信,主要完成分区镜像烧录、分区擦除、设备重启、获取设备状态信息等操作。当需要通过fastboot协议与Android系统交互时,Android系统需要启动到bootloader模式,此时只有最基础的硬件初始化,包括按键、USB、存储系统、显示等模块,以支持分区镜像的写入和系统启动模式的切换。
二、 如何进入Fastboot模式
分析fastboot启动模式,要从手机启动过程开始,如下图:
图1 Linux Kernel启动流程
A1:上电后执行BootROM代码,探测启动媒介,查找第一阶段的引导加载程序bootloader;
A2:一旦boot媒介顺序确定,Boot ROM会试着装载bootloader的第一阶段到内部RAM中,一旦bootloader就位,BootROM 代码会跳到并执行bootloader;
B1:bootloader第一阶段会检测和设置外部 RAM;
B2:一旦外部RAM可用,系统会准备装载主bootloader,把它放到外部RAM 中;
B3:bootloader第二阶段是运行的第一个重要程序,它包含了设置文件系统,内存,网络支持和其他的代码;
B4:一旦bootloader完成这些特殊任务,开始寻找Linux内核,它会从boot媒介上装载 Linux内核,把它放到 RAM 中,同时它也会在内存中为内核替换一些在内核启动时读取的启动参数;
B5:跳到Linux内核。
fastboot就是在bootloader阶段中运行的。进入fastboot模式一般有两种方式,一种是在关机状态通过按键进入,另外一种是在Android系统启动之后通过adb指令进入到bootloader模式。
通过按键方式进入fastboot模式的过程:bootloader完成硬件初始化之后,启动Linux内核时,启动流程会检测按键,如果检测到对应的按键组合则将启动模式设置为fastboot模式。
按键检测逻辑为:
检测到按键之后,根据按键对启动模式设定:
设置启动模式时各个ODM厂商可以根据自身业务需求进行客制化调整。
通过adb指令进入fastboot模式的指令为:
Adb reboot bootloader
这条指令会将启动模式作为参数传到Linux的启动过程中,按键检测完成之后,还会检测是否有启动模式传入,如果存在参数传递,则重新设置启动模式,忽略之前的按键检测。
在最终获取的启动方式为FASTBOOT_MODE时,系统将进入fastboot模式启动流程,主要完成USB设备的设备的初始化,并启动fastboot指令处理线程;注册fastboot指令处理函数;显示fastboot菜单,并初始化菜单按钮检测程序,处理菜单切换和选择事件,对于一些厂商会客制化一些鉴权过程,鉴权失败则会切换到正常启动流程。
初始化fastboot的入口函数为:
注册fastboot处理函数的过程,简化之后的主要流程为:
三、 Fastboot常用指令
fastboot指令形式为:fastboot[<option>] <command>
提供与PC端的交互指令,通过命令行的形式实现单镜像更新、分区擦除、系统启动等操作。常用指令有:
参数(options):
例如:
擦除分区:fastbooterase boot
烧录分区:fastbootflash boot path/boot.img
打包烧录:fastbootupdate update.zip(将需要烧录的分区打包到update.zip中)
重启手机:fastbootreboot
获取手机端版本信息:fastboot getvar version:version-bootloader(获取bootloader版本号)
四、 Fastboot镜像烧录权限控制
通过命令行进行镜像烧录时,首先在PC端进行简单的过滤:
判断设备是否锁定,分区是否存在,是否为保护分区,校验通过之后给手机端发送flash指令,手机端收到之后进行更加详细的判断。验证识别锁定,分区是否保护代码如下:
校验通过之后根据镜像的不同格式调用不同的下载处理过程
五、 传输要求及传输示例
如果使用USB通道实现fastboot传输,对于USB的基本要求如下:
两个端点,一个输入端,一个输出端;
对于全速(full-speed)USB,最大包尺寸必须是64个字节;
对于高速(high-speed)USB,最大包尺寸必须是512个字节;
对于超高速(super-speed)USB,最大包尺寸必须是1024个字节;
协议完全是主机驱动(注:相对于设备客户端而言),并且是同步的。这与多通道、双向、异步的ADB协议不同。
fastboot传输和组帧:
步骤1、主机发送命令。一个命令是一个ASCII字符串,并且只能包含在不大于64个字节的单个包内;
步骤2、客户端用一个单个的不大于64个字节的包响应。响应包开头四个字节是“OKAY”、“FAIL”、“DATA”或者“INFO”。响应包剩余的字节可以包含ASCII格式的说明性信息;
步骤3、数据阶段。根据命令的不同,主机或者客户端将发送指定大小的数据。比指定长度短的包总是可接受的,零长度的包将被忽略。这个阶段会一直持续,直到客户端已经发送或接收了上面数据响应包中指定大小的字节数为止;
步骤4、客户端用一个单个的不大于64个字节的包响应;
步骤5、命令执行成功,结束交互。
以烧录boot分区镜像为例,fastboot数据传输过程如下:
图2 fastboot数据传输过程
六、 与其他刷机方式对比
七、 总结
fastboot提供对镜像烧录、擦除、手机信息查询等操作,系统权限较高,使用时需要格外留意。相比于其他刷机方式,具有操作方便使用灵活的优点,但是同时存在解锁复杂的缺点。同时对于fastboot需要运行在bootloader中,对于空板,无法使用,需要首先通过底层线刷模式烧录一个小的系统,之后才能启动fastboot的烧录流程。
参考资料:
android/system/core/fastboot/README.md
长按关注
内核工匠微信
Linux 内核黑科技 | 技术文章 | 精选教程