与recover工作相关的三个部分
- Recovery的工作需要整个软件平台的配合,从通信架构上看,主要有三个部分。
- 主系统:上面提到的正常启动模式,是用boot.img启动的系统,Android的正常工作模式。更新时,在这种模式中我们的上层操作就是使用OTA或者从SD卡中选择升级包。在重启进入recovery模式之前,会向BCB中写入命令,以便在重启后告诉bootloader进入recovery模式。
- Recovery:系统进入Recovery模式后加载Recovery分区,该分区包含recovery.img(和boot.img相同,包含了标准的内核和根文件系统)。进入该模式后主要是运行Recovery服务(/sbin/recovery)来做相应的操作(重启、升级、擦除cache、data等)。
- Bootloader:除了正常的加载启动系统外,还会通过读取MISC分区(BCB)获得主系统和recovery的消息。另外还会完成Modem和bootlader的升级。
在Recovery过程中,三部分之间的通信是必不可少的,他们之间的通信接口有两个:
1、通过CACHE分区的三个文件
- /cache/recovery/command: 这个文件保存着Main system传给Recovery的命令行,每一行就是一条命令,支持一下几种的组合:
--send_intent=anystring //write the text out to recovery/intent 在Recovery结束时在finish_recovery函数中将定义的intent字符串作为参数传进来,并写入到/cache/recovery/intent中
--update_package=root:path //verify install an OTA package file Main system将这条命令写入时,代表系统需要升级,在进入Recovery模式后,将该文件中的命令读取并 写入BCB中,然后进行相应的更新update.zip包的操作。
--wipe_data //erase user data(and cache),then reboot。擦除用户数据。擦除data分区时必须要擦除cache分区。
--wipe_cache //wipe cache(but not user data),then reboot。擦除cache分区。
- /cache/recovery/log: Recovery模式在工作中的log打印。在recovery服务运行过程中,stdout以及stderr会重定位到/tmp/recovery.log在recovery退出之前会将其转存到/cache/recovery/log中,供查看。
- /cache/recovery/intent:Recovery传递给Main system的信息。
2、通过BCB(Bootloader Control Block)
BCB是bootloader与Recovery的通信接口,也是Bootloader与Main system之间的通信接口。存储在flash中的MISC分区,占用三个page,其本身就是一个结构体,具体成员以及各成员含义如下:
struct bootloader_message{
char command[32];
char status[32];
char recovery[1024];
};
- command:在上文已经分析过了,当我们想要在重启进入Recovery模式时,会更新这个成员的值。另外在成功更新后结束Recovery时,会清除这个成员的值,防止重启时再次进入Recovery模式。
- status:在完成相应的更新后,Bootloader会将执行结果写入到这个字段。
- recovery:可被Main System写入,也可被Recovery服务程序写入。该文件的内容格式为:“recovery\n<recovery command>\n<recovery command>”