4. 生成全量OTA包
任务说明
本案例目标为:基于当前系统源码编译产物,生成包含完整系统镜像的全量OTA包。该包可用于设备首次刷机或系统恢复场景,不依赖设备当前已有版本。
环境与依赖
- AOSP源码树(已执行
source build/envsetup.sh并lunch目标产品) - 已完成的编译产物(
make成功生成system.img、boot.img等) - 主机工具:
ota_from_target_files(位于build/tools/releasetools/)
实现步骤
全量OTA包生成分为两步:先将编译产物打包为target-files包,再基于该包生成全量OTA升级包。
1. 生成target-files包
# 在AOSP根目录执行
source build/envsetup.sh
lunch <product_name>-userdebug
# 生成target-files包(包含完整系统镜像)
make dist -j$(nproc)
# 产物位于 out/dist/<product_name>-target_files-*.zip
2. 生成全量OTA包
# 使用ota_from_target_files生成全量OTA
./build/tools/releasetools/ota_from_target_files \
-i out/dist/<product_name>-target_files-*.zip \
out/dist/full_ota-$(date +%Y%m%d).zip
# 参数说明:
# -i 指定输入target-files包(全量包只需一个输入)
# 输出为完整系统镜像的OTA包
关键代码逻辑
以下为ota_from_target_files生成全量包的核心处理流程(位于build/tools/releasetools/ota_from_target_files.py):
def WriteFullOTAPackage(input_zip, output_zip):
"""生成全量OTA包核心逻辑"""
# 1. 写入升级脚本头
script = edify_generator.EdifyGenerator(3, OPTIONS.info_dict)
script.Mount("/system")
script.AssertSomeFingerprint(OPTIONS.info_dict["fingerprint"])
# 2. 写入完整系统镜像
script.FormatPartition("/system")
script.LessTextInt("system", "system.img")
# 3. 写入boot镜像
script.WriteRawImage("/boot", "boot.img")
# 4. 写入完整文件清单(全量包包含所有文件)
script.ShowProgress(0.95, 0)
script.AddToZip("system", input_zip, output_zip)
# 5. 设置权限与属性
script.SetPermissions()
script.Unmount("/system")
验证方法
生成完成后,通过以下方式验证包完整性:
# 1. 检查包内是否包含完整镜像
unzip -l out/dist/full_ota-*.zip | grep -E "system.img|boot.img"
# 2. 验证包签名(若配置了签名)
./build/tools/releasetools/check_ota_package_signature \
out/dist/full_ota-*.zip
# 3. 检查升级脚本关键内容
unzip -p out/dist/full_ota-*.zip META-INF/com/google/android/updater-script | \
grep -E "format|package_extract_file"
通过条件:
- 包内包含
system.img与boot.img完整镜像文件 updater-script中包含format("/system")操作(区别于增量包)- 包大小与
system.img原始大小接近(全量包不依赖差分算法) - 签名验证通过(若配置)
常见问题
- 缺少
dist产物:需先执行make dist,仅make不会生成target-files包 - OTA包过大:全量包包含完整系统镜像,大小约等于所有img文件总和,属正常现象
- 设备无法升级:确认设备当前系统版本与包内
fingerprint匹配,或使用-w参数允许擦除数据