二、A/B 升级update_engine分析-整体模块

    调试通了AB后确实想好好整理下这部分,其实与传统ota对比,我个人这样划分1、bootloder部分 2、kernel部分 3、framwork部分 4、update_engine核心 5、升级包的制作,而其中的大部分工作都来源于核心update_engine,在这里卡了很久,决定先从这里入手,按照framwork---->(binder机制)update_engine流程(设定对应的值给到boot_control)---->bootloder--->kernel---->ramdisk--->Android这样分析,本次先着重分析update_engine模块,我个人觉得对于目前分析问题,思路对于工作越来越重要,工作中问题形形色色,千奇百怪,有一套自己的方法处理起来才能得心应手。

    system/update_engine/的代码量比较多,首先我们先从Android.mk分析,这都是比较好的习惯,例如我们分析可执行文件和py文件从main方法入手一样,Android.mk代码比较多,先分割模块

总体模块

一、控制变量设定

二、编译参数设定和依赖定义

三、update_metadata-protos模块编译

四、libpayload_consumer模块编译

五、libupdate_engine_boot_control模块编译

六、libupdate_engine模块编译

七、libupdate_engine_android模块编译

八、update_engine模块编译

九、update_engine_sideload模块编译

十、update_engine_client模块编译

十一、libpayload_generator模块编译

十二、delta_generator模块编译

十三、Private and public keys for unittests.

十四、Sample images for unittests.

十五、update_engine.conf

十六、test_http_server

十七、test_subprocess

十八、update_engine_unittests

十九、Update payload signing public key.

二十、Brillo update payload generation script

 

看起来是挺多的,20个需要分析的,不过里面有部分并不会用到,下面我们开始挖坑分析

 

一、控制变量设定

 

# Default values for the USE flags. Override these USE flags from your product
# by setting BRILLO_USE_* values. Note that we define local variables like
# local_use_* to prevent leaking our default setting for other packages.
#USE标志的默认值。 覆盖产品中的这些USE标志
#通过设置BRILLO_USE_ *值。 请注意,我们定义了局部变量,例如
#local_use_ *以防止泄漏其他软件包的默认设置
local_use_binder := $(if $(BRILLO_USE_BINDER),$(BRILLO_USE_BINDER),1)
local_use_hwid_override := \
    $(if $(BRILLO_USE_HWID_OVERRIDE),$(BRILLO_USE_HWID_OVERRIDE),0)
local_use_mtd := $(if $(BRILLO_USE_MTD),$(BRILLO_USE_MTD),0)
local_use_chrome_network_proxy := 0
local_use_chrome_kiosk_app := 0

# IoT devices use Omaha for updates.
local_use_omaha := $(if $(filter true,$(PRODUCT_IOT)),1,0)
    
#log for local_use_*  这里是我加的打印,变量不清楚就打印出来看
#system/update_engine/Android.mk:35: warning: "local_use_binder = 1"
#system/update_engine/Android.mk:36: warning: "local_use_hwid_override = 0"
#system/update_engine/Android.mk:37: warning: "local_use_mtd = 0"
#system/update_engine/Android.mk:38: warning: "local_use_chrome_network_proxy = 0"
#system/update_engine/Android.mk:39: warning: "local_use_chrome_kiosk_app = 0"
#system/update_engine/Android.mk:46: warning: "local_use_omaha = 0"
    
$(warning "local_use_binder = $(local_use_binder)")  
$(warning "local_use_hwid_override = $(local_use_hwid_override)")
$(warning "local_use_mtd = $(local_use_mtd)")
$(warning "local_use_chrome_network_proxy = $(local_use_chrome_network_proxy)")
$(warning "local_use_chrome_kiosk_app = $(local_use_chrome_kiosk_app)")
$(warning "local_use_omaha = $(local_use_omaha)")

这些变量定义好,用于下面各模块的编译控制

local_use_binder = 1

local_use_hwid_override = 0

local_use_mtd = 0

local_use_chrome_network_proxy = 0

local_use_chrome_kiosk_app = 0

local_use_omaha = 0

二、编译参数设定和依赖定义

 

#定义一些编译的规则
ue_common_cflags := \
    -DUSE_BINDER=$(local_use_binder) \
    -DUSE_CHROME_NETWORK_PROXY=$(local_use_chrome_network_proxy) \
    -DUSE_CHROME_KIOSK_APP=$(local_use_chrome_kiosk_app) \
    -DUSE_HWID_OVERRIDE=$(local_use_hwid_override) \
    -DUSE_MTD=$(local_use_mtd) \
    -DUSE_OMAHA=$(local_use_omaha) \
    -D_FILE_OFFSET_BITS=64 \
    -D_POSIX_C_SOURCE=199309L \
    -Wa,--noexecstack \
    -Wall \
    -Werror \
    -Wextra \
    -Wformat=2 \
    -Wno-psabi \
    -Wno-unused-parameter \
    -ffunction-sections \
    -fstack-protector-strong \
    -fvisibility=hidden
ue_common_cppflags := \
    -Wnon-virtual-dtor \
    -fno-strict-aliasing
ue_common_ldflags := \
    -Wl,--gc-sections
#定义依赖
#c文件依赖
ue_common_c_includes := \
    $(LOCAL_PATH)/client_library/include \
    system
#动态库依赖
ue_common_shared_libraries := \
    libbrillo-stream \
    libbrillo \
    libchrome
#静态库依赖
ue_common_static_libraries := \
    libgtest_prod \

三、update_metadata-protos模块编译

# update_metadata-protos (type: static_library)
# ========================================================
# Protobufs.
ue_update_metadata_protos_exported_static_libraries := \
    update_metadata-protos
ue_update_metadata_protos_exported_shared_libraries := \
    libprotobuf-cpp-lite

ue_update_metadata_protos_src_files := \
    update_metadata.proto

# Build for the host.编译host静态库
include $(CLEAR_VARS)
LOCAL_MODULE := update_metadata-protos
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_IS_HOST_MODULE := true
generated_sources_dir := $(call local-generated-sources-dir)
LOCAL_EXPORT_C_INCLUDE_DIRS := $(generated_sources_dir)/proto/system
LOCAL_SRC_FILES := $(ue_update_metadata_protos_src_files)
LOCAL_CFLAGS := -Wall -Werror
include $(BUILD_HOST_STATIC_LIBRARY)

# Build for the target.编译target静态库
include $(CLEAR_VARS)
LOCAL_MODULE := update_metadata-protos
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
generated_sources_dir := $(call local-generated-sources-dir)
LOCAL_EXPORT_C_INCLUDE_DIRS := $(generated_sources_dir)/proto/system
LOCAL_SRC_FILES := $(ue_update_metadata_protos_src_files)
LOCAL_CFLAGS := -Wall -Werror
include $(BUILD_STATIC_LIBRARY)

定义静态库update_metadata-protos,分别指向host和target环境

protobuf是google团队开发的用于高效存储和读取结构化数据的工具。什么是结构化数据呢,正如字面上表达的,就是带有一定结构的数据。比如电话簿上有很多记录数据,每条记录包含姓名、ID、邮件、电话等,这种结构重复出现。

xml、json也可以用来存储此类结构化数据,但是使用protobuf表示的数据能更加高效,并且将数据压缩得更小,大约是json格式的1/10,xml格式的1/20。

四、libpayload_consumer模块编译

# libpayload_consumer (type: static_library)
# ========================================================
# The payload application component and common dependencies.
# payload应用程序组件和通用依赖项。
ue_libpayload_consumer_exported_static_libraries := \
    #包含了update_metadata-protos 所以先编译update_metadata-protos静态库,再编译libpayload_consumer
    update_metadata-protos \
    libxz \
    libbz \
    libbspatch \
    libbrotli \
    libpuffpatch \
    $(ue_update_metadata_protos_exported_static_libraries)
ue_libpayload_consumer_exported_shared_libraries := \
    libcrypto \
    $(ue_update_metadata_protos_exported_shared_libraries)

ue_libpayload_consumer_src_files := \
    common/action_processor.cc \
    common/boot_control_stub.cc \
    common/clock.cc \
    common/constants.cc \
    common/cpu_limiter.cc \
    common/error_code_utils.cc \
    common/file_fetcher.cc \
    common/hash_calculator.cc \
    common/http_common.cc \
    common/http_fetcher.cc \
    common/hwid_override.cc \
    common/multi_range_http_fetcher.cc \
    common/platform_constants_android.cc \
    common/prefs.cc \
    common/subprocess.cc \
    common/terminator.cc \
    common/utils.cc \
    payload_consumer/bzip_extent_writer.cc \
    payload_consumer/cached_file_descriptor.cc \
    payload_consumer/delta_performer.cc \
    payload_consumer/download_action.cc \
    payload_consumer/extent_reader.cc \
    payload_consumer/extent_writer.cc \
    payload_consumer/file_descriptor.cc \
    payload_consumer/file_descriptor_utils.cc \
    payload_consumer/file_writer.cc \
    payload_consumer/filesystem_verifier_action.cc \
    payload_consumer/install_plan.cc \
    payload_consumer/mount_history.cc \
    payload_consumer/payload_constants.cc \
    payload_consumer/payload_metadata.cc \
    payload_consumer/payload_verifier.cc \
    payload_consumer/postinstall_runner_action.cc \
    payload_consumer/xz_extent_writer.cc

ifeq ($(HOST_OS),linux)
# Build for the host.
include $(CLEAR_VARS)
LOCAL_MODULE := libpayload_consumer
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes)
LOCAL_STATIC_LIBRARIES := \
    update_metadata-protos \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries) \
    $(ue_update_metadata_protos_exported_static_libraries)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_consumer_exported_shared_libraries) \
    $(ue_update_metadata_protos_exported_shared_libraries)
LOCAL_SRC_FILES := $(ue_libpayload_consumer_src_files)
include $(BUILD_HOST_STATIC_LIBRARY)
endif  # HOST_OS == linux

# Build for the target.
include $(CLEAR_VARS)
LOCAL_MODULE := libpayload_consumer
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes)
LOCAL_STATIC_LIBRARIES := \
    update_metadata-protos \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries:-host=) \
    $(ue_update_metadata_protos_exported_static_libraries)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_consumer_exported_shared_libraries:-host=) \
    $(ue_update_metadata_protos_exported_shared_libraries)
LOCAL_SRC_FILES := $(ue_libpayload_consumer_src_files)
include $(BUILD_STATIC_LIBRARY)

定义静态库libpayload_consumer,分别指向host和target环境

五、libupdate_engine_boot_control模块编译

# libupdate_engine_boot_control (type: static_library)
# ========================================================
# A BootControl class implementation using Android's HIDL boot_control HAL.
# 使用Android的HIDL boot_control HAL的BootControl类实现。
ue_libupdate_engine_boot_control_exported_static_libraries := \
    update_metadata-protos \
    $(ue_update_metadata_protos_exported_static_libraries)

ue_libupdate_engine_boot_control_exported_shared_libraries := \
    libhwbinder \
    libhidlbase \
    libutils \
    android.hardware.boot@1.0 \
    $(ue_update_metadata_protos_exported_shared_libraries)

include $(CLEAR_VARS)
LOCAL_MODULE := libupdate_engine_boot_control
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes) \
    bootable/recovery
LOCAL_STATIC_LIBRARIES := \
    $(ue_common_static_libraries) \
    $(ue_libupdate_engine_boot_control_exported_static_libraries)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libupdate_engine_boot_control_exported_shared_libraries)
LOCAL_SRC_FILES := \
    boot_control_android.cc
include $(BUILD_STATIC_LIBRARY)

编译libupdate_engine_boot_control静态库,实现了hardware HAL 层定义的boot_control相关的接口,升级执行完需要设定slot a 和slot b两套系统的一些参数,判定如何启动

六、libupdate_engine模块编译

#根据我们之前local_use_omaha = 0 不会再编译libupdate_engine静态库
#而是编译libupdate_engine_android模块
ifeq ($(local_use_omaha),1)
编译libupdate_engine静态库

# libupdate_engine (type: static_library)
编译libupdate_engine_androi静态库

endif  # local_use_omaha == 1

 

七、libupdate_engine_android模块编译

# libupdate_engine_android (type: static_library)
# ========================================================
# The main daemon static_library used in Android (non-Brillo). This only has a
# loop to apply payloads provided by the upper layer via a Binder interface.
ue_libupdate_engine_android_exported_static_libraries := \
    libpayload_consumer \
    libfs_mgr \
    libbase \
    liblog \
    $(ue_libpayload_consumer_exported_static_libraries) \
    libupdate_engine_boot_control \
    $(ue_libupdate_engine_boot_control_exported_static_libraries)
ue_libupdate_engine_android_exported_shared_libraries := \
    $(ue_libpayload_consumer_exported_shared_libraries) \
    $(ue_libupdate_engine_boot_control_exported_shared_libraries) \
    libandroid_net \
    libbinder \
    libbinderwrapper \
    libbrillo-binder \
    libcutils \
    libcurl \
    libmetricslogger \
    libssl \
    libutils

include $(CLEAR_VARS)
LOCAL_MODULE := libupdate_engine_android
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes) \
    bootable/recovery
#TODO(deymo): Remove external/cros/system_api/dbus once the strings are moved
# out of the DBus interface.
LOCAL_C_INCLUDES += \
    external/cros/system_api/dbus
LOCAL_STATIC_LIBRARIES := \
    $(ue_common_static_libraries) \
    $(ue_libupdate_engine_android_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES += \
    $(ue_common_shared_libraries) \
    $(ue_libupdate_engine_android_exported_shared_libraries:-host=)
LOCAL_AIDL_INCLUDES := $(LOCAL_PATH)/binder_bindings
LOCAL_SRC_FILES += \
    binder_bindings/android/os/IUpdateEngine.aidl \
    binder_bindings/android/os/IUpdateEngineCallback.aidl \
    binder_service_android.cc \
    certificate_checker.cc \
    daemon.cc \
    daemon_state_android.cc \
    hardware_android.cc \
    libcurl_http_fetcher.cc \
    metrics_reporter_android.cc \
    metrics_utils.cc \
    network_selector_android.cc \
    proxy_resolver.cc \
    update_attempter_android.cc \
    update_status_utils.cc \
    utils_android.cc
include $(BUILD_STATIC_LIBRARY)

编译libupdate_engine_android静态库

八、update_engine模块编译

# update_engine (type: executable)
# ========================================================
# update_engine daemon.  update_engine守护程序
include $(CLEAR_VARS)
LOCAL_MODULE := update_engine
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_REQUIRED_MODULES := \
    cacerts_google
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries)
LOCAL_STATIC_LIBRARIES := \
    $(ue_common_static_libraries)
LOCAL_SRC_FILES := \
    main.cc
#根据local_use_omaha判断所需的静态库依赖
ifeq ($(local_use_omaha),1)
LOCAL_C_INCLUDES += \
    $(ue_libupdate_engine_exported_c_includes)
LOCAL_STATIC_LIBRARIES += \
    libupdate_engine \
    $(ue_libupdate_engine_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES += \
    $(ue_libupdate_engine_exported_shared_libraries:-host=)
else  # local_use_omaha == 1
#依赖libupdate_engine_android
LOCAL_STATIC_LIBRARIES += \
    libupdate_engine_android \
    $(ue_libupdate_engine_android_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES += \
    $(ue_libupdate_engine_android_exported_shared_libraries:-host=)
endif  # local_use_omaha == 1

LOCAL_INIT_RC := update_engine.rc
include $(BUILD_EXECUTABLE)

编译可执行文件update_engine,所需静态库依赖是libupdate_engine_android

九、update_engine_sideload模块编译

# update_engine_sideload (type: executable)
# ========================================================
# A static binary equivalent to update_engine daemon that installs an update
# from a local file directly instead of running in the background.
#一个等同于update_engine守护程序的静态二进制文件,用于安装更新
#直接从本地文件而不是在后台运行。
include $(CLEAR_VARS)
LOCAL_MODULE := update_engine_sideload
LOCAL_FORCE_STATIC_EXECUTABLE := true
LOCAL_MODULE_PATH := $(TARGET_RECOVERY_ROOT_OUT)/sbin
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := \
    $(ue_common_cflags) \
    -D_UE_SIDELOAD
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes) \
    bootable/recovery
#TODO(deymo): Remove external/cros/system_api/dbus once the strings are moved
# out of the DBus interface.
LOCAL_C_INCLUDES += \
    external/cros/system_api/dbus
LOCAL_SRC_FILES := \
    boot_control_recovery.cc \
    hardware_android.cc \
    metrics_reporter_stub.cc \
    metrics_utils.cc \
    network_selector_stub.cc \
    proxy_resolver.cc \
    sideload_main.cc \
    update_attempter_android.cc \
    update_status_utils.cc \
    utils_android.cc
LOCAL_STATIC_LIBRARIES := \
    libfs_mgr \
    libbase \
    liblog \
    #静态库依赖libpayload_consumer
    libpayload_consumer \
    update_metadata-protos \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries:-host=) \
    $(ue_update_metadata_protos_exported_static_libraries)
# We add the static versions of the shared libraries since we are forcing this
# binary to be a static binary, so we also need to include all the static
# library dependencies of these static libraries.
LOCAL_STATIC_LIBRARIES += \
    $(ue_common_shared_libraries) \
    libbase \
    liblog \
    $(ue_libpayload_consumer_exported_shared_libraries:-host=) \
    $(ue_update_metadata_protos_exported_shared_libraries) \
    libevent \
    libmodpb64 \
    libgtest_prod
#判断PRODUCT_STATIC_BOOT_CONTROL_HAL是否为空
ifeq ($(strip $(PRODUCT_STATIC_BOOT_CONTROL_HAL)),)
# No static boot_control HAL defined, so no sideload support. We use a fake
# boot_control HAL to allow compiling update_engine_sideload for test purposes.
ifeq ($(strip $(AB_OTA_UPDATER)),true)
#如果PRODUCT_STATIC_BOOT_CONTROL_HAL为空而AB_OTA_UPDATER不为空,会在编译报出warning,因为
两个宏控不同步,所以不支持update sideload
$(warning No PRODUCT_STATIC_BOOT_CONTROL_HAL configured but AB_OTA_UPDATER is \
true, no update sideload support.)
endif  # AB_OTA_UPDATER == true
LOCAL_SRC_FILES += \
    boot_control_recovery_stub.cc
else  # PRODUCT_STATIC_BOOT_CONTROL_HAL != ""
#如果PRODUCT_STATIC_BOOT_CONTROL_HAL不为空,指定静态库依赖PRODUCT_STATIC_BOOT_CONTROL_HAL
LOCAL_STATIC_LIBRARIES += \
    $(PRODUCT_STATIC_BOOT_CONTROL_HAL)
endif  # PRODUCT_STATIC_BOOT_CONTROL_HAL != ""

include $(BUILD_EXECUTABLE)

编译update_engine_sideload可执行程序,根据这个名字显然是跟之前recvoery下的本地升级类似

LOCAL_MODULE := update_engine_sideload

LOCAL_FORCE_STATIC_EXECUTABLE := true

LOCAL_MODULE_PATH := $(TARGET_RECOVERY_ROOT_OUT)/sbin

定义编译可执行程序的名称为update_engine_sideload,位置在recovery/sbin,因为recovery下面使用不到update_engine守护进程,所以这里定义了一个类似的update_engine_sideload,同时该可执行程序需要依赖静态库PRODUCT_STATIC_BOOT_CONTROL_HAL

开启AB升级后,该宏控是有值的device/mediatek/common/device.mk:3681:PRODUCT_STATIC_BOOT_CONTROL_HAL := bootctrl.$(MTK_PLATFORM_DIR)

十、libupdate_engine_client模块编译

 libupdate_engine_client (type: shared_library)
# ========================================================
include $(CLEAR_VARS)
LOCAL_MODULE := libupdate_engine_client
LOCAL_CFLAGS := \
    -Wall \
    -Werror \
    -Wno-unused-parameter \
    -DUSE_BINDER=$(local_use_binder)
LOCAL_CPP_EXTENSION := .cc
# TODO(deymo): Remove "external/cros/system_api/dbus" when dbus is not used.
LOCAL_C_INCLUDES := \
    $(LOCAL_PATH)/client_library/include \
    external/cros/system_api/dbus \
    system
LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/client_library/include
LOCAL_SHARED_LIBRARIES := \
    libchrome \
    libbrillo
LOCAL_SRC_FILES := \
    client_library/client.cc \
    update_status_utils.cc

# We only support binder IPC mechanism in Android.
ifeq ($(local_use_binder),1)
LOCAL_AIDL_INCLUDES := $(LOCAL_PATH)/binder_bindings
LOCAL_SHARED_LIBRARIES += \
    libbinder \
    libbrillo-binder \
    libutils
LOCAL_SRC_FILES += \
    binder_bindings/android/brillo/IUpdateEngine.aidl \
    binder_bindings/android/brillo/IUpdateEngineStatusCallback.aidl \
    client_library/client_binder.cc \
    parcelable_update_engine_status.cc
endif  # local_use_binder == 1

include $(BUILD_SHARED_LIBRARY)

编译libupdate_engine_client共享库

十一、update_engine_client模块编译

# update_engine_client (type: executable)
# ========================================================
# update_engine console client. update_engine控制台客户端
include $(CLEAR_VARS)
LOCAL_MODULE := update_engine_client
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_SHARED_LIBRARIES := $(ue_common_shared_libraries)
LOCAL_STATIC_LIBRARIES := $(ue_common_static_libraries)
ifeq ($(local_use_omaha),1)
LOCAL_SHARED_LIBRARIES += \
    libupdate_engine_client
LOCAL_SRC_FILES := \
    update_engine_client.cc \
    common/error_code_utils.cc \
    omaha_utils.cc
else  # local_use_omaha == 1
#TODO(deymo): Remove external/cros/system_api/dbus once the strings are moved
# out of the DBus interface.我们关注的代码
LOCAL_C_INCLUDES += \
    external/cros/system_api/dbus
LOCAL_SHARED_LIBRARIES += \
    libbinder \
    libbinderwrapper \
    libbrillo-binder \
    libutils
LOCAL_AIDL_INCLUDES := $(LOCAL_PATH)/binder_bindings
LOCAL_SRC_FILES := \
    binder_bindings/android/os/IUpdateEngine.aidl \
    binder_bindings/android/os/IUpdateEngineCallback.aidl \
    common/error_code_utils.cc \
    update_engine_client_android.cc \
    update_status_utils.cc
endif  # local_use_omaha == 1
include $(BUILD_EXECUTABLE)

编译update_engine_client可执行文件,这个在ab中其实是用于测试的,开启后可以在adblog中输出升级的log,

这里其实有个疑问,编译了libupdate_engine_client,但是实际只有iot会用到这个共享库,普通Android并没有依赖这个共享库,所以为什么不在libupdate_engine_client编译的时候也加入local_use_omaha的控制开关呢

十二、libpayload_generator模块编译

# libpayload_generator (type: static_library)
# ========================================================
# server-side code. This is used for delta_generator and unittests but not
# for any client code.
#服务器端代码。这是用于delta_generator和单元测试,但不对于任何客户端代码。
ue_libpayload_generator_exported_static_libraries := \
    libbsdiff \
    libdivsufsort \
    libdivsufsort64 \
    libbrotli \
    liblzma \
    libpayload_consumer \
    libpuffdiff \
    libz \
    update_metadata-protos \
    $(ue_libpayload_consumer_exported_static_libraries) \
    $(ue_update_metadata_protos_exported_static_libraries)
ue_libpayload_generator_exported_shared_libraries := \
    libext2fs \
    $(ue_libpayload_consumer_exported_shared_libraries) \
    $(ue_update_metadata_protos_exported_shared_libraries)

ue_libpayload_generator_src_files := \
    payload_generator/ab_generator.cc \
    payload_generator/annotated_operation.cc \
    payload_generator/blob_file_writer.cc \
    payload_generator/block_mapping.cc \
    payload_generator/bzip.cc \
    payload_generator/cycle_breaker.cc \
    payload_generator/deflate_utils.cc \
    payload_generator/delta_diff_generator.cc \
    payload_generator/delta_diff_utils.cc \
    payload_generator/ext2_filesystem.cc \
    payload_generator/extent_ranges.cc \
    payload_generator/extent_utils.cc \
    payload_generator/full_update_generator.cc \
    payload_generator/graph_types.cc \
    payload_generator/graph_utils.cc \
    payload_generator/inplace_generator.cc \
    payload_generator/mapfile_filesystem.cc \
    payload_generator/payload_file.cc \
    payload_generator/payload_generation_config.cc \
    payload_generator/payload_signer.cc \
    payload_generator/raw_filesystem.cc \
    payload_generator/squashfs_filesystem.cc \
    payload_generator/tarjan.cc \
    payload_generator/topological_sort.cc \
    payload_generator/xz_android.cc

ifeq ($(HOST_OS),linux)
# Build for the host.
include $(CLEAR_VARS)
LOCAL_MODULE := libpayload_generator
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_STATIC_LIBRARIES := \
    libbsdiff \
    libdivsufsort \
    libdivsufsort64 \
    liblzma \
    libpayload_consumer \
    libpuffdiff \
    update_metadata-protos \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries) \
    $(ue_update_metadata_protos_exported_static_libraries)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_generator_exported_shared_libraries) \
    $(ue_libpayload_consumer_exported_shared_libraries) \
    $(ue_update_metadata_protos_exported_shared_libraries)
LOCAL_SRC_FILES := $(ue_libpayload_generator_src_files)
include $(BUILD_HOST_STATIC_LIBRARY)
endif  # HOST_OS == linux

# Build for the target.
include $(CLEAR_VARS)
LOCAL_MODULE := libpayload_generator
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_STATIC_LIBRARIES := \
    libbsdiff \
    libdivsufsort \
    libdivsufsort64 \
    libpayload_consumer \
    update_metadata-protos \
    liblzma \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries:-host=) \
    $(ue_update_metadata_protos_exported_static_libraries)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_generator_exported_shared_libraries:-host=) \
    $(ue_libpayload_consumer_exported_shared_libraries:-host=) \
    $(ue_update_metadata_protos_exported_shared_libraries)
LOCAL_SRC_FILES := $(ue_libpayload_generator_src_files)
include $(BUILD_STATIC_LIBRARY)

编译libpayload_generator静态库,分别用于host和target环境

十三、delta_generator模块编译

# delta_generator (type: executable)
# ========================================================
# server-side delta generator.服务器端增量生成器
ue_delta_generator_src_files := \
    payload_generator/generate_delta_main.cc

ifeq ($(HOST_OS),linux)
# Build for the host.
include $(CLEAR_VARS)
LOCAL_MODULE := delta_generator
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_STATIC_LIBRARIES := \
    libpayload_consumer \
    libpayload_generator \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries) \
    $(ue_libpayload_generator_exported_static_libraries)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_consumer_exported_shared_libraries) \
    $(ue_libpayload_generator_exported_shared_libraries)
LOCAL_SRC_FILES := $(ue_delta_generator_src_files)
include $(BUILD_HOST_EXECUTABLE)
endif  # HOST_OS == linux

# Build for the target.
include $(CLEAR_VARS)
LOCAL_MODULE := ue_unittest_delta_generator
LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests
LOCAL_MODULE_STEM := delta_generator
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_STATIC_LIBRARIES := \
    libpayload_consumer \
    libpayload_generator \
    $(ue_common_static_libraries) \
    $(ue_libpayload_consumer_exported_static_libraries:-host=) \
    $(ue_libpayload_generator_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_consumer_exported_shared_libraries:-host=) \
    $(ue_libpayload_generator_exported_shared_libraries:-host=)
LOCAL_SRC_FILES := $(ue_delta_generator_src_files)
include $(BUILD_EXECUTABLE)

编译delta_generator可执行程序,分别用于host 和 target 环境,这个文件在做ab升级包的时候会用到

十四、Private and public keys for unittests.

# Private and public keys for unittests.
# ========================================================
# Generate a module that installs a prebuilt private key and a module that
# installs a public key generated from the private key.
# 生成安装预建私钥的模块和安装从私钥生成的公钥的模块。
# $(1): The path to the private key in pem format.
define ue-unittest-keys
    $(eval include $(CLEAR_VARS)) \
    $(eval LOCAL_MODULE := ue_$(1).pem) \
    $(eval LOCAL_MODULE_CLASS := ETC) \
    $(eval LOCAL_SRC_FILES := $(1).pem) \
    $(eval LOCAL_MODULE_PATH := \
        $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests) \
    $(eval LOCAL_MODULE_STEM := $(1).pem) \
    $(eval include $(BUILD_PREBUILT)) \
    \
    $(eval include $(CLEAR_VARS)) \
    $(eval LOCAL_MODULE := ue_$(1).pub.pem) \
    $(eval LOCAL_MODULE_CLASS := ETC) \
    $(eval LOCAL_MODULE_PATH := \
        $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests) \
    $(eval LOCAL_MODULE_STEM := $(1).pub.pem) \
    $(eval include $(BUILD_SYSTEM)/base_rules.mk) \
    $(eval $(LOCAL_BUILT_MODULE) : $(LOCAL_PATH)/$(1).pem ; \
        openssl rsa -in $$< -pubout -out $$@)
endef

$(call ue-unittest-keys,unittest_key)
$(call ue-unittest-keys,unittest_key2)

十五、Sample images for unittests.

# Sample images for unittests.
# ========================================================
# Generate a prebuilt module that installs a sample image from the compressed
# sample_images.tar.bz2 file used by the unittests.
#生成一个预构建模块,该模块从单元测试使用的压缩sample_images.tar.bz2文件中安装示例图像。
# $(1): The filename in the sample_images.tar.bz2
define ue-unittest-sample-image
    $(eval include $(CLEAR_VARS)) \
    $(eval LOCAL_MODULE := ue_unittest_$(1)) \
    $(eval LOCAL_MODULE_CLASS := EXECUTABLES) \
    $(eval LOCAL_MODULE_PATH := \
        $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests/gen) \
    $(eval LOCAL_MODULE_STEM := $(1)) \
    $(eval include $(BUILD_SYSTEM)/base_rules.mk) \
    $(eval $(LOCAL_BUILT_MODULE) : \
        $(LOCAL_PATH)/sample_images/sample_images.tar.bz2 ; \
        tar -jxf $$< -C $$(dir $$@) $$(notdir $$@) && touch $$@)
endef

$(call ue-unittest-sample-image,disk_ext2_1k.img)
$(call ue-unittest-sample-image,disk_ext2_4k.img)
$(call ue-unittest-sample-image,disk_ext2_4k_empty.img)
$(call ue-unittest-sample-image,disk_ext2_unittest.img)

 

十六、update_engine.conf

# update_engine.conf
# ========================================================
include $(CLEAR_VARS)
LOCAL_MODULE := ue_unittest_update_engine.conf
LOCAL_MODULE_CLASS := ETC
LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests
LOCAL_MODULE_STEM := update_engine.conf
LOCAL_SRC_FILES := update_engine.conf
include $(BUILD_PREBUILT)

拷贝ue_unittest_update_engine.conf到out下面

十七、test_http_server

# test_http_server (type: executable)
# ========================================================
# Test HTTP Server.
include $(CLEAR_VARS)
LOCAL_MODULE := test_http_server
LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_SHARED_LIBRARIES := $(ue_common_shared_libraries)
LOCAL_STATIC_LIBRARIES := $(ue_common_static_libraries)
LOCAL_SRC_FILES := \
    common/http_common.cc \
    test_http_server.cc
include $(BUILD_EXECUTABLE)

测试模块,暂时不做分析

十八、test_subprocess

# test_subprocess (type: executable)
# ========================================================
# Test helper subprocess program.
include $(CLEAR_VARS)
LOCAL_MODULE := test_subprocess
LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_NATIVE_TESTS)/update_engine_unittests
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := $(ue_common_c_includes)
LOCAL_SHARED_LIBRARIES := $(ue_common_shared_libraries)
LOCAL_STATIC_LIBRARIES := $(ue_common_static_libraries)
LOCAL_SRC_FILES := test_subprocess.cc
include $(BUILD_EXECUTABLE)

测试模块,暂时不做分析

十九、update_engine_unittests

# update_engine_unittests (type: executable)
# ========================================================
# Main unittest file.主单元测试文件
include $(CLEAR_VARS)
LOCAL_MODULE := update_engine_unittests
LOCAL_REQUIRED_MODULES := \
    test_http_server \
    test_subprocess \
    ue_unittest_delta_generator \
    ue_unittest_disk_ext2_1k.img \
    ue_unittest_disk_ext2_4k.img \
    ue_unittest_disk_ext2_4k_empty.img \
    ue_unittest_disk_ext2_unittest.img \
    ue_unittest_key.pem \
    ue_unittest_key.pub.pem \
    ue_unittest_key2.pem \
    ue_unittest_key2.pub.pem \
    ue_unittest_update_engine.conf
LOCAL_CPP_EXTENSION := .cc
LOCAL_CFLAGS := $(ue_common_cflags)
LOCAL_CPPFLAGS := $(ue_common_cppflags)
LOCAL_LDFLAGS := $(ue_common_ldflags)
LOCAL_C_INCLUDES := \
    $(ue_common_c_includes) \
    $(ue_libupdate_engine_exported_c_includes)
LOCAL_STATIC_LIBRARIES := \
    libpayload_generator \
    libbrillo-test-helpers \
    libgmock \
    libchrome_test_helpers \
    $(ue_common_static_libraries) \
    $(ue_libpayload_generator_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES := \
    $(ue_common_shared_libraries) \
    $(ue_libpayload_generator_exported_shared_libraries:-host=)
LOCAL_SRC_FILES := \
    certificate_checker_unittest.cc \
    common/action_pipe_unittest.cc \
    common/action_processor_unittest.cc \
    common/action_unittest.cc \
    common/cpu_limiter_unittest.cc \
    common/fake_prefs.cc \
    common/file_fetcher_unittest.cc \
    common/hash_calculator_unittest.cc \
    common/http_fetcher_unittest.cc \
    common/hwid_override_unittest.cc \
    common/mock_http_fetcher.cc \
    common/prefs_unittest.cc \
    common/subprocess_unittest.cc \
    common/terminator_unittest.cc \
    common/test_utils.cc \
    common/utils_unittest.cc \
    payload_consumer/bzip_extent_writer_unittest.cc \
    payload_consumer/cached_file_descriptor_unittest.cc \
    payload_consumer/delta_performer_integration_test.cc \
    payload_consumer/delta_performer_unittest.cc \
    payload_consumer/extent_reader_unittest.cc \
    payload_consumer/extent_writer_unittest.cc \
    payload_consumer/fake_file_descriptor.cc \
    payload_consumer/file_descriptor_utils_unittest.cc \
    payload_consumer/file_writer_unittest.cc \
    payload_consumer/filesystem_verifier_action_unittest.cc \
    payload_consumer/postinstall_runner_action_unittest.cc \
    payload_consumer/xz_extent_writer_unittest.cc \
    payload_generator/ab_generator_unittest.cc \
    payload_generator/blob_file_writer_unittest.cc \
    payload_generator/block_mapping_unittest.cc \
    payload_generator/cycle_breaker_unittest.cc \
    payload_generator/deflate_utils_unittest.cc \
    payload_generator/delta_diff_utils_unittest.cc \
    payload_generator/ext2_filesystem_unittest.cc \
    payload_generator/extent_ranges_unittest.cc \
    payload_generator/extent_utils_unittest.cc \
    payload_generator/fake_filesystem.cc \
    payload_generator/full_update_generator_unittest.cc \
    payload_generator/graph_utils_unittest.cc \
    payload_generator/inplace_generator_unittest.cc \
    payload_generator/mapfile_filesystem_unittest.cc \
    payload_generator/payload_file_unittest.cc \
    payload_generator/payload_generation_config_unittest.cc \
    payload_generator/payload_signer_unittest.cc \
    payload_generator/squashfs_filesystem_unittest.cc \
    payload_generator/tarjan_unittest.cc \
    payload_generator/topological_sort_unittest.cc \
    payload_generator/zip_unittest.cc \
    proxy_resolver_unittest.cc \
    testrunner.cc
#iot 定义依赖
ifeq ($(local_use_omaha),1)
LOCAL_C_INCLUDES += \
    $(ue_libupdate_engine_exported_c_includes)
LOCAL_STATIC_LIBRARIES += \
    libupdate_engine \
    $(ue_libupdate_engine_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES += \
    $(ue_libupdate_engine_exported_shared_libraries:-host=)
LOCAL_SRC_FILES += \
    common_service_unittest.cc \
    fake_system_state.cc \
    image_properties_android_unittest.cc \
    metrics_reporter_omaha_unittest.cc \
    metrics_utils_unittest.cc \
    omaha_request_action_unittest.cc \
    omaha_request_params_unittest.cc \
    omaha_response_handler_action_unittest.cc \
    omaha_utils_unittest.cc \
    p2p_manager_unittest.cc \
    payload_consumer/download_action_unittest.cc \
    payload_state_unittest.cc \
    parcelable_update_engine_status_unittest.cc \
    update_attempter_unittest.cc \
    update_manager/android_things_policy_unittest.cc \
    update_manager/boxed_value_unittest.cc \
    update_manager/chromeos_policy.cc \
    update_manager/chromeos_policy_unittest.cc \
    update_manager/enterprise_device_policy_impl.cc \
    update_manager/evaluation_context_unittest.cc \
    update_manager/generic_variables_unittest.cc \
    update_manager/next_update_check_policy_impl_unittest.cc \
    update_manager/out_of_box_experience_policy_impl.cc \
    update_manager/policy_test_utils.cc \
    update_manager/prng_unittest.cc \
    update_manager/real_device_policy_provider_unittest.cc \
    update_manager/real_random_provider_unittest.cc \
    update_manager/real_system_provider_unittest.cc \
    update_manager/real_time_provider_unittest.cc \
    update_manager/real_updater_provider_unittest.cc \
    update_manager/umtest_utils.cc \
    update_manager/update_manager_unittest.cc \
    update_manager/variable_unittest.cc
else  # local_use_omaha == 1
#普通android定义依赖
LOCAL_STATIC_LIBRARIES += \
    libupdate_engine_android \
    $(ue_libupdate_engine_android_exported_static_libraries:-host=)
LOCAL_SHARED_LIBRARIES += \
    $(ue_libupdate_engine_android_exported_shared_libraries:-host=)
LOCAL_SRC_FILES += \
    update_attempter_android_unittest.cc
endif  # local_use_omaha == 1
include $(BUILD_NATIVE_TEST)

编译可执行程序update_engine_unittests

二十、Update payload signing public key.

# Update payload signing public key.
# ========================================================
ifeq ($(PRODUCT_IOT),true)
include $(CLEAR_VARS)
LOCAL_MODULE := brillo-update-payload-key
LOCAL_MODULE_CLASS := ETC
LOCAL_MODULE_PATH := $(TARGET_OUT_ETC)/update_engine
LOCAL_MODULE_STEM := update-payload-key.pub.pem
LOCAL_SRC_FILES := update_payload_key/brillo-update-payload-key.pub.pem
LOCAL_BUILT_MODULE_STEM := update_payload_key/brillo-update-payload-key.pub.pem
include $(BUILD_PREBUILT)
endif  # PRODUCT_IOT

这一段不做分析,ifeq ($(PRODUCT_IOT),true)就是local_use_omaha,IOT设备会把brillo公钥拷贝到$(TARGET_OUT_ETC)/update_engine下面

二一、Brillo update payload generation script

# Brillo update payload generation script
# ========================================================
ifeq ($(HOST_OS),linux)
include $(CLEAR_VARS)
LOCAL_SRC_FILES := scripts/brillo_update_payload
LOCAL_MODULE := brillo_update_payload
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_IS_HOST_MODULE := true
LOCAL_MODULE_TAGS := optional
LOCAL_REQUIRED_MODULES := \
    delta_generator \
    shflags \
    simg2img
include $(BUILD_PREBUILT)
endif  # HOST_OS == linux

编译复制脚本brillo_update_payload到host下面

 

模块汇总

以上基本上是update_engine所有编译出来的模块,下面我们做个汇总

一、静态库模块

update_metadata-protos                     指向host和target环境       不知道是个啥,要再详细了解下

 

libpayload_consumer                            指向host和target环境

依赖:update_metadata-protos

 

libupdate_engine_boot_control        指向target环境                    连接boot_control模块

 

libupdate_engine_android                  指向target环境

 

libpayload_generator                             指向host和target环境

二、可执行程序

update_engine                                         指向target环境                 服务端进程,也是我们要分析的重中之重

依赖:libupdate_engine_android

 

update_engine_sideload                      指向target环境                  recovery升级使用,最后再分析

 

update_engine_client                            指向target环境                  相当于一个调试模块,也是客户端进程的demo

 

delta_generator                                        指向host和target环境      制作差分包会使用到

依赖:libpayload_generator

 

update_engine_unittests                      指向target环境

依赖:libupdate_engine_android

 

三、预编译文件

update_engine.conf                                拷贝到target环境

 

brillo_update_payload                            拷贝到host环境                  制作差分包会使用到

 

 

看了这份文档,好像写了东西,又好像什么都没写,不过确实对我们需要关注的点有了更好的划分,这就是写的重要性,接下来将从update_engine_client update_engine开始分析,虽然client只是一个测试模块,不过我想按照先客户端再服务端进行分析。

 

 

 

 

  • 2
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
NOTE: > Executing update_desktop_database intercept ... NOTE: > Executing update_gtk_immodules_cache intercept ... NOTE: Exit code 1. Output: /home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/intercept_scripts-b51052418cd1de15aa19deeae9844eade47e1e2e32985d114ac9c6c1afe994aa/update_gtk_immodules_cache: line 15: /home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/rootfs/usr/lib64/gtk-3.0/3.0.0/immodules.cache: No such file or directory chown: cannot access '/home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/rootfs/usr/lib64/gtk-3.0/3.0.0/immodules.cache': No such file or directory ERROR: The postinstall intercept hook 'update_gtk_immodules_cache' failed, details in /home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/temp/log.do_rootfs NOTE: > Executing update_desktop_database intercept ... NOTE: > Executing update_gtk_immodules_cache intercept ... NOTE: Exit code 1. Output: /home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/intercept_scripts-b51052418cd1de15aa19deeae9844eade47e1e2e32985d114ac9c6c1afe994aa/update_gtk_immodules_cache: line 15: /home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/rootfs/usr/lib64/gtk-3.0/3.0.0/immodules.cache: No such file or directory chown: cannot access '/home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/rootfs/usr/lib64/gtk-3.0/3.0.0/immodules.cache': No such file or directory ERROR: The postinstall intercept hook 'update_gtk_immodules_cache' failed, details in /home/wu/g2l/build-niicl-nom-r001l/tmp/work/nom_r001l-niic-linux/core-image-weston/1.0-r0/temp/log.do_rootfs DEBUG: Python function do_rootfs finished如何解决
07-20

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值