一、A/B升级之系统image的生成
本篇将对AB升级打开宏开关后make 和 makeotapackage的流程做分析,下面这张图是之前文档中所提到的按照对应文件打开宏开关,即可开启AB升级,但是代码里面针对该宏控也有对应代码处理,本次先分析device 和 build下的修改

一、device主要修改
最初加入了MTK_AB_OTA_UPDATER = yes
去除cache分区编译的控制开关
ifneq ($(strip $(MTK_AB_OTA_UPDATER)), yes)
BOARD_CACHEIMAGE_FILE_SYSTEM_TYPE := ext4
endif
diff --git a/mediateksample/k39tv1_64_bsp/BoardConfig.mk b/mediateksample/k39tv1_64_bsp/BoardConfig.mk index 13eb004..fd32381 100644 --- a/mediateksample/k39tv1_64_bsp/BoardConfig.mk +++ b/mediateksample/k39tv1_64_bsp/BoardConfig.mk @@ -6,10 +6,11 @@ include device/mediatek/mt6739/BoardConfig.mk #Config partition size -include $(MTK_PTGEN_OUT)/partition_size.mk +ifneq ($(strip $(MTK_AB_OTA_UPDATER)), yes) BOARD_CACHEIMAGE_FILE_SYSTEM_TYPE := ext4 +endif BOARD_FLASH_BLOCK_SIZE := 4096 - MTK_INTERNAL_CDEFS := $(foreach t,$(AUTO_ADD_GLOBAL_DEFINE_BY_NAME),$(if $(filter-out no NO none NONE false FALSE,$($(t))),-D$(t))) MTK_INTERNAL_CDEFS += $(foreach t,$(AUTO_ADD_GLOBAL_DEFINE_BY_VALUE),$(if $(filter-out no NO none NONE false FALSE,$($(t))),$(foreach v,$(shell echo $($(t)) | tr '[a-z]' '[A-Z]'),-D$(v)))) MTK_INTERNAL_CDEFS += $(foreach t,$(AUTO_ADD_GLOBAL_DEFINE_BY_NAME_VALUE),$(if $(filter-out no NO none NONE false FALSE,$($(t))),-D$(t)=\"$(strip $($(t)))\")) diff --git a/mediateksample/k39tv1_64_bsp/ProjectConfig.mk b/mediateksample/k39tv1_64_bsp/ProjectConfig.mk index 99aebd3..3419c65 100755 --- a/mediateksample/k39tv1_64_bsp/ProjectConfig.mk +++ b/mediateksample/k39tv1_64_bsp/ProjectConfig.mk @@ -685,7 +685,8 @@ TRUSTONIC_TEE_SUPPORT = no USE_FRAUNHOFER_AAC = no USE_XML_AUDIO_POLICY_CONF = 1 WIFI_WEP_KEY_ID_SET = no -MTK_AB_OTA_UPDATER = no +CONFIG_MTK_AB_OTA_UPDATER = yes +MTK_AB_OTA_UPDATER = yes
搜索宏控相关文件如下
libiaobiao:~/code/s219_ab/device$ grep -rni "MTK_AB_OTA_UPDATER"
mediateksample/k39tv1_64_bsp/BoardConfig.mk:9:ifneq ($(strip $(MTK_AB_OTA_UPDATER)), yes)
mediateksample/k39tv1_64_bsp/ProjectConfig.mk:688:CONFIG_MTK_AB_OTA_UPDATER = yes
mediateksample/k39tv1_64_bsp/ProjectConfig.mk:689:MTK_AB_OTA_UPDATER = yes
mediatek/common/device.mk:3643:ifeq ($(strip $(MTK_AB_OTA_UPDATER)), yes)
mediatek/common/BoardConfig.mk:228: ifeq ($(strip $(MTK_AB_OTA_UPDATER)), yes)
mediatek/mt6739/BoardConfig.mk:132:ifneq ($(strip $(MTK_AB_OTA_UPDATER)),yes)
mediatek/build/build/tools/ptgen/MT6739/ptgen.mk:71: MTK_AB_OTA_UPDATER=${MTK_AB_OTA_UPDATER} \
mediatek/build/build/tools/ptgen/MT6739/ptgen.pl:195: $ArgList{MTK_AB_OTA_UPDATER} = $ENV{MTK_AB_OTA_UPDATER};
mediatek/build/build/tools/ptgen/MT6739/ptgen.pl:260: if ($ArgList{MTK_AB_OTA_UPDATER} eq "yes")
mediatek/build/build/tools/ptgen/MT6739/ptgen.pl:271: if ($ArgList{MTK_AB_OTA_UPDATER} eq "yes")
mediatek/build/build/tools/ptgen/MT6739/ptgen.pl:768: if ($ArgList{MTK_AB_OTA_UPDATER} eq "yes")
mediatek/build/build/tools/partition/gen-partition.py:123: if os.getenv("MTK_AB_OTA_UPDATER") == "yes":
1、mediatek/common/device.mk
# A/B System updates
ifeq ($(strip $(MTK_AB_OTA_UPDATER)), yes)
# Squashfs config system文件格式使用squashfs,这是与ext4不同的格式,目前没用到
#BOARD_SYSTEMIMAGE_FILE_SYSTEM_TYPE := squashfs
#PRODUCT_PACKAGES += mksquashfs
#PRODUCT_PACKAGES += mksquashfsimage.sh
#PRODUCT_PACKAGES += libsquashfs_utils
#将recovery ramdisk放到boot.img文件内
BOARD_USES_RECOVERY_AS_BOOT := true
#不再编译recovery.img
TARGET_NO_RECOVERY := true
#打开AB_OTA_UPDATER宏,这个本身是google原生的打开AB的主控开
AB_OTA_UPDATER := true
# A/B OTA partitions AB升级中可升级的分区
AB_OTA_PARTITIONS := \
boot \
system \
lk \
preloader
#编译update_engine update_verifier brillo_update_payload模块
PRODUCT_PACKAGES += \
update_engine \
shflags \
delta_generator \
bsdiff \
brillo_update_payload \
update_engine_sideload \
update_verifier \
#这两个时debug的调试工具update_engine_client 可以在adblog中输出升级流程
#bootctl是boot_control模块调用的工具,可以通过命令调用接口
PRODUCT_PACKAGES_DEBUG += \
update_engine_client \
bootctl
# bootctrl HAL and HIDL 编译启动相关的bootctrl hal层
PRODUCT_PACKAGES += \
bootctrl.$(MTK_PLATFORM_DIR) \
android.hardware.boot@1.0-impl \
android.hardware.boot@1.0-service
PRODUCT_STATIC_BOOT_CONTROL_HAL := bootctrl.$(MTK_PLATFORM_DIR)
# A/B OTA dexopt package
PRODUCT_PACKAGES += otapreopt_script
# Install odex files into the other system image
#编译了system_other 并将odex文件放入
BOARD_USES_SYSTEM_OTHER_ODEX := true
# A/B OTA dexopt update_engine hookup
AB_OTA_POSTINSTALL_CONFIG += \
RUN_POSTINSTALL_system=true \
POSTINSTALL_PATH_system=system/bin/otapreopt_script \
FILESYSTEM_TYPE_system=ext4 \
POSTINSTALL_OPTIONAL_system=true
# Tell the system to enable copying odexes from other partition.
PRODUCT_PACKAGES += \
cppreopts.sh
PRODUCT_PROPERTY_OVERRIDES += \
ro.cp_system_other_odex=1
DEVICE_MANIFEST_FILE += device/mediatek/common/project_manifest/manifest_boot.xml
endif
#下面一个单独的判断,定义是否将rootfs放入system,
ifneq ($(strip $(SYSTEM_AS_ROOT)), no)
BOARD_BUILD_SYSTEM_ROOT_IMAGE := true
endif
2、mediatek/common/BoardConfig.mk
这部分的修改与odex化的编译有关,以下时相关的资料
开odex优化首次开机速度,是牺牲空间换取时间的做法,仅限于空间足够的设备。开了odex之后,在编译的时候,整个system image就会被预先优化。由于在启动时不再需要进行app的dex文件进行优化(dex2oat操作)从而提升其启动速度。
关于odex,有几个下面几个宏开关:
1、WITH_DEXPREOPT
这个开关在6.0 USER版本上是默认开启的,意思就是USER版本要开odex预编译。会导致system image中的所有东西都被提前优化(pre-optimized)。这可能导致system image非常大。
那么问题就来了,既然 WITH_DEXPREOPT := true 默认开启,那么为什么首次启动依然耗时很长呢?这个就和第二个宏开关——DONT_DEXPREOPT_PREBUILTS有关了。
2、DONT_DEXPREOPT_PREBUILTS
如果我们不想把prebuilts目录中的第三方应用进行预先优化(这些应用在他们的Android.mk文件中有include$(BUILD_PREBUILT) ),而是希望这些app通过playstore 或者app提供商进行升级,那么我们可以打开这个宏开关。
事实上,6.0上面,这个宏开关也是默认开启的。我们全局搜索一下“(BUILD_PREBUILT) ”会发现很多结果,这也就是为什么默认odex都开了,为什么开机并没有觉得快的原因了。
因此我们在做odex优化的时候,都会关闭DONT_DEXPREOPT_PREBUILTS,然后重新给我们预置的App添加 LOCAL_DEX_PREOPT :=false 让它们不进行预编译,这样也就能节省一些不必要的空间消耗。同时因为关闭了DONT_DEXPREOPT_PREBUILTS,很多可以随ROM升级的系统App也就进行了预编译,因此开机速度就有了明显的提高。
开AB后DONT_DEXPREOPT_PREBUILTS :=false 看到这里其实看不出什么,后面分析Makefile可以看出具体生成,不过暂时根据out下生成的system 和 system_other system下面是单独的APK 而system_other是单独的odex和vdex,
ifeq ($(BUILD_GMS),yes)
ifeq ($(strip $(MTK_AB_OTA_UPDATER)), yes)
DONT_DEXPREOPT_PREBUILTS := false
else
DONT_DEXPREOPT_PREBUILTS := true
endif
else

本文详细解析了A/B升级方案中系统Image的生成流程,包括开启宏开关后的make和makeotapackage过程,重点介绍了device和build下的关键修改,如AB升级宏控、系统分区调整及odex优化策略。

2023

被折叠的 条评论
为什么被折叠?



