Android recovery分区表

本文以imx6q的Android 5.1为例,详细阐述了recovery分区表的配置和加载过程。主要内容包括:recovery分区表加载的源码分析,发现分区表recovery.fstab的生成位置在device/fsl/platform中由TARGET_RECOVERY_FSTAB变量决定,并且在recovery启动与正常启动中,分区表存在区别,特别是udisk和sd卡的挂载处理。通过对recovery分区表的独立设置,解决了在recovery模式下udisk无法挂载的问题。

写在前面

这篇文章以imx6q的android5.1为例,介绍recovery分区表的配置和加载

分区表加载

//bootable/recovery/roots.cpp
void load_volume_table()
{
    int i;
    int ret;

    fstab = fs_mgr_read_fstab("/etc/recovery.fstab");          //由此看见,recovery.fstab为recovery的分区表文件
    if (!fstab) {
        LOGE("failed to read /etc/recovery.fstab\n");
        return;
    }

    ret = fs_mgr_add_entry(fstab, "/tmp", "ramdisk", "ramdisk");
    if (ret < 0 ) {
        LOGE("failed to add /tmp entry to fstab\n");
        fs_mgr_free_fstab(fstab);
        fstab = NULL;
        return;
    }

    printf("recovery filesystem table\n");        //在/cache/recovery/last_log 文件中可以看到此log
    printf("=========================\n");
    for (i = 0; i < fstab->num_entries; ++i) {
        Volume* v = &fstab->recs[i];
        printf("  %d %s %s %s %lld\n", i, v->mount_point, v->fs_type,
               v->blk_device, v->length);
    }
    printf("\n");
}

recovery.fstab的生成

通过查看recovery的源码,知道了recovery加载的分区表是recovery.fstab,然后在device目录下进行查找,竟然没有找到。
一般编译recovery.img的指令只make recoveryimage,所以猜测分区表的加载可能是在Makefile中指定的,然后去查找/build/core/Makefile文件,果然。

......
$(INSTALLED_RECOVERYIMAG
<think>我们正在处理关于Android设备缺少recovery分区的问题。用户询问如何添加recovery分区或解决方案。根据引用内容:引用[1]提到recovery分区表与正常启动的分区表相同,但挂载问题不同,因此需要独立设置分区表。引用[2]说明了在编译过程中recovery分区大小不足的解决方法,即修改BoardConfig.mk中的BOARD_RECOVERYIMAGE_PARTITION_SIZE值。引用[3]则提供了添加新分区(如odm分区)的方法:确定上一个分区的起始地址和大小,然后计算新分区的起始地址。因此,添加recovery分区需要修改分区表(partitiontable)。在Android设备上,分区表通常由分区表文件(如GPT格式)定义,在编译过程中由设备制造商配置。解决方案步骤:1.确定设备的分区表布局:需要查看当前设备的分区表,可以通过编译环境中的分区表文件(如fstab或BoardConfig.mk)或设备上的/proc/partitions来了解。2.recovery分区分配空间:通常需要从现有分区中划分出一块空间(例如,减少system分区的大小),或者扩展整个存储设备的分区表(如果支持)。3.修改分区表配置文件:在Android源代码中,分区表通常在设备特定的BoardConfig.mk文件中定义。需要添加recovery分区的定义,包括分区大小和起始地址(如引用[3]所示)。4.调整recovery镜像的大小:如引用[2]所示,如果recovery镜像太大,需要调整分区大小(BOARD_RECOVERYIMAGE_PARTITION_SIZE)或优化recovery镜像。5.编译并烧写新的分区表:重新编译系统并烧写到设备。注意:修改分区表有风险,可能导致设备无法启动,因此需要谨慎操作。具体步骤:1.在设备对应的BoardConfig.mk文件中,添加或修改recovery分区的配置:```makefileBOARD_RECOVERYIMAGE_PARTITION_SIZE:=131663296#根据实际需要调整大小```同时,确保在分区表文件中(如partition.xml或fstab)添加recovery分区的条目。2.如果设备原本没有recovery分区,可能需要调整其他分区的大小来腾出空间。例如,在分区表文件中,调整其他分区的大小,然后为recovery分区指定起始地址和大小(如引用[3]的方法)。3.编译recovery镜像:确保在device.mk或类似文件中包含recovery模块。4.编译并烧写:使用编译命令生成新的镜像,然后通过fastboot或刷机工具烧写到设备。但是,请注意,有些设备可能使用动态分区(super分区),这种情况下,recovery分区可能包含在super分区内。在Android10及以上版本,动态分区是常见的。因此,需要根据设备的具体Android版本来调整方法。如果设备是动态分区,那么需要在动态分区的配置中添加recovery分区。具体步骤:-在super分区表(如super_partitions.mk)中添加recovery分区。-确保在BoardConfig.mk中设置BOARD_RECOVERYIMAGE_PARTITION_SIZE,并且这个值不大于super分区中分配给recovery的空间。如果用户设备原本没有recovery分区,并且用户希望添加,那么需要确保硬件(存储空间)支持,并且有相应的引导程序(bootloader)支持加载recovery分区。风险提示:修改分区表是高风险操作,操作不当可能导致设备变砖。建议在充分备份和了解设备分区结构的基础上进行。因此,我们给出以下解决方案:步骤1:检查当前设备的分区表Android源代码中,找到设备对应的分区表文件(通常位于device/<厂商>/<设备名>/目录下),查看是否存在recovery分区的定义。步骤2:如果没有,则添加recovery分区-在BoardConfig.mk中设置recovery分区大小:```makefileBOARD_RECOVERYIMAGE_PARTITION_SIZE:=<大小>#单位字节,例如131072000表示125MB```-在分区表文件(例如fstab.<设备名>或partition.xml)中添加recovery分区的条目。分区表文件可能使用不同的格式,需要根据实际情况添加。步骤3:调整其他分区(如果需要)-如果存储空间不足,可能需要减小其他分区(如system、vendor等)的大小。步骤4:配置recovery的编译-确保在设备mk文件中包含recovery的配置,例如:```makefile#启用recoveryBOARD_USES_RECOVERY_AS_BOOT:=falseBOARD_BUILD_SYSTEM_ROOT_IMAGE:=falseTARGET_NO_RECOVERY:=false```这些配置根据Android版本和设备而有所不同。步骤5:编译并烧写-编译整个系统(或recovery镜像),然后烧写新的分区表recovery镜像。注意:如果设备已经出厂,并且没有预留额外的空间,那么添加新分区可能非常困难,甚至不可能。这种情况下,可能需要使用虚拟分区或通过其他方式进入恢复模式(例如通过fastboot启动临时recovery镜像)。替代方案:如果无法添加recovery分区,可以考虑使用fastboot模式临时启动recovery镜像(不需要永久写入recovery分区):```bashfastbootbootrecovery.img```但这种方式需要设备解锁bootloader,并且每次都需要通过电脑执行命令。总结:添加recovery分区需要在编译阶段修改分区表配置,并重新编译和烧写系统。如果设备硬件空间不足,则无法添加。相关问题:1.如何查看Android设备的分区表?2.如何调整现有分区的大小?3.动态分区(super分区)如何添加recovery分区?4.如何通过fastboot临时启动recovery镜像?5.修改分区表有哪些风险?如何避免设备变砖?</think>### Android 设备缺少 recovery 分区的解决方案 #### 问题核心原因 Recovery 分区是 Android 系统用于系统恢复/刷机的独立分区。设备缺失该分区通常由以下原因导致: 1. **分区表未定义**:设备的分区表(partition table)未包含 recovery 分区条目 2. **空间分配不足**:recovery 分区大小未配置或配置值过小(如引用[2]所示) 3. **镜像生成失败**:编译时因分区限制导致 recovery.img 无法生成 --- ### 解决方案 #### 方法 1:添加 recovery 分区到分区表(推荐) **步骤:** 1. **定位分区表文件** 在 Android 源码中找到设备的分区配置文件,通常位于: `device/<厂商>/<设备名>/BoardConfig.mk` 或 `partition.xml` 2. **计算分区地址**(引用[3]方法) 假设最后一个分区是 `system`(起始地址 `0x007ed000`,大小 `0x00614000`): $$ \text{recovery 起始地址} = \text{system 起始地址} + \text{system 大小} $$ $$ 0x007ed000 + 0x00614000 = 0x00e01000 $$ 3. **修改分区表** 在 `BoardConfig.mk` 中添加(示例): ```makefile # 定义分区大小(参考引用[2]) BOARD_RECOVERYIMAGE_PARTITION_SIZE := 131072000 # 125MB # 定义分区类型 TARGET_RECOVERY_FSTAB := device/<厂商>/<设备名>/recovery.fstab ``` 4. **更新存储映射**(引用[1]关键点) 在 `recovery.fstab` 中独立配置挂载点,避免与正常系统冲突: ``` /sdcard vfat /dev/block/sda4 # 明确指定 recovery 模式下的存储设备 ``` 5. **重新编译并烧写** ```bash make recoveryimage && fastboot flash recovery recovery.img ``` --- #### 方法 2:扩展现有分区大小(适用于空间不足) 当出现引用[2]的镜像过大错误时: 1. **定位分区大小定义** ```bash grep -r "BOARD_RECOVERYIMAGE_PARTITION_SIZE" device/ ``` 2. **调整大小值**(增加 20%-30%) ```makefile # 原值 131663296 → 新值 157995955(增加 20%) BOARD_RECOVERYIMAGE_PARTITION_SIZE := 157995955 ``` --- #### 方法 3:临时替代方案(无需物理分区) 若硬件限制无法修改分区表: 1. **通过 boot 分区启动 recovery** ```bash fastboot boot recovery.img # 从 boot 分区临时加载 recovery ``` 2. **使用虚拟 A/B 分区(Android 11+)** 在 `BoardConfig.mk` 中启用: ```makefile BOARD_USES_RECOVERY_AS_BOOT := true ``` --- ### 关键注意事项 1. **分区地址对齐** 起始地址需按 `2048-sector` 对齐(通常为 1MB 边界),避免 I/O 性能下降: $$ \text{aligned\_address} = \left\lceil \frac{\text{raw\_address}}{1048576} \right\rceil \times 1048576 $$ 2. **备份原始分区表** 修改前务必备份: ```bash adb pull /dev/block/by-name/ptable ptable_backup.img ``` 3. **验证分区连续性** 使用 `parted` 工具检查分区是否重叠: ```bash parted /dev/block/sda print ``` > **风险提示**:错误修改分区表可能导致设备变砖!操作前需解锁 bootloader 并确保可访问 EDL 救砖模式。 --- ### 相关问题 1. **如何确定设备是否支持添加新分区?** - 需检查存储设备剩余空间(`cat /proc/partitions`) - 验证 bootloader 是否支持动态分区表更新 2. **Android 动态分区(super.img)如何影响 recovery?** - Android 10+ 需在 `super` 分区内分配 recovery 子分区 - 需修改 `dynamic_partitions_info.txt` 而非传统分区表 3. **recovery 分区最小合理大小是多少?** - 基础功能: ≥ 64MB(可执行基础刷机) - GUI 支持: ≥ 125MB(含图形界面和工具) - 计算公式: $$ \text{min\_size} = \text{recovery\_img} \times 1.3 + \text{cache\_overhead} $$ 4. **修改后 recovery 仍然无法挂载存储怎么办?** - 检查 `recovery.fstab` 设备路径(引用[1]的 sda4 问题) - 确认内核驱动支持(`CONFIG_MMC_BLOCK=y`) 5. **如何调试 recovery 分区的启动失败?** - 通过串口日志查看 bootloader 加载过程 - 使用 `adb shell dmesg | grep recovery` 分析内核识别情况 --- > 引用来源: > [^1]: Recovery 分区独立配置与存储挂载问题 > [^2]: Recovery 镜像编译时的分区大小错误解决方案 > [^3]: 新增分区的地址计算逻辑
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值