Merge "Revert^2 "Remove libmdnssd"" into main
diff --git a/METADATA b/METADATA
deleted file mode 100644
index 44781a7..0000000
--- a/METADATA
+++ /dev/null
@@ -1,8 +0,0 @@
-third_party {
- license_note: "would be NOTICE save for GPL in:\n"
- " core/LINUX_KERNEL_COPYING\n"
- " tools/droiddoc/templates-pdk/assets/jquery-1.6.2.min.js\n"
- " tools/droiddoc/templates-pdk/assets/jquery-history.js\n"
- " tools/droiddoc/templates-pdk/assets/jquery-resizable.min.js"
- license_type: RESTRICTED
-}
diff --git a/core/Makefile b/core/Makefile
index 712719a..4900ac2 100644
--- a/core/Makefile
+++ b/core/Makefile
@@ -3406,12 +3406,12 @@
FULL_SYSTEMIMAGE_DEPS += $(INTERNAL_ROOT_FILES) $(INSTALLED_FILES_FILE_ROOT)
-# Returns a list of all the zip files from EXTRA_INSTALL_ZIPS whose install destination is
-# under $(1)
+# Returns a list of EXTRA_INSTALL_ZIPS trios whose primary file is contained within $(1)
+# The trios will contain the primary installed file : the directory to unzip the zip to : the zip
define relevant-extra-install-zips
$(strip $(foreach p,$(EXTRA_INSTALL_ZIPS), \
- $(if $(filter $(1)/%,$(call word-colon,1,$(p))/), \
- $(call word-colon,2,$(p)))))
+ $(if $(filter $(call word-colon,1,$(p)),$(1)), \
+ $(p))))
endef
# Writes a text file that contains all of the files that will be inside a partition.
@@ -3423,12 +3423,13 @@
# $(2): The partition's staging directory
# $(3): Files to include in the partition
define write-partition-file-list
-$(1): $$(HOST_OUT_EXECUTABLES)/extra_install_zips_file_list $(call relevant-extra-install-zips,$(2))
+$(1): PRIVATE_RELEVANT_EXTRA_INSTALL_ZIPS := $(call relevant-extra-install-zips,$(filter $(2)/%,$(3)))
+$(1): $$(HOST_OUT_EXECUTABLES)/extra_install_zips_file_list $$(foreach p,$$(PRIVATE_RELEVANT_EXTRA_INSTALL_ZIPS),$$(call word-colon,3,$$(p)))
@echo Writing $$@
rm -f $$@
echo -n > $$@
$$(foreach f,$(subst $(2)/,,$(filter $(2)/%,$(3))),echo "$$(f)" >> $$@$$(newline))
- $$(HOST_OUT_EXECUTABLES)/extra_install_zips_file_list $(2) $$(EXTRA_INSTALL_ZIPS) >> $$@
+ $$(HOST_OUT_EXECUTABLES)/extra_install_zips_file_list $(2) $$(PRIVATE_RELEVANT_EXTRA_INSTALL_ZIPS) >> $$@
endef
# -----------------------------------------------------------------
diff --git a/core/android_soong_config_vars.mk b/core/android_soong_config_vars.mk
index ed72fc3..c43081e 100644
--- a/core/android_soong_config_vars.mk
+++ b/core/android_soong_config_vars.mk
@@ -94,6 +94,7 @@
$(call add_soong_config_var_value,ANDROID,release_avf_enable_dice_changes,$(RELEASE_AVF_ENABLE_DICE_CHANGES))
$(call add_soong_config_var_value,ANDROID,release_avf_enable_llpvm_changes,$(RELEASE_AVF_ENABLE_LLPVM_CHANGES))
$(call add_soong_config_var_value,ANDROID,release_avf_enable_multi_tenant_microdroid_vm,$(RELEASE_AVF_ENABLE_MULTI_TENANT_MICRODROID_VM))
+$(call add_soong_config_var_value,ANDROID,release_avf_enable_network,$(RELEASE_AVF_ENABLE_NETWORK))
$(call add_soong_config_var_value,ANDROID,release_avf_enable_remote_attestation,$(RELEASE_AVF_ENABLE_REMOTE_ATTESTATION))
$(call add_soong_config_var_value,ANDROID,release_avf_enable_vendor_modules,$(RELEASE_AVF_ENABLE_VENDOR_MODULES))
$(call add_soong_config_var_value,ANDROID,release_avf_enable_virt_cpufreq,$(RELEASE_AVF_ENABLE_VIRT_CPUFREQ))
diff --git a/core/art_config.mk b/core/art_config.mk
index 196db4f..9e87a7b 100644
--- a/core/art_config.mk
+++ b/core/art_config.mk
@@ -22,17 +22,16 @@
# Create APEX_BOOT_JARS_EXCLUDED which is a list of jars to be removed from
# ApexBoorJars when built from mainline prebuilts.
-# soong variables indicate whether the prebuilt is enabled:
-# - $(m)_module/source_build for art and TOGGLEABLE_PREBUILT_MODULES
-# - ANDROID/module_build_from_source for other mainline modules
# Note that RELEASE_APEX_BOOT_JARS_PREBUILT_EXCLUDED_LIST is the list of module names
# and library names of jars that need to be removed. We have to keep separated list per
# release config due to possibility of different prebuilt content.
-APEX_BOOT_JARS_EXCLUDED :=
-$(foreach pair, $(RELEASE_APEX_BOOT_JARS_PREBUILT_EXCLUDED_LIST),\
- $(eval m := $(subst com.android.,,$(call word-colon,1,$(pair)))) \
- $(if $(call soong_config_get,$(m)_module,source_build), \
- $(if $(filter true,$(call soong_config_get,$(m)_module,source_build)),, \
- $(eval APEX_BOOT_JARS_EXCLUDED += $(pair))), \
- $(if $(filter true,$(call soong_config_get,ANDROID,module_build_from_source)),, \
- $(eval APEX_BOOT_JARS_EXCLUDED += $(pair)))))
+#
+# If a device has opted to not use google prebuilts (determined using
+# PRODUCT_BUILD_IGNORE_APEX_CONTRIBUTION_CONTENTS), then no jars need to be removed.
+# Example of products where PRODUCT_BUILD_IGNORE_APEX_CONTRIBUTION_CONTENTS is true are
+# 1. aosp devices (they do not use google apexes)
+# 2. hwasan devices (apex prebuilts are not compatible with these devices)
+# 3. coverage builds
+ifneq (true, $(PRODUCT_BUILD_IGNORE_APEX_CONTRIBUTION_CONTENTS))
+ APEX_BOOT_JARS_EXCLUDED += $(RELEASE_APEX_BOOT_JARS_PREBUILT_EXCLUDED_LIST)
+endif
diff --git a/core/envsetup.mk b/core/envsetup.mk
index 1c3a1b3..3271079 100644
--- a/core/envsetup.mk
+++ b/core/envsetup.mk
@@ -255,6 +255,7 @@
HOST_PREBUILT_ARCH := x86
# This is the standard way to name a directory containing prebuilt host
# objects. E.g., prebuilt/$(HOST_PREBUILT_TAG)/cc
+# This must match the logic in get_host_prebuilt_prefix in envsetup.sh
HOST_PREBUILT_TAG := $(BUILD_OS)-$(HOST_PREBUILT_ARCH)
# TARGET_COPY_OUT_* are all relative to the staging directory, ie PRODUCT_OUT.
diff --git a/core/main.mk b/core/main.mk
index d700fcb..62fa53d 100644
--- a/core/main.mk
+++ b/core/main.mk
@@ -276,7 +276,7 @@
# Include all of the makefiles in the system
#
-subdir_makefiles := $(SOONG_ANDROID_MK)
+subdir_makefiles := $(SOONG_OUT_DIR)/installs-$(TARGET_PRODUCT).mk $(SOONG_ANDROID_MK)
# Android.mk files are only used on Linux builds, Mac only supports Android.bp
ifeq ($(HOST_OS),linux)
subdir_makefiles += $(file <$(OUT_DIR)/.module_paths/Android.mk.list)
@@ -287,8 +287,6 @@
$(foreach mk,$(subdir_makefiles),$(info [$(call inc_and_print,subdir_makefiles_inc)/$(subdir_makefiles_total)] including $(mk) ...)$(eval include $(mk)))
-include $(SOONG_OUT_DIR)/installs-$(TARGET_PRODUCT).mk
-
# For an unbundled image, we can skip blueprint_tools because unbundled image
# aims to remove a large number framework projects from the manifest, the
# sources or dependencies for these tools may be missing from the tree.
diff --git a/core/release_config.mk b/core/release_config.mk
index 97c8dd3..5fe3d39 100644
--- a/core/release_config.mk
+++ b/core/release_config.mk
@@ -14,6 +14,16 @@
# -----------------------------------------------------------------
+# Determine which pass this is.
+# -----------------------------------------------------------------
+# On the first pass, we are asked for only PRODUCT_RELEASE_CONFIG_MAPS,
+# on the second pass, we are asked for whatever else is wanted.
+_final_product_config_pass:=
+ifneq (PRODUCT_RELEASE_CONFIG_MAPS,$(DUMP_MANY_VARS))
+ _final_product_config_pass:=true
+endif
+
+# -----------------------------------------------------------------
# Choose the flag files
# -----------------------------------------------------------------
# Release configs are defined in reflease_config_map files, which map
@@ -90,7 +100,7 @@
ifneq (,$(_must_protobuf))
ifeq (,$(_can_protobuf))
- # We must use protobuf, but we cannot use protobuf.
+ # We must use protobuf, but we cannot use protobuf.
$(error release config is a mixture of .scl and .textproto)
endif
endif
@@ -120,12 +130,22 @@
# Disable the build flag in release-config.
_args += --guard=false
endif
- _flags_file:=$(OUT_DIR)/soong/release-config/release_config-$(TARGET_PRODUCT)-$(TARGET_RELEASE).mk
- $(KATI_shell_no_rerun $(OUT_DIR)/release-config $(_args) >$(OUT_DIR)/release-config.out 2>&1 && touch -t 200001010000 $(OUT_DIR)/release-config.out $(_flags_file))
+ _flags_file:=$(OUT_DIR)/soong/release-config/release_config-$(TARGET_PRODUCT)-$(TARGET_RELEASE).vars
+ # release-config generates $(_flags_varmk)
+ _flags_varmk:=$(_flags_file:.vars=.varmk)
+ $(shell $(OUT_DIR)/release-config $(_args) >$(OUT_DIR)/release-config.out 2>&1 && touch -t 200001010000 $(_flags_varmk))
$(if $(filter-out 0,$(.SHELLSTATUS)),$(error release-config failed to run))
- # This will also set _all_release_configs for us.
- $(eval include $(OUT_DIR)/soong/release-config/release_config-$(TARGET_PRODUCT)-$(TARGET_RELEASE).mk)
- $(KATI_extra_file_deps $(OUT_DIR)/release-config $(config_map_files))
+ ifneq (,$(_final_product_config_pass))
+ # Save the final version of the config.
+ $(shell if ! cmp --quiet $(_flags_varmk) $(_flags_file); then cp $(_flags_varmk) $(_flags_file); fi)
+ # This will also set _all_release_configs and _used_files for us.
+ $(eval include $(_flags_file))
+ $(KATI_extra_file_deps $(OUT_DIR)/release-config $(protobuf_map_files) $(_flags_file))
+ else
+ # This is the first pass of product config.
+ $(eval include $(_flags_varmk))
+ endif
+ _used_files :=
ifeq (,$(_must_protobuf)$(RELEASE_BUILD_FLAGS_IN_PROTOBUF))
_use_protobuf :=
endif
@@ -238,7 +258,7 @@
# During pass 1 of product config, using a non-existent release config is not an error.
# We can safely assume that we are doing pass 1 if DUMP_MANY_VARS=="PRODUCT_RELEASE_CONFIG_MAPS".
-ifneq (PRODUCT_RELEASE_CONFIG_MAPS,$(DUMP_MANY_VARS))
+ifneq (,$(_final_product_config_pass))
ifeq ($(filter $(_all_release_configs), $(TARGET_RELEASE)),)
$(error No release config found for TARGET_RELEASE: $(TARGET_RELEASE). Available releases are: $(_all_release_configs))
endif
diff --git a/core/tasks/meta-lic.mk b/core/tasks/meta-lic.mk
index 2126bd0..c41de63 100644
--- a/core/tasks/meta-lic.mk
+++ b/core/tasks/meta-lic.mk
@@ -140,3 +140,10 @@
$(eval $(call declare-1p-copy-files,frameworks/base,dirty-image-objects))
$(eval $(call declare-1p-copy-files,frameworks/base/config,))
$(eval $(call declare-1p-copy-files,frameworks/native/data,))
+
+# Moved here from hardware/google/camera/Android.mk
+$(eval $(call declare-1p-copy-files,hardware/google/camera,))
+
+# Moved here from hardware/interfaces/tv/Android.mk
+$(eval $(call declare-1p-copy-files,hardware/interfaces/tv,tuner_vts_config_1_0.xml))
+$(eval $(call declare-1p-copy-files,hardware/interfaces/tv,tuner_vts_config_1_1.xml))
diff --git a/envsetup.sh b/envsetup.sh
index 50fec51..af33174 100644
--- a/envsetup.sh
+++ b/envsetup.sh
@@ -196,40 +196,19 @@
(\cd $T; build/soong/soong_ui.bash --dumpvar-mode $1)
}
-# check to see if the supplied product is one we can build
-function check_product()
+# This logic matches envsetup.mk
+function get_host_prebuilt_prefix
{
- local T=$(gettop)
- if [ ! "$T" ]; then
- echo "Couldn't locate the top of the tree. Try setting TOP." >&2
- return
- fi
- TARGET_PRODUCT=$1 \
- TARGET_RELEASE= \
- TARGET_BUILD_VARIANT= \
- TARGET_BUILD_TYPE= \
- TARGET_BUILD_APPS= \
- get_build_var TARGET_DEVICE > /dev/null
- # hide successful answers, but allow the errors to show
+ local un=$(uname)
+ if [[ $un == "Linux" ]] ; then
+ echo linux-x86
+ elif [[ $un == "Darwin" ]] ; then
+ echo darwin-x86
+ else
+ echo "Error: Invalid host operating system: $un" 1>&2
+ fi
}
-VARIANT_CHOICES=(user userdebug eng)
-
-# check to see if the supplied variant is valid
-function check_variant()
-{
- local v
- for v in ${VARIANT_CHOICES[@]}
- do
- if [ "$v" = "$1" ]
- then
- return 0
- fi
- done
- return 1
-}
-
-
# Add directories to PATH that are dependent on the lunch target.
# For directories that are not lunch-specific, add them in set_global_paths
function set_lunch_paths()
@@ -467,9 +446,6 @@
fi
done
- if should_add_completion bit ; then
- complete -C "bit --tab" bit
- fi
if [ -z "$ZSH_VERSION" ]; then
# Doesn't work in zsh.
complete -o nospace -F _croot croot
@@ -486,236 +462,6 @@
complete -F _complete_android_module_names m
}
-function multitree_lunch_help()
-{
- echo "usage: lunch PRODUCT-RELEASE-VARIANT" 1>&2
- echo " Set up android build environment based on a product short name and variant" 1>&2
- echo 1>&2
- echo "lunch COMBO_FILE VARIANT" 1>&2
- echo " Set up android build environment based on a specific lunch combo file" 1>&2
- echo " and variant." 1>&2
- echo 1>&2
- echo "lunch --print [CONFIG]" 1>&2
- echo " Print the contents of a configuration. If CONFIG is supplied, that config" 1>&2
- echo " will be flattened and printed. If CONFIG is not supplied, the currently" 1>&2
- echo " selected config will be printed. Returns 0 on success or nonzero on error." 1>&2
- echo 1>&2
- echo "lunch --list" 1>&2
- echo " List all possible combo files available in the current tree" 1>&2
- echo 1>&2
- echo "lunch --help" 1>&2
- echo "lunch -h" 1>&2
- echo " Prints this message." 1>&2
-}
-
-function multitree_lunch()
-{
- local code
- local results
- # Lunch must be run in the topdir, but this way we get a clear error
- # message, instead of FileNotFound.
- local T=$(multitree_gettop)
- if [ -z "$T" ]; then
- _multitree_lunch_error
- return 1
- fi
- if $(echo "$1" | grep -q '^-') ; then
- # Calls starting with a -- argument are passed directly and the function
- # returns with the lunch.py exit code.
- "${T}/orchestrator/build/orchestrator/core/lunch.py" "$@"
- code=$?
- if [[ $code -eq 2 ]] ; then
- echo 1>&2
- multitree_lunch_help
- return $code
- elif [[ $code -ne 0 ]] ; then
- return $code
- fi
- else
- # All other calls go through the --lunch variant of lunch.py
- results=($(${T}/orchestrator/build/orchestrator/core/lunch.py --lunch "$@"))
- code=$?
- if [[ $code -eq 2 ]] ; then
- echo 1>&2
- multitree_lunch_help
- return $code
- elif [[ $code -ne 0 ]] ; then
- return $code
- fi
-
- export TARGET_BUILD_COMBO=${results[0]}
- export TARGET_BUILD_VARIANT=${results[1]}
- fi
-}
-
-function choosetype()
-{
- echo "Build type choices are:"
- echo " 1. release"
- echo " 2. debug"
- echo
-
- local DEFAULT_NUM DEFAULT_VALUE
- DEFAULT_NUM=1
- DEFAULT_VALUE=release
-
- export TARGET_BUILD_TYPE=
- local ANSWER
- while [ -z $TARGET_BUILD_TYPE ]
- do
- echo -n "Which would you like? ["$DEFAULT_NUM"] "
- if [ -z "$1" ] ; then
- read ANSWER
- else
- echo $1
- ANSWER=$1
- fi
- case $ANSWER in
- "")
- export TARGET_BUILD_TYPE=$DEFAULT_VALUE
- ;;
- 1)
- export TARGET_BUILD_TYPE=release
- ;;
- release)
- export TARGET_BUILD_TYPE=release
- ;;
- 2)
- export TARGET_BUILD_TYPE=debug
- ;;
- debug)
- export TARGET_BUILD_TYPE=debug
- ;;
- *)
- echo
- echo "I didn't understand your response. Please try again."
- echo
- ;;
- esac
- if [ -n "$1" ] ; then
- break
- fi
- done
-
- build_build_var_cache
- set_stuff_for_environment
- destroy_build_var_cache
-}
-
-#
-# This function isn't really right: It chooses a TARGET_PRODUCT
-# based on the list of boards. Usually, that gets you something
-# that kinda works with a generic product, but really, you should
-# pick a product by name.
-#
-function chooseproduct()
-{
- local default_value
- if [ "x$TARGET_PRODUCT" != x ] ; then
- default_value=$TARGET_PRODUCT
- else
- default_value=aosp_arm
- fi
-
- export TARGET_BUILD_APPS=
- export TARGET_PRODUCT=
- local ANSWER
- while [ -z "$TARGET_PRODUCT" ]
- do
- echo -n "Which product would you like? [$default_value] "
- if [ -z "$1" ] ; then
- read ANSWER
- else
- echo $1
- ANSWER=$1
- fi
-
- if [ -z "$ANSWER" ] ; then
- export TARGET_PRODUCT=$default_value
- else
- if check_product $ANSWER
- then
- export TARGET_PRODUCT=$ANSWER
- else
- echo "** Not a valid product: $ANSWER"
- fi
- fi
- if [ -n "$1" ] ; then
- break
- fi
- done
-
- build_build_var_cache
- set_stuff_for_environment
- destroy_build_var_cache
-}
-
-function choosevariant()
-{
- echo "Variant choices are:"
- local index=1
- local v
- for v in ${VARIANT_CHOICES[@]}
- do
- # The product name is the name of the directory containing
- # the makefile we found, above.
- echo " $index. $v"
- index=$(($index+1))
- done
-
- local default_value=eng
- local ANSWER
-
- export TARGET_BUILD_VARIANT=
- while [ -z "$TARGET_BUILD_VARIANT" ]
- do
- echo -n "Which would you like? [$default_value] "
- if [ -z "$1" ] ; then
- read ANSWER
- else
- echo $1
- ANSWER=$1
- fi
-
- if [ -z "$ANSWER" ] ; then
- export TARGET_BUILD_VARIANT=$default_value
- elif (echo -n $ANSWER | grep -q -e "^[0-9][0-9]*$") ; then
- if [ "$ANSWER" -le "${#VARIANT_CHOICES[@]}" ] ; then
- export TARGET_BUILD_VARIANT=${VARIANT_CHOICES[@]:$(($ANSWER-1)):1}
- fi
- else
- if check_variant $ANSWER
- then
- export TARGET_BUILD_VARIANT=$ANSWER
- else
- echo "** Not a valid variant: $ANSWER"
- fi
- fi
- if [ -n "$1" ] ; then
- break
- fi
- done
-}
-
-function choosecombo()
-{
- choosetype $1
-
- echo
- echo
- chooseproduct $2
-
- echo
- echo
- choosevariant $3
-
- echo
- build_build_var_cache
- set_stuff_for_environment
- printconfig
- destroy_build_var_cache
-}
-
function add_lunch_combo()
{
if [ -n "$ZSH_VERSION" ]; then
@@ -1013,34 +759,6 @@
destroy_build_var_cache
}
-# TODO: Merge into gettop as part of launching multitree
-function multitree_gettop
-{
- local TOPFILE=orchestrator/build/make/core/envsetup.mk
- if [ -n "$TOP" -a -f "$TOP/$TOPFILE" ] ; then
- # The following circumlocution ensures we remove symlinks from TOP.
- (cd "$TOP"; PWD= /bin/pwd)
- else
- if [ -f $TOPFILE ] ; then
- # The following circumlocution (repeated below as well) ensures
- # that we record the true directory name and not one that is
- # faked up with symlink names.
- PWD= /bin/pwd
- else
- local HERE=$PWD
- local T=
- while [ \( ! \( -f $TOPFILE \) \) -a \( "$PWD" != "/" \) ]; do
- \cd ..
- T=`PWD= /bin/pwd -P`
- done
- \cd "$HERE"
- if [ -f "$T/$TOPFILE" ]; then
- echo "$T"
- fi
- fi
- fi
-}
-
function croot()
{
local T=$(gettop)
@@ -1575,17 +1293,6 @@
adb shell am instrument -w com.android.smoketest.tests/android.test.InstrumentationTestRunner
}
-# simple shortcut to the runtest command
-function runtest()
-{
- local T=$(gettop)
- if [ ! "$T" ]; then
- echo "Couldn't locate the top of the tree. Try setting TOP." >&2
- return
- fi
- ("$T"/development/testrunner/runtest.py $@)
-}
-
function godir () {
if [[ -z "$1" ]]; then
echo "Usage: godir <regex>"
@@ -1982,22 +1689,6 @@
_wrap_build $(get_make_command "$@") "$@"
}
-function _multitree_lunch_error()
-{
- >&2 echo "Couldn't locate the top of the tree. Please run \'source build/envsetup.sh\' and multitree_lunch from the root of your workspace."
-}
-
-function multitree_build()
-{
- local T=$(multitree_gettop)
- if [ -n "$T" ]; then
- "$T/orchestrator/build/orchestrator/core/orchestrator.py" "$@"
- else
- _multitree_lunch_error
- return 1
- fi
-}
-
function provision()
{
if [ ! "$ANDROID_PRODUCT_OUT" ]; then
@@ -2119,25 +1810,17 @@
fi
}
-function avbtool() {
- if [[ ! -f "$ANDROID_SOONG_HOST_OUT"/bin/avbtool ]]; then
- m avbtool
- fi
- "$ANDROID_SOONG_HOST_OUT"/bin/avbtool $@
-}
+# These functions used to be here but are now standalone scripts.
+# Unset these for the time being so the real script is picked up.
+# TODO: Remove this some time after a suitable delay (maybe 2025?)
+unset aninja
+unset overrideflags
-function overrideflags() {
- local T="$(gettop)"
- (\cd "${T}" && build/make/tools/overrideflags.sh "$@")
-}
-
-function aninja() {
- local T="$(gettop)"
- (\cd "${T}" && prebuilts/build-tools/linux-x86/bin/ninja -f out/combined-${TARGET_PRODUCT}.ninja "$@")
-}
validate_current_shell
set_global_paths
source_vendorsetup
addcompletions
+
+
diff --git a/shell_utils.sh b/shell_utils.sh
index 9de5a50..15051e9 100644
--- a/shell_utils.sh
+++ b/shell_utils.sh
@@ -40,9 +40,7 @@
fi
}
-# Sets TOP, or if the root of the tree can't be found, prints a message and
-# exits. Since this function exits, it should not be called from functions
-# defined in envsetup.sh.
+# Asserts that the root of the tree can be found.
if [ -z "${IMPORTING_ENVSETUP:-}" ] ; then
function require_top
{
@@ -54,6 +52,17 @@
}
fi
+# Asserts that the lunch variables have been set
+if [ -z "${IMPORTING_ENVSETUP:-}" ] ; then
+function require_lunch
+{
+ if [[ ! $TARGET_PRODUCT || ! $TARGET_RELEASE || ! $TARGET_BUILD_VARIANT ]] ; then
+ echo "Please run lunch and try again." >&2
+ exit 1
+ fi
+}
+fi
+
function getoutdir
{
local top=$(gettop)
diff --git a/target/product/base_system.mk b/target/product/base_system.mk
index 42cfc9a..634bf66 100644
--- a/target/product/base_system.mk
+++ b/target/product/base_system.mk
@@ -288,6 +288,7 @@
uncrypt \
usbd \
vdc \
+ vintf \
voip-common \
vold \
watchdogd \
diff --git a/target/product/virtual_ab_ota/vabc_features.mk b/target/product/virtual_ab_ota/vabc_features.mk
index 3f484e4..1219763 100644
--- a/target/product/virtual_ab_ota/vabc_features.mk
+++ b/target/product/virtual_ab_ota/vabc_features.mk
@@ -34,6 +34,21 @@
PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.io_uring.enabled=true
PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.compression.xor.enabled=true
PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.batch_writes=true
+# Low memory device configurations. If memory usage and cpu utilization is
+# a bottleneck during OTA, the below configurations can be added to a
+# device's .mk file improve performance for low mem devices. Disabling
+# ro.virtual_ab.compression.xor.enabled and ro.virtual_ab.io_uring.enabled
+# is also recommended
+#
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.o_direct.enabled=true
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.merge_thread_priority=19
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.worker_thread_priority=0
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.num_worker_threads=3
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.num_merge_threads=1
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.num_verify_threads=1
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.cow_op_merge_size=16
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.verify_threshold_size=1073741824
+# PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.verify_block_size=1048576
# Enabling this property, will improve OTA install time
# but will use an additional CPU core
diff --git a/tools/aconfig/aconfig_device_paths/src/lib.rs b/tools/aconfig/aconfig_device_paths/src/lib.rs
index c5a6bff..7480b30 100644
--- a/tools/aconfig/aconfig_device_paths/src/lib.rs
+++ b/tools/aconfig/aconfig_device_paths/src/lib.rs
@@ -21,11 +21,19 @@
use std::fs;
+fn read_partition_paths() -> Vec<PathBuf> {
+ include_str!("../partition_aconfig_flags_paths.txt")
+ .split(',')
+ .map(|s| s.trim().trim_matches('"'))
+ .filter(|s| !s.is_empty())
+ .map(|s| PathBuf::from(s.to_string()))
+ .collect()
+}
+
/// Determine all paths that contain an aconfig protobuf file.
pub fn parsed_flags_proto_paths() -> Result<Vec<PathBuf>> {
- let mut result: Vec<PathBuf> = [include_str!("../partition_aconfig_flags_paths.txt")]
- .map(|s| PathBuf::from(s.to_string()))
- .to_vec();
+ let mut result: Vec<PathBuf> = read_partition_paths();
+
for dir in fs::read_dir("/apex")? {
let dir = dir?;
@@ -45,3 +53,23 @@
Ok(result)
}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+
+ #[test]
+ fn test_read_partition_paths() {
+ assert_eq!(read_partition_paths().len(), 4);
+
+ assert_eq!(
+ read_partition_paths(),
+ vec![
+ PathBuf::from("/system/etc/aconfig_flags.pb"),
+ PathBuf::from("/system_ext/etc/aconfig_flags.pb"),
+ PathBuf::from("/product/etc/aconfig_flags.pb"),
+ PathBuf::from("/vendor/etc/aconfig_flags.pb")
+ ]
+ );
+ }
+}
diff --git a/tools/aconfig/aconfig_protos/Android.bp b/tools/aconfig/aconfig_protos/Android.bp
index 18c545a..d241994 100644
--- a/tools/aconfig/aconfig_protos/Android.bp
+++ b/tools/aconfig/aconfig_protos/Android.bp
@@ -17,7 +17,22 @@
apex_available: [
"com.android.configinfrastructure",
"//apex_available:platform",
- ]
+ ],
+}
+
+java_library {
+ name: "libaconfig_java_proto_nano",
+ srcs: ["protos/aconfig.proto"],
+ static_libs: ["libprotobuf-java-nano"],
+ proto: {
+ type: "nano",
+ },
+ sdk_version: "current",
+ min_sdk_version: "UpsideDownCake",
+ apex_available: [
+ "//apex_available:platform",
+ ],
+ jarjar_rules: "jarjar-nano-rules.txt",
}
java_library_host {
@@ -58,7 +73,7 @@
],
proc_macros: [
"libpaste",
- ]
+ ],
}
rust_library {
diff --git a/tools/aconfig/aconfig_protos/jarjar-nano-rules.txt b/tools/aconfig/aconfig_protos/jarjar-nano-rules.txt
new file mode 100644
index 0000000..b58fa64
--- /dev/null
+++ b/tools/aconfig/aconfig_protos/jarjar-nano-rules.txt
@@ -0,0 +1 @@
+rule com.google.protobuf.** android.internal.framework.protobuf.@1
\ No newline at end of file
diff --git a/tools/aconfig/aconfig_storage_file/protos/aconfig_storage_metadata.proto b/tools/aconfig/aconfig_storage_file/protos/aconfig_storage_metadata.proto
index f6bf1a4..e1c1c7f 100644
--- a/tools/aconfig/aconfig_storage_file/protos/aconfig_storage_metadata.proto
+++ b/tools/aconfig/aconfig_storage_file/protos/aconfig_storage_metadata.proto
@@ -27,9 +27,7 @@
optional string flag_map = 4;
optional string flag_val = 5;
optional string flag_info = 6;
- optional string local_overrides = 7;
- optional string default_flag_val = 8;
- optional int64 timestamp = 9;
+ optional int64 timestamp = 7;
}
message storage_files {
diff --git a/tools/aconfig/aflags/src/aconfig_storage_source.rs b/tools/aconfig/aflags/src/aconfig_storage_source.rs
index c21c542..04140c7 100644
--- a/tools/aconfig/aflags/src/aconfig_storage_source.rs
+++ b/tools/aconfig/aflags/src/aconfig_storage_source.rs
@@ -27,8 +27,7 @@
let container =
file_info.container.ok_or(anyhow!("storage file is missing container"))?;
- for listed_flag in
- aconfig_storage_file::list_flags(&package_map, &flag_map, &flag_val)?
+ for listed_flag in aconfig_storage_file::list_flags(&package_map, &flag_map, &flag_val)?
{
result.push(Flag {
name: listed_flag.flag_name,
diff --git a/tools/aconfig/aflags/src/main.rs b/tools/aconfig/aflags/src/main.rs
index 516b773..05c15bb 100644
--- a/tools/aconfig/aflags/src/main.rs
+++ b/tools/aconfig/aflags/src/main.rs
@@ -35,10 +35,14 @@
impl std::fmt::Display for FlagPermission {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
- write!(f, "{}", match &self {
- Self::ReadOnly => "read-only",
- Self::ReadWrite => "read-write",
- })
+ write!(
+ f,
+ "{}",
+ match &self {
+ Self::ReadOnly => "read-only",
+ Self::ReadWrite => "read-write",
+ }
+ )
}
}
@@ -50,10 +54,14 @@
impl std::fmt::Display for ValuePickedFrom {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
- write!(f, "{}", match &self {
- Self::Default => "default",
- Self::Server => "server",
- })
+ write!(
+ f,
+ "{}",
+ match &self {
+ Self::Default => "default",
+ Self::Server => "server",
+ }
+ )
}
}
@@ -77,10 +85,14 @@
impl std::fmt::Display for FlagValue {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
- write!(f, "{}", match &self {
- Self::Enabled => "enabled",
- Self::Disabled => "disabled",
- })
+ write!(
+ f,
+ "{}",
+ match &self {
+ Self::Enabled => "enabled",
+ Self::Disabled => "disabled",
+ }
+ )
}
}
@@ -153,6 +165,10 @@
/// Read from the new flag storage.
#[clap(long)]
use_new_storage: bool,
+
+ /// Optionally filter by container name.
+ #[clap(short = 'c', long = "container")]
+ container: Option<String>,
},
/// Enable an aconfig flag on this device, on the next boot.
@@ -176,6 +192,23 @@
longest_permission_col: usize,
}
+struct Filter {
+ container: Option<String>,
+}
+
+impl Filter {
+ fn apply(&self, flags: &[Flag]) -> Vec<Flag> {
+ flags
+ .iter()
+ .filter(|flag| match &self.container {
+ Some(c) => flag.container == *c,
+ None => true,
+ })
+ .cloned()
+ .collect()
+ }
+}
+
fn format_flag_row(flag: &Flag, info: &PaddingInfo) -> String {
let full_name = flag.qualified_name();
let p0 = info.longest_flag_col + 1;
@@ -215,11 +248,12 @@
Ok(())
}
-fn list(source_type: FlagSourceType) -> Result<String> {
- let flags = match source_type {
+fn list(source_type: FlagSourceType, container: Option<String>) -> Result<String> {
+ let flags_unfiltered = match source_type {
FlagSourceType::DeviceConfig => DeviceConfigSource::list_flags()?,
FlagSourceType::AconfigStorage => AconfigStorageSource::list_flags()?,
};
+ let flags = (Filter { container }).apply(&flags_unfiltered);
let padding_info = PaddingInfo {
longest_flag_col: flags.iter().map(|f| f.qualified_name().len()).max().unwrap_or(0),
longest_val_col: flags.iter().map(|f| f.value.to_string().len()).max().unwrap_or(0),
@@ -251,8 +285,12 @@
fn main() {
let cli = Cli::parse();
let output = match cli.command {
- Command::List { use_new_storage: true } => list(FlagSourceType::AconfigStorage).map(Some),
- Command::List { use_new_storage: false } => list(FlagSourceType::DeviceConfig).map(Some),
+ Command::List { use_new_storage: true, container } => {
+ list(FlagSourceType::AconfigStorage, container).map(Some)
+ }
+ Command::List { use_new_storage: false, container } => {
+ list(FlagSourceType::DeviceConfig, container).map(Some)
+ }
Command::Enable { qualified_name } => set_flag(&qualified_name, "true").map(|_| None),
Command::Disable { qualified_name } => set_flag(&qualified_name, "false").map(|_| None),
};
@@ -262,3 +300,84 @@
Err(message) => println!("Error: {message}"),
}
}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+
+ #[test]
+ fn test_filter_container() {
+ let flags = vec![
+ Flag {
+ namespace: "namespace".to_string(),
+ name: "test1".to_string(),
+ package: "package".to_string(),
+ value: FlagValue::Disabled,
+ staged_value: None,
+ permission: FlagPermission::ReadWrite,
+ value_picked_from: ValuePickedFrom::Default,
+ container: "system".to_string(),
+ },
+ Flag {
+ namespace: "namespace".to_string(),
+ name: "test2".to_string(),
+ package: "package".to_string(),
+ value: FlagValue::Disabled,
+ staged_value: None,
+ permission: FlagPermission::ReadWrite,
+ value_picked_from: ValuePickedFrom::Default,
+ container: "not_system".to_string(),
+ },
+ Flag {
+ namespace: "namespace".to_string(),
+ name: "test3".to_string(),
+ package: "package".to_string(),
+ value: FlagValue::Disabled,
+ staged_value: None,
+ permission: FlagPermission::ReadWrite,
+ value_picked_from: ValuePickedFrom::Default,
+ container: "system".to_string(),
+ },
+ ];
+
+ assert_eq!((Filter { container: Some("system".to_string()) }).apply(&flags).len(), 2);
+ }
+
+ #[test]
+ fn test_filter_no_container() {
+ let flags = vec![
+ Flag {
+ namespace: "namespace".to_string(),
+ name: "test1".to_string(),
+ package: "package".to_string(),
+ value: FlagValue::Disabled,
+ staged_value: None,
+ permission: FlagPermission::ReadWrite,
+ value_picked_from: ValuePickedFrom::Default,
+ container: "system".to_string(),
+ },
+ Flag {
+ namespace: "namespace".to_string(),
+ name: "test2".to_string(),
+ package: "package".to_string(),
+ value: FlagValue::Disabled,
+ staged_value: None,
+ permission: FlagPermission::ReadWrite,
+ value_picked_from: ValuePickedFrom::Default,
+ container: "not_system".to_string(),
+ },
+ Flag {
+ namespace: "namespace".to_string(),
+ name: "test3".to_string(),
+ package: "package".to_string(),
+ value: FlagValue::Disabled,
+ staged_value: None,
+ permission: FlagPermission::ReadWrite,
+ value_picked_from: ValuePickedFrom::Default,
+ container: "system".to_string(),
+ },
+ ];
+
+ assert_eq!((Filter { container: None }).apply(&flags).len(), 3);
+ }
+}
diff --git a/tools/check-flagged-apis/src/com/android/checkflaggedapis/CheckFlaggedApisTest.kt b/tools/check-flagged-apis/src/com/android/checkflaggedapis/CheckFlaggedApisTest.kt
index cd85944..111ea91 100644
--- a/tools/check-flagged-apis/src/com/android/checkflaggedapis/CheckFlaggedApisTest.kt
+++ b/tools/check-flagged-apis/src/com/android/checkflaggedapis/CheckFlaggedApisTest.kt
@@ -270,6 +270,42 @@
}
@Test
+ fun testNestedFlagsOuterFlagWins() {
+ val apiSignature =
+ """
+ // Signature format: 2.0
+ package android {
+ @FlaggedApi("android.flag.foo") public final class A {
+ method @FlaggedApi("android.flag.bar") public boolean method();
+ }
+ @FlaggedApi("android.flag.bar") public final class B {
+ method @FlaggedApi("android.flag.foo") public boolean method();
+ }
+ }
+ """
+ .trim()
+
+ val apiVersions =
+ """
+ <?xml version="1.0" encoding="utf-8"?>
+ <api version="3">
+ <class name="android/B" since="1">
+ <extends name="java/lang/Object"/>
+ </class>
+ </api>
+ """
+ .trim()
+
+ val expected = setOf<ApiError>()
+ val actual =
+ findErrors(
+ parseApiSignature("in-memory", apiSignature.byteInputStream()),
+ parseFlagValues(generateFlagsProto(DISABLED, ENABLED)),
+ parseApiVersions(apiVersions.byteInputStream()))
+ assertEquals(expected, actual)
+ }
+
+ @Test
fun testFindErrorsDisabledFlaggedApiIsPresent() {
val expected =
setOf<ApiError>(
diff --git a/tools/check-flagged-apis/src/com/android/checkflaggedapis/Main.kt b/tools/check-flagged-apis/src/com/android/checkflaggedapis/Main.kt
index b514048..a277ce8 100644
--- a/tools/check-flagged-apis/src/com/android/checkflaggedapis/Main.kt
+++ b/tools/check-flagged-apis/src/com/android/checkflaggedapis/Main.kt
@@ -385,10 +385,48 @@
return false
}
+
+ /**
+ * Returns whether the given flag is enabled for the given symbol.
+ *
+ * A flagged member inside a flagged class is ignored (and the flag value considered disabled) if
+ * the class' flag is disabled.
+ *
+ * @param symbol the symbol to check
+ * @param flag the flag to check
+ * @return whether the flag is enabled for the given symbol
+ */
+ fun isFlagEnabledForSymbol(symbol: Symbol, flag: Flag): Boolean {
+ when (symbol) {
+ is ClassSymbol -> return flags.getValue(flag)
+ is MemberSymbol -> {
+ val memberFlagValue = flags.getValue(flag)
+ if (!memberFlagValue) {
+ return false
+ }
+ // Special case: if the MemberSymbol's flag is enabled, but the outer
+ // ClassSymbol's flag (if the class is flagged) is disabled, consider
+ // the MemberSymbol's flag as disabled:
+ //
+ // @FlaggedApi(this-flag-is-disabled) Clazz {
+ // @FlaggedApi(this-flag-is-enabled) method(); // The Clazz' flag "wins"
+ // }
+ //
+ // Note: the current implementation does not handle nested classes.
+ val classFlagValue =
+ flaggedSymbolsInSource
+ .find { it.first.toPrettyString() == symbol.clazz }
+ ?.let { flags.getValue(it.second) }
+ ?: true
+ return classFlagValue
+ }
+ }
+ }
+
val errors = mutableSetOf<ApiError>()
for ((symbol, flag) in flaggedSymbolsInSource) {
try {
- if (flags.getValue(flag)) {
+ if (isFlagEnabledForSymbol(symbol, flag)) {
if (!symbolsInOutput.containsSymbol(symbol)) {
errors.add(EnabledFlaggedApiNotPresentError(symbol, flag))
}
diff --git a/tools/overrideflags.sh b/tools/overrideflags.sh
deleted file mode 100755
index b8605dc..0000000
--- a/tools/overrideflags.sh
+++ /dev/null
@@ -1,99 +0,0 @@
-#!/bin/bash -e
-# Copyright (C) 2023 The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-
-source $(cd $(dirname $BASH_SOURCE) &> /dev/null && pwd)/../shell_utils.sh
-require_top
-
-function print_help() {
- echo -e "overrideflags is used to set default value for local build."
- echo -e "\nOptions:"
- echo -e "\t--release-config \tPath to release configuration directory. Required"
- echo -e "\t--no-edit \tIf present, skip editing flag value file."
- echo -e "\t-h/--help \tShow this help."
-}
-
-function main() {
- while (($# > 0)); do
- case $1 in
- --release-config)
- if [[ $# -le 1 ]]; then
- echo "--release-config requires a path"
- return 1
- fi
- local release_config_dir="$2"
- shift 2
- ;;
- --no-edit)
- local no_edit="true"
- shift 1
- ;;
- -h|--help)
- print_help
- return
- ;;
- *)
- echo "$1 is unrecognized"
- print_help
- return 1
- ;;
- esac
- done
-
-
-
- case $(uname -s) in
- Darwin)
- local host_arch=darwin-x86
- ;;
- Linux)
- local host_arch=linux-x86
- ;;
- *)
- >&2 echo Unknown host $(uname -s)
- return
- ;;
- esac
-
- if [[ -z "${release_config_dir}" ]]; then
- echo "Please provide release configuration path by --release-config"
- exit 1
- elif [ ! -d "${release_config_dir}" ]; then
- echo "${release_config_dir} is an invalid directory"
- exit 1
- fi
- local T="$(gettop)"
- local aconfig_dir="${T}"/build/make/tools/aconfig/
- local overrideflag_py="${aconfig_dir}"/overrideflags/overrideflags.py
- local overridefile="${release_config_dir}/aconfig/override_values.textproto"
-
- # Edit override file
- if [[ -z "${no_edit}" ]]; then
- editor="${EDITOR:-$(which vim)}"
-
- eval "${editor} ${overridefile}"
- if [ $? -ne 0 ]; then
- echo "Fail to set override values"
- return 1
- fi
- fi
-
- ${T}/prebuilts/build-tools/${host_arch}/bin/py3-cmd -u "${overrideflag_py}" \
- --overrides "${overridefile}" \
- --out "${release_config_dir}/aconfig"
-}
-
-
-main "$@"
diff --git a/tools/releasetools/ota_from_target_files.py b/tools/releasetools/ota_from_target_files.py
index 432ea19..5a024ce 100755
--- a/tools/releasetools/ota_from_target_files.py
+++ b/tools/releasetools/ota_from_target_files.py
@@ -914,12 +914,13 @@
# and install time performance. All OTA's with
# both the source build and target build with VIRTUAL_AB_COW_VERSION = 3
# can support the new format. Otherwise, fallback on older versions
- if not source_info.vabc_cow_version or not target_info.vabc_cow_version:
- logger.info("Source or Target doesn't have VABC_COW_VERSION specified, default to version 2")
- OPTIONS.vabc_cow_version = 2
- elif source_info.vabc_cow_version != target_info.vabc_cow_version:
- logger.info("Source and Target have different cow VABC_COW_VERSION specified, default to minimum version")
- OPTIONS.vabc_cow_version = min(source_info.vabc_cow_version, target_info.vabc_cow_version)
+ if not OPTIONS.vabc_cow_version:
+ if not source_info.vabc_cow_version or not target_info.vabc_cow_version:
+ logger.info("Source or Target doesn't have VABC_COW_VERSION specified, default to version 2")
+ OPTIONS.vabc_cow_version = 2
+ elif source_info.vabc_cow_version != target_info.vabc_cow_version:
+ logger.info("Source and Target have different cow VABC_COW_VERSION specified, default to minimum version")
+ OPTIONS.vabc_cow_version = min(source_info.vabc_cow_version, target_info.vabc_cow_version)
# Virtual AB Compression was introduced in Androd S.
# Later, we backported VABC to Android R. But verity support was not
@@ -933,19 +934,20 @@
assert "ab_partitions" in OPTIONS.info_dict, \
"META/ab_partitions.txt is required for ab_update."
source_info = None
- if not target_info.vabc_cow_version:
+ if not OPTIONS.vabc_cow_version:
+ if not target_info.vabc_cow_version:
+ OPTIONS.vabc_cow_version = 2
+ elif target_info.vabc_cow_version >= "3" and target_info.vendor_api_level < 35:
+ logger.warning(
+ "This full OTA is configured to use VABC cow version"
+ " 3 which is supported since"
+ " Android API level 35, but device is "
+ "launched with {} . If this full OTA is"
+ " served to a device running old build, OTA might fail due to "
+ "unsupported vabc cow version. For safety, version 2 is used because "
+ "it's supported since day 1.".format(
+ target_info.vendor_api_level))
OPTIONS.vabc_cow_version = 2
- elif target_info.vabc_cow_version >= "3" and target_info.vendor_api_level < 35:
- logger.warning(
- "This full OTA is configured to use VABC cow version"
- " 3 which is supported since"
- " Android API level 35, but device is "
- "launched with {} . If this full OTA is"
- " served to a device running old build, OTA might fail due to "
- "unsupported vabc cow version. For safety, version 2 is used because "
- "it's supported since day 1.".format(
- target_info.vendor_api_level))
- OPTIONS.vabc_cow_version = 2
if OPTIONS.vabc_compression_param is None and vabc_compression_param:
minimum_api_level_required = VABC_COMPRESSION_PARAM_SUPPORT[
vabc_compression_param]