Merge "Allow setting some build_broken out of boardconfig" into main
diff --git a/core/Makefile b/core/Makefile
index 3bd6ae1..3013b78 100644
--- a/core/Makefile
+++ b/core/Makefile
@@ -16,53 +16,93 @@
ODM_DLKM_NOTICE_DEPS :=
SYSTEM_DLKM_NOTICE_DEPS :=
-# -----------------------------------------------------------------
-# Release Config Flags
-# Create a summary file of build flags for each partition
-# $(1): build flags json file
-# $(2): flag names
-define generate-partition-build-flag-file
-$(eval $(strip $(1)): PRIVATE_OUT := $(strip $(1)))
-$(eval $(strip $(1)): PRIVATE_FLAG_NAMES := $(strip $(2)))
-$(strip $(1)):
- mkdir -p $$(dir $$(PRIVATE_OUT))
- echo '{' > $$(PRIVATE_OUT)
- echo '"flags": [' >> $$(PRIVATE_OUT)
- $$(foreach flag, $$(PRIVATE_FLAG_NAMES), \
- ( \
- printf ' { "name": "%s", "value": "%s", ' \
- '$$(flag)' \
- '$$(_ALL_RELEASE_FLAGS.$$(flag).VALUE)' \
- ; \
- printf '"set": "%s", "default": "%s", "declared": "%s" }' \
- '$$(_ALL_RELEASE_FLAGS.$$(flag).SET_IN)' \
- '$$(_ALL_RELEASE_FLAGS.$$(flag).DEFAULT)' \
- '$$(_ALL_RELEASE_FLAGS.$$(flag).DECLARED_IN)' \
- ; \
- printf '$$(if $$(filter $$(lastword $$(PRIVATE_FLAG_NAMES)),$$(flag)),,$$(comma))\n' ; \
- ) >> $$(PRIVATE_OUT) \
- )
- echo "]" >> $$(PRIVATE_OUT)
- echo "}" >> $$(PRIVATE_OUT)
+# IMAGES_TO_BUILD is a list of the partition .img files that will be created.
+IMAGES_TO_BUILD:=
+ifneq ($(BUILDING_BOOT_IMAGE),)
+ IMAGES_TO_BUILD += boot
+endif
+ifneq ($(BUILDING_CACHE_IMAGE),)
+ IMAGES_TO_BUILD += cache
+endif
+ifneq ($(BUILDING_DEBUG_BOOT_IMAGE),)
+ IMAGES_TO_BUILD += debug_boot
+endif
+ifneq ($(BUILDING_DEBUG_VENDOR_BOOT_IMAGE),)
+ IMAGES_TO_BUILD += debug_vendor_boot
+endif
+ifneq ($(BUILDING_INIT_BOOT_IMAGE),)
+ IMAGES_TO_BUILD += init_boot
+endif
+ifneq ($(BUILDING_ODM_DLKM_IMAGE),)
+ IMAGES_TO_BUILD += odm_dlkm
+endif
+ifneq ($(BUILDING_ODM_IMAGE),)
+ IMAGES_TO_BUILD += odm
+endif
+ifneq ($(BUILDING_PRODUCT_IMAGE),)
+ IMAGES_TO_BUILD += product
+endif
+ifneq ($(BUILDING_RAMDISK_IMAGE),)
+ IMAGES_TO_BUILD += ramdisk
+endif
+ifneq ($(BUILDING_RECOVERY_IMAGE),)
+ IMAGES_TO_BUILD += recovery
+endif
+ifneq ($(BUILDING_SUPER_EMPTY_IMAGE),)
+ IMAGES_TO_BUILD += super_empty
+endif
+ifneq ($(BUILDING_SYSTEM_DLKM_IMAGE),)
+ IMAGES_TO_BUILD += system_dlkm
+endif
+ifneq ($(BUILDING_SYSTEM_EXT_IMAGE),)
+ IMAGES_TO_BUILD += system_ext
+endif
+ifneq ($(BUILDING_SYSTEM_IMAGE),)
+ IMAGES_TO_BUILD += system
+endif
+ifneq ($(BUILDING_SYSTEM_OTHER_IMAGE),)
+ IMAGES_TO_BUILD += system_other
+endif
+ifneq ($(BUILDING_USERDATA_IMAGE),)
+ IMAGES_TO_BUILD += userdata
+endif
+ifneq ($(BUILDING_VBMETA_IMAGE),)
+ IMAGES_TO_BUILD += vbmeta
+endif
+ifneq ($(BUILDING_VENDOR_BOOT_IMAGE),)
+ IMAGES_TO_BUILD += vendor_boot
+endif
+ifneq ($(BUILDING_VENDOR_DLKM_IMAGE),)
+ IMAGES_TO_BUILD += vendor_dlkm
+endif
+ifneq ($(BUILDING_VENDOR_IMAGE),)
+ IMAGES_TO_BUILD += vendor
+endif
+ifneq ($(BUILDING_VENDOR_KERNEL_BOOT_IMAGE),)
+ IMAGES_TO_BUILD += vendor_kernel_boot
+endif
+
+
+###########################################################
+# Get the module names suitable for ALL_MODULES.* variables that are installed
+# for a given partition
+#
+# $(1): Partition
+###########################################################
+define register-names-for-partition
+$(sort $(foreach m,$(product_MODULES),\
+ $(if $(filter $(PRODUCT_OUT)/$(strip $(1))/%, $(ALL_MODULES.$(m).INSTALLED)), \
+ $(m)
+ ) \
+))
endef
-_FLAG_PARTITIONS := product system system_ext vendor
-$(foreach partition, $(_FLAG_PARTITIONS), \
- $(eval BUILD_FLAG_SUMMARIES.$(partition) \
- := $(TARGET_OUT_FLAGS)/$(partition)/etc/build_flags.json) \
- $(eval $(call generate-partition-build-flag-file, \
- $(BUILD_FLAG_SUMMARIES.$(partition)), \
- $(_ALL_RELEASE_FLAGS.PARTITIONS.$(partition)) \
- ) \
- ) \
-)
+# Release & Aconfig Flags
+# -----------------------------------------------------------------
+include $(BUILD_SYSTEM)/packaging/flags.mk
-# TODO: Remove
-.PHONY: flag-files
-flag-files: $(foreach partition, $(_FLAG_PARTITIONS), \
- $(TARGET_OUT_FLAGS)/$(partition)/etc/build_flags.json)
# -----------------------------------------------------------------
# Define rules to copy PRODUCT_COPY_FILES defined by the product.
@@ -7388,6 +7428,9 @@
haiku-rust: $(SOONG_RUST_FUZZ_PACKAGING_ARCH_MODULES) $(ALL_RUST_FUZZ_TARGETS)
$(call dist-for-goals,haiku-rust,$(SOONG_RUST_FUZZ_PACKAGING_ARCH_MODULES))
$(call dist-for-goals,haiku-rust,$(PRODUCT_OUT)/module-info.json)
+.PHONY: haiku-presubmit
+haiku-presubmit: $(SOONG_PRESUBMIT_FUZZ_PACKAGING_ARCH_MODULES) $(ALL_PRESUBMIT_FUZZ_TARGETS)
+$(call dist-for-goals,haiku-presubmit,$(SOONG_PRESUBMIT_FUZZ_PACKAGING_ARCH_MODULES))
# -----------------------------------------------------------------
# Extract platform fonts used in Layoutlib
diff --git a/core/base_rules.mk b/core/base_rules.mk
index 998cb0d..e7c28ec 100644
--- a/core/base_rules.mk
+++ b/core/base_rules.mk
@@ -1058,6 +1058,10 @@
$(ALL_MODULES.$(my_register_name).SUPPORTED_VARIANTS) \
$(filter-out $(ALL_MODULES.$(my_register_name).SUPPORTED_VARIANTS),$(my_supported_variant))
+ALL_MODULES.$(my_register_name).ACONFIG_FILES := \
+ $(ALL_MODULES.$(my_register_name).ACONFIG_FILES) $(LOCAL_ACONFIG_FILES)
+
+
##########################################################################
## When compiling against API imported module, use API import stub
## libraries.
diff --git a/core/clear_vars.mk b/core/clear_vars.mk
index bb7ba1b..25b26cc 100644
--- a/core/clear_vars.mk
+++ b/core/clear_vars.mk
@@ -9,6 +9,7 @@
LOCAL_AAPT_FLAGS:=
LOCAL_AAPT_INCLUDE_ALL_RESOURCES:=
LOCAL_AAPT_NAMESPACES:=
+LOCAL_ACONFIG_FILES:=
LOCAL_ADDITIONAL_CERTIFICATES:=
LOCAL_ADDITIONAL_CHECKED_MODULE:=
LOCAL_ADDITIONAL_DEPENDENCIES:=
diff --git a/core/config.mk b/core/config.mk
index 0c6653a..55ff6ba 100644
--- a/core/config.mk
+++ b/core/config.mk
@@ -649,6 +649,7 @@
FILESLIST_UTIL :=$= build/make/tools/fileslist_util.py
HOST_INIT_VERIFIER := $(HOST_OUT_EXECUTABLES)/host_init_verifier
XMLLINT := $(HOST_OUT_EXECUTABLES)/xmllint
+ACONFIG := $(HOST_OUT_EXECUTABLES)/aconfig
# SOONG_ZIP is exported by Soong, but needs to be defined early for
# $OUT/dexpreopt.global. It will be verified against the Soong version.
diff --git a/core/config_sanitizers.mk b/core/config_sanitizers.mk
index 7fa190f..82b17be 100644
--- a/core/config_sanitizers.mk
+++ b/core/config_sanitizers.mk
@@ -413,7 +413,6 @@
my_cflags += -fvisibility=default
endif
my_ldflags += $(CFI_EXTRA_LDFLAGS)
- my_arflags += --plugin $(LLVM_PREBUILTS_PATH)/../lib64/LLVMgold.so
ifeq ($(LOCAL_FORCE_STATIC_EXECUTABLE),true)
my_ldflags := $(filter-out -fsanitize-cfi-cross-dso,$(my_ldflags))
diff --git a/core/main.mk b/core/main.mk
index cbdb680..48b4b5e 100644
--- a/core/main.mk
+++ b/core/main.mk
@@ -1364,6 +1364,7 @@
product_host_FILES := $(call host-installed-files,$(INTERNAL_PRODUCT))
product_target_FILES := $(call product-installed-files, $(INTERNAL_PRODUCT))
# WARNING: The product_MODULES variable is depended on by external files.
+ # It contains the list of register names that will be installed on the device
product_MODULES := $(_pif_modules)
# Verify the artifact path requirements made by included products.
diff --git a/core/packaging/flags.mk b/core/packaging/flags.mk
new file mode 100644
index 0000000..4b692be
--- /dev/null
+++ b/core/packaging/flags.mk
@@ -0,0 +1,122 @@
+# 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.
+
+#
+# This file is included by build/make/core/Makefile, and contains the logic for
+# the combined flags files.
+#
+
+# TODO: Should we do all of the images in $(IMAGES_TO_BUILD)?
+_FLAG_PARTITIONS := product system system_ext vendor
+
+
+# -----------------------------------------------------------------
+# Release Config Flags
+
+# Create a summary file of build flags for each partition
+# $(1): built build flags json file
+# $(2): installed build flags json file
+# $(3): flag names
+define generate-partition-build-flag-file
+$(eval $(strip $(1)): PRIVATE_OUT := $(strip $(1)))
+$(eval $(strip $(1)): PRIVATE_FLAG_NAMES := $(strip $(3)))
+$(strip $(1)):
+ mkdir -p $$(dir $$(PRIVATE_OUT))
+ echo '{' > $$(PRIVATE_OUT)
+ echo '"flags": [' >> $$(PRIVATE_OUT)
+ $$(foreach flag, $$(PRIVATE_FLAG_NAMES), \
+ ( \
+ printf ' { "name": "%s", "value": "%s", ' \
+ '$$(flag)' \
+ '$$(_ALL_RELEASE_FLAGS.$$(flag).VALUE)' \
+ ; \
+ printf '"set": "%s", "default": "%s", "declared": "%s" }' \
+ '$$(_ALL_RELEASE_FLAGS.$$(flag).SET_IN)' \
+ '$$(_ALL_RELEASE_FLAGS.$$(flag).DEFAULT)' \
+ '$$(_ALL_RELEASE_FLAGS.$$(flag).DECLARED_IN)' \
+ ; \
+ printf '$$(if $$(filter $$(lastword $$(PRIVATE_FLAG_NAMES)),$$(flag)),,$$(comma))\n' ; \
+ ) >> $$(PRIVATE_OUT) ; \
+ )
+ echo "]" >> $$(PRIVATE_OUT)
+ echo "}" >> $$(PRIVATE_OUT)
+$(call copy-one-file, $(1), $(2))
+endef
+
+$(foreach partition, $(_FLAG_PARTITIONS), \
+ $(eval build_flag_summaries.$(partition) := $(PRODUCT_OUT)/$(partition)/etc/build_flags.json) \
+ $(eval $(call generate-partition-build-flag-file, \
+ $(TARGET_OUT_FLAGS)/$(partition)/build_flags.json, \
+ $(build_flag_summaries.$(partition)), \
+ $(_ALL_RELEASE_FLAGS.PARTITIONS.$(partition)) \
+ ) \
+ ) \
+)
+
+
+# -----------------------------------------------------------------
+# Aconfig Flags
+
+# Create a summary file of build flags for each partition
+# $(1): built aconfig flags textprot file (out)
+# $(2): installed aconfig flags textprot file (out)
+# $(3): input aconfig files for the partition (in)
+define generate-partition-aconfig-flag-file
+$(eval $(strip $(1)): PRIVATE_OUT := $(strip $(1)))
+$(eval $(strip $(1)): PRIVATE_IN := $(strip $(3)))
+$(strip $(1)): $(ACONFIG)
+ mkdir -p $$(dir $$(PRIVATE_OUT))
+ $$(if $$(PRIVATE_IN), \
+ $$(ACONFIG) dump --format textproto --out $$(PRIVATE_OUT) \
+ $$(addprefix --cache ,$$(PRIVATE_IN)), \
+ echo "# No aconfig flags" > $$(PRIVATE_OUT) \
+ )
+$(call copy-one-file, $(1), $(2))
+endef
+
+
+$(foreach partition, $(_FLAG_PARTITIONS), \
+ $(eval aconfig_flag_summaries.$(partition) := $(PRODUCT_OUT)/$(partition)/etc/aconfig_flags.textproto) \
+ $(eval $(call generate-partition-aconfig-flag-file, \
+ $(TARGET_OUT_FLAGS)/$(partition)/aconfig_flags.textproto, \
+ $(aconfig_flag_summaries.$(partition)), \
+ $(sort $(foreach m,$(call register-names-for-partition, $(partition)), \
+ $(ALL_MODULES.$(m).ACONFIG_FILES) \
+ )) \
+ )) \
+)
+
+
+# -----------------------------------------------------------------
+# Install the ones we need for the configured product
+required_flags_files := \
+ $(sort $(foreach partition, $(filter $(IMAGES_TO_BUILD), $(_FLAG_PARTITIONS)), \
+ $(build_flag_summaries.$(partition)) \
+ $(aconfig_flag_summaries.$(partition)) \
+ ))
+
+ALL_DEFAULT_INSTALLED_MODULES += $(required_flags_files)
+
+# TODO: Remove
+.PHONY: flag-files
+flag-files: $(required_flags_files)
+
+
+# Clean up
+required_flags_files:=
+$(foreach partition, $(_FLAG_PARTITIONS), \
+ $(eval build_flag_summaries.$(partition):=) \
+ $(eval aconfig_flag_summaries.$(partition):=) \
+)
+
diff --git a/tools/aconfig/Android.bp b/tools/aconfig/Android.bp
index c349907..a4ea7f4 100644
--- a/tools/aconfig/Android.bp
+++ b/tools/aconfig/Android.bp
@@ -67,7 +67,7 @@
],
}
-// integration tests: java
+// integration tests: general
aconfig_declarations {
name: "aconfig.test.flags",
@@ -91,8 +91,10 @@
],
}
+// integration tests: java
+
java_aconfig_library {
- name: "aconfig_test_java",
+ name: "aconfig_test_java_library",
aconfig_declarations: "aconfig.test.flags",
}
@@ -104,9 +106,30 @@
manifest: "tests/AndroidManifest.xml",
certificate: "platform",
static_libs: [
+ "aconfig_test_java_library",
"androidx.test.rules",
"testng",
- "aconfig_test_java",
],
test_suites: ["device-tests"],
}
+
+// integration tests: C++
+
+cc_aconfig_library {
+ name: "aconfig_test_cpp_library",
+ aconfig_declarations: "aconfig.test.flags",
+}
+
+cc_test {
+ name: "aconfig.test.cpp",
+ srcs: [
+ "tests/aconfig_test.cpp",
+ ],
+ static_libs: [
+ "aconfig_test_cpp_library",
+ "libgmock",
+ ],
+ shared_libs: [
+ "server_configurable_flags",
+ ],
+}
diff --git a/tools/aconfig/src/codegen_cpp.rs b/tools/aconfig/src/codegen_cpp.rs
index c17af1f..530af49 100644
--- a/tools/aconfig/src/codegen_cpp.rs
+++ b/tools/aconfig/src/codegen_cpp.rs
@@ -57,26 +57,6 @@
template: include_str!("../templates/cpp_source_file.template"),
dir: "",
},
- FileSpec {
- name: &format!("{}_flag_provider.h", header),
- template: match codegen_mode {
- CodegenMode::Production => {
- include_str!("../templates/cpp_prod_flag_provider.template")
- }
- CodegenMode::Test => include_str!("../templates/cpp_test_flag_provider.template"),
- },
- dir: "",
- },
- FileSpec {
- name: &format!("{}_c.h", header),
- template: include_str!("../templates/c_exported_header.template"),
- dir: "include",
- },
- FileSpec {
- name: &format!("{}_c.cc", header),
- template: include_str!("../templates/c_source_file.template"),
- dir: "",
- },
];
files.iter().map(|file| generate_file(file, &context)).collect()
}
@@ -138,12 +118,13 @@
const EXPORTED_PROD_HEADER_EXPECTED: &str = r#"
#pragma once
+#ifdef __cplusplus
+
#include <memory>
namespace com::android::aconfig::test {
class flag_provider_interface {
public:
-
virtual ~flag_provider_interface() = default;
virtual bool disabled_ro() = 0;
@@ -174,14 +155,32 @@
}
}
+
+extern "C" {
+#endif // __cplusplus
+
+bool com_android_aconfig_test_disabled_ro();
+
+bool com_android_aconfig_test_disabled_rw();
+
+bool com_android_aconfig_test_enabled_ro();
+
+bool com_android_aconfig_test_enabled_rw();
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
"#;
const EXPORTED_TEST_HEADER_EXPECTED: &str = r#"
#pragma once
+#ifdef __cplusplus
+
#include <memory>
namespace com::android::aconfig::test {
+
class flag_provider_interface {
public:
@@ -245,164 +244,9 @@
}
}
-"#;
- const PROD_FLAG_PROVIDER_HEADER_EXPECTED: &str = r#"
-#pragma once
-
-#include "com_android_aconfig_test.h"
-#include <server_configurable_flags/get_flags.h>
-
-namespace com::android::aconfig::test {
-class flag_provider : public flag_provider_interface {
-public:
-
- virtual bool disabled_ro() override {
- return false;
- }
-
- virtual bool disabled_rw() override {
- return server_configurable_flags::GetServerConfigurableFlag(
- "aconfig_test",
- "com.android.aconfig.test.disabled_rw",
- "false") == "true";
- }
-
- virtual bool enabled_ro() override {
- return true;
- }
-
- virtual bool enabled_rw() override {
- return server_configurable_flags::GetServerConfigurableFlag(
- "aconfig_test",
- "com.android.aconfig.test.enabled_rw",
- "true") == "true";
- }
-};
-}
-"#;
-
- const TEST_FLAG_PROVIDER_HEADER_EXPECTED: &str = r#"
-#pragma once
-
-#include "com_android_aconfig_test.h"
-#include <server_configurable_flags/get_flags.h>
-
-#include <unordered_map>
-#include <string>
-
-namespace com::android::aconfig::test {
-class flag_provider : public flag_provider_interface {
-private:
- std::unordered_map<std::string, bool> overrides_;
-
-public:
-
- flag_provider()
- : overrides_()
- {}
-
- virtual bool disabled_ro() override {
- auto it = overrides_.find("disabled_ro");
- if (it != overrides_.end()) {
- return it->second;
- } else {
- return false;
- }
- }
-
- virtual void disabled_ro(bool val) override {
- overrides_["disabled_ro"] = val;
- }
-
- virtual bool disabled_rw() override {
- auto it = overrides_.find("disabled_rw");
- if (it != overrides_.end()) {
- return it->second;
- } else {
- return server_configurable_flags::GetServerConfigurableFlag(
- "aconfig_test",
- "com.android.aconfig.test.disabled_rw",
- "false") == "true";
- }
- }
-
- virtual void disabled_rw(bool val) override {
- overrides_["disabled_rw"] = val;
- }
-
- virtual bool enabled_ro() override {
- auto it = overrides_.find("enabled_ro");
- if (it != overrides_.end()) {
- return it->second;
- } else {
- return true;
- }
- }
-
- virtual void enabled_ro(bool val) override {
- overrides_["enabled_ro"] = val;
- }
-
- virtual bool enabled_rw() override {
- auto it = overrides_.find("enabled_rw");
- if (it != overrides_.end()) {
- return it->second;
- } else {
- return server_configurable_flags::GetServerConfigurableFlag(
- "aconfig_test",
- "com.android.aconfig.test.enabled_rw",
- "true") == "true";
- }
- }
-
- virtual void enabled_rw(bool val) override {
- overrides_["enabled_rw"] = val;
- }
-
- virtual void reset_flags() override {
- overrides_.clear();
- }
-};
-}
-"#;
-
- const SOURCE_FILE_EXPECTED: &str = r#"
-#include "com_android_aconfig_test.h"
-#include "com_android_aconfig_test_flag_provider.h"
-
-namespace com::android::aconfig::test {
- std::unique_ptr<flag_provider_interface> provider_ =
- std::make_unique<flag_provider>();
-}
-"#;
-
- const C_EXPORTED_PROD_HEADER_EXPECTED: &str = r#"
-#pragma once
-
-#ifdef __cplusplus
extern "C" {
-#endif
-
-bool com_android_aconfig_test_disabled_ro();
-
-bool com_android_aconfig_test_disabled_rw();
-
-bool com_android_aconfig_test_enabled_ro();
-
-bool com_android_aconfig_test_enabled_rw();
-
-#ifdef __cplusplus
-}
-#endif
-"#;
-
- const C_EXPORTED_TEST_HEADER_EXPECTED: &str = r#"
-#pragma once
-
-#ifdef __cplusplus
-extern "C" {
-#endif
+#endif // __cplusplus
bool com_android_aconfig_test_disabled_ro();
@@ -422,14 +266,50 @@
void com_android_aconfig_test_reset_flags();
+
#ifdef __cplusplus
-}
+} // extern "C"
#endif
+
+
"#;
- const C_PROD_SOURCE_FILE_EXPECTED: &str = r#"
-#include "com_android_aconfig_test_c.h"
+ const PROD_SOURCE_FILE_EXPECTED: &str = r#"
#include "com_android_aconfig_test.h"
+#include <server_configurable_flags/get_flags.h>
+
+namespace com::android::aconfig::test {
+
+ class flag_provider : public flag_provider_interface {
+ public:
+
+ virtual bool disabled_ro() override {
+ return false;
+ }
+
+ virtual bool disabled_rw() override {
+ return server_configurable_flags::GetServerConfigurableFlag(
+ "aconfig_test",
+ "com.android.aconfig.test.disabled_rw",
+ "false") == "true";
+ }
+
+ virtual bool enabled_ro() override {
+ return true;
+ }
+
+ virtual bool enabled_rw() override {
+ return server_configurable_flags::GetServerConfigurableFlag(
+ "aconfig_test",
+ "com.android.aconfig.test.enabled_rw",
+ "true") == "true";
+ }
+
+ };
+
+ std::unique_ptr<flag_provider_interface> provider_ =
+ std::make_unique<flag_provider>();
+}
bool com_android_aconfig_test_disabled_ro() {
return false;
@@ -446,16 +326,97 @@
bool com_android_aconfig_test_enabled_rw() {
return com::android::aconfig::test::enabled_rw();
}
+
"#;
- const C_TEST_SOURCE_FILE_EXPECTED: &str = r#"
-#include "com_android_aconfig_test_c.h"
+ const TEST_SOURCE_FILE_EXPECTED: &str = r#"
#include "com_android_aconfig_test.h"
+#include <server_configurable_flags/get_flags.h>
+
+namespace com::android::aconfig::test {
+
+ class flag_provider : public flag_provider_interface {
+ private:
+ std::unordered_map<std::string, bool> overrides_;
+
+ public:
+ flag_provider()
+ : overrides_()
+ {}
+
+ virtual bool disabled_ro() override {
+ auto it = overrides_.find("disabled_ro");
+ if (it != overrides_.end()) {
+ return it->second;
+ } else {
+ return false;
+ }
+ }
+
+ virtual void disabled_ro(bool val) override {
+ overrides_["disabled_ro"] = val;
+ }
+
+ virtual bool disabled_rw() override {
+ auto it = overrides_.find("disabled_rw");
+ if (it != overrides_.end()) {
+ return it->second;
+ } else {
+ return server_configurable_flags::GetServerConfigurableFlag(
+ "aconfig_test",
+ "com.android.aconfig.test.disabled_rw",
+ "false") == "true";
+ }
+ }
+
+ virtual void disabled_rw(bool val) override {
+ overrides_["disabled_rw"] = val;
+ }
+
+ virtual bool enabled_ro() override {
+ auto it = overrides_.find("enabled_ro");
+ if (it != overrides_.end()) {
+ return it->second;
+ } else {
+ return true;
+ }
+ }
+
+ virtual void enabled_ro(bool val) override {
+ overrides_["enabled_ro"] = val;
+ }
+
+ virtual bool enabled_rw() override {
+ auto it = overrides_.find("enabled_rw");
+ if (it != overrides_.end()) {
+ return it->second;
+ } else {
+ return server_configurable_flags::GetServerConfigurableFlag(
+ "aconfig_test",
+ "com.android.aconfig.test.enabled_rw",
+ "true") == "true";
+ }
+ }
+
+ virtual void enabled_rw(bool val) override {
+ overrides_["enabled_rw"] = val;
+ }
+
+
+ virtual void reset_flags() override {
+ overrides_.clear();
+ }
+ };
+
+ std::unique_ptr<flag_provider_interface> provider_ =
+ std::make_unique<flag_provider>();
+}
bool com_android_aconfig_test_disabled_ro() {
return com::android::aconfig::test::disabled_ro();
}
+
void set_com_android_aconfig_test_disabled_ro(bool val) {
com::android::aconfig::test::disabled_ro(val);
}
@@ -464,6 +425,7 @@
return com::android::aconfig::test::disabled_rw();
}
+
void set_com_android_aconfig_test_disabled_rw(bool val) {
com::android::aconfig::test::disabled_rw(val);
}
@@ -472,6 +434,7 @@
return com::android::aconfig::test::enabled_ro();
}
+
void set_com_android_aconfig_test_enabled_ro(bool val) {
com::android::aconfig::test::enabled_ro(val);
}
@@ -480,14 +443,17 @@
return com::android::aconfig::test::enabled_rw();
}
+
void set_com_android_aconfig_test_enabled_rw(bool val) {
com::android::aconfig::test::enabled_rw(val);
}
void com_android_aconfig_test_reset_flags() {
- com::android::aconfig::test::reset_flags();
+ com::android::aconfig::test::reset_flags();
}
+
"#;
+
fn test_generate_cpp_code(mode: CodegenMode) {
let parsed_flags = crate::test::parse_test_flags();
let generated =
@@ -514,50 +480,14 @@
)
);
- target_file_path = String::from("com_android_aconfig_test_flag_provider.h");
- assert!(generated_files_map.contains_key(&target_file_path));
- assert_eq!(
- None,
- crate::test::first_significant_code_diff(
- match mode {
- CodegenMode::Production => PROD_FLAG_PROVIDER_HEADER_EXPECTED,
- CodegenMode::Test => TEST_FLAG_PROVIDER_HEADER_EXPECTED,
- },
- generated_files_map.get(&target_file_path).unwrap()
- )
- );
-
target_file_path = String::from("com_android_aconfig_test.cc");
assert!(generated_files_map.contains_key(&target_file_path));
assert_eq!(
None,
crate::test::first_significant_code_diff(
- SOURCE_FILE_EXPECTED,
- generated_files_map.get(&target_file_path).unwrap()
- )
- );
-
- target_file_path = String::from("include/com_android_aconfig_test_c.h");
- assert!(generated_files_map.contains_key(&target_file_path));
- assert_eq!(
- None,
- crate::test::first_significant_code_diff(
match mode {
- CodegenMode::Production => C_EXPORTED_PROD_HEADER_EXPECTED,
- CodegenMode::Test => C_EXPORTED_TEST_HEADER_EXPECTED,
- },
- generated_files_map.get(&target_file_path).unwrap()
- )
- );
-
- target_file_path = String::from("com_android_aconfig_test_c.cc");
- assert!(generated_files_map.contains_key(&target_file_path));
- assert_eq!(
- None,
- crate::test::first_significant_code_diff(
- match mode {
- CodegenMode::Production => C_PROD_SOURCE_FILE_EXPECTED,
- CodegenMode::Test => C_TEST_SOURCE_FILE_EXPECTED,
+ CodegenMode::Production => PROD_SOURCE_FILE_EXPECTED,
+ CodegenMode::Test => TEST_SOURCE_FILE_EXPECTED,
},
generated_files_map.get(&target_file_path).unwrap()
)
diff --git a/tools/aconfig/src/codegen_rust.rs b/tools/aconfig/src/codegen_rust.rs
index 45303ce..053cebc 100644
--- a/tools/aconfig/src/codegen_rust.rs
+++ b/tools/aconfig/src/codegen_rust.rs
@@ -92,7 +92,7 @@
//! codegenerated rust flag lib
/// flag provider
-pub struct FlagProvider
+pub struct FlagProvider;
impl FlagProvider {
/// query flag disabled_ro
diff --git a/tools/aconfig/src/commands.rs b/tools/aconfig/src/commands.rs
index 0ac84b2..4f0a706 100644
--- a/tools/aconfig/src/commands.rs
+++ b/tools/aconfig/src/commands.rs
@@ -127,6 +127,8 @@
}
}
+ // Create a sorted parsed_flags
+ crate::protos::parsed_flags::sort_parsed_flags(&mut parsed_flags);
crate::protos::parsed_flags::verify_fields(&parsed_flags)?;
let mut output = Vec::new();
parsed_flags.write_to_vec(&mut output)?;
@@ -211,7 +213,7 @@
#[derive(Copy, Clone, Debug, PartialEq, Eq, ValueEnum)]
pub enum DumpFormat {
Text,
- Debug,
+ Verbose,
Protobuf,
Textproto,
}
@@ -227,18 +229,27 @@
DumpFormat::Text => {
for parsed_flag in parsed_flags.parsed_flag.into_iter() {
let line = format!(
- "{}/{}: {:?} {:?}\n",
+ "{}/{}: {:?} + {:?}\n",
parsed_flag.package(),
parsed_flag.name(),
- parsed_flag.state(),
- parsed_flag.permission()
+ parsed_flag.permission(),
+ parsed_flag.state()
);
output.extend_from_slice(line.as_bytes());
}
}
- DumpFormat::Debug => {
+ DumpFormat::Verbose => {
for parsed_flag in parsed_flags.parsed_flag.into_iter() {
- let line = format!("{:#?}\n", parsed_flag);
+ let sources: Vec<_> =
+ parsed_flag.trace.iter().map(|tracepoint| tracepoint.source()).collect();
+ let line = format!(
+ "{}/{}: {:?} + {:?} ({})\n",
+ parsed_flag.package(),
+ parsed_flag.name(),
+ parsed_flag.permission(),
+ parsed_flag.state(),
+ sources.join(", ")
+ );
output.extend_from_slice(line.as_bytes());
}
}
@@ -324,7 +335,7 @@
let input = parse_test_flags_as_input();
let bytes = dump_parsed_flags(vec![input], DumpFormat::Text).unwrap();
let text = std::str::from_utf8(&bytes).unwrap();
- assert!(text.contains("com.android.aconfig.test/disabled_ro: DISABLED READ_ONLY"));
+ assert!(text.contains("com.android.aconfig.test/disabled_ro: READ_ONLY + DISABLED"));
}
#[test]
diff --git a/tools/aconfig/src/protos.rs b/tools/aconfig/src/protos.rs
index a621b87..4ddada7 100644
--- a/tools/aconfig/src/protos.rs
+++ b/tools/aconfig/src/protos.rs
@@ -255,6 +255,10 @@
Ok(merged)
}
+ pub fn sort_parsed_flags(pf: &mut ProtoParsedFlags) {
+ pf.parsed_flag.sort_by_key(create_sorting_key);
+ }
+
fn create_sorting_key(pf: &ProtoParsedFlag) -> String {
format!("{}.{}", pf.package(), pf.name())
}
diff --git a/tools/aconfig/templates/c_exported_header.template b/tools/aconfig/templates/c_exported_header.template
deleted file mode 100644
index ca812a7..0000000
--- a/tools/aconfig/templates/c_exported_header.template
+++ /dev/null
@@ -1,21 +0,0 @@
-#pragma once
-
-#ifdef __cplusplus
-extern "C" \{
-#endif
-
-{{ for item in class_elements }}
-bool {header}_{item.flag_name}();
-
-{{ if for_test }}
-void set_{header}_{item.flag_name}(bool val);
-{{ -endif }}
-{{ endfor - }}
-
-{{ if for_test }}
-void {header}_reset_flags();
-{{ -endif }}
-
-#ifdef __cplusplus
-}
-#endif
diff --git a/tools/aconfig/templates/c_source_file.template b/tools/aconfig/templates/c_source_file.template
deleted file mode 100644
index 384221d..0000000
--- a/tools/aconfig/templates/c_source_file.template
+++ /dev/null
@@ -1,28 +0,0 @@
-#include "{header}_c.h"
-#include "{header}.h"
-
-{{ for item in class_elements}}
-bool {header}_{item.flag_name}() \{
- {{ if for_test }}
- return {cpp_namespace}::{item.flag_name}();
- {{ -else- }}
- {{ if not item.readwrite- }}
- return {item.default_value};
- {{ -else- }}
- return {cpp_namespace}::{item.flag_name}();
- {{ -endif }}
- {{ -endif }}
-}
-
-{{ if for_test }}
-void set_{header}_{item.flag_name}(bool val) \{
- {cpp_namespace}::{item.flag_name}(val);
-}
-{{ -endif }}
-{{ endfor -}}
-
-{{ if for_test }}
-void {header}_reset_flags() \{
- {cpp_namespace}::reset_flags();
-}
-{{ -endif }}
diff --git a/tools/aconfig/templates/cpp_exported_header.template b/tools/aconfig/templates/cpp_exported_header.template
index cd01853..4d56dbc 100644
--- a/tools/aconfig/templates/cpp_exported_header.template
+++ b/tools/aconfig/templates/cpp_exported_header.template
@@ -1,5 +1,7 @@
#pragma once
+#ifdef __cplusplus
+
#include <memory>
namespace {cpp_namespace} \{
@@ -47,4 +49,25 @@
return provider_->reset_flags();
}
{{ -endif }}
+
}
+
+extern "C" \{
+#endif // __cplusplus
+
+{{ for item in class_elements }}
+bool {header}_{item.flag_name}();
+
+{{ if for_test }}
+void set_{header}_{item.flag_name}(bool val);
+{{ -endif }}
+{{ endfor - }}
+
+{{ if for_test }}
+void {header}_reset_flags();
+{{ -endif }}
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
+
diff --git a/tools/aconfig/templates/cpp_prod_flag_provider.template b/tools/aconfig/templates/cpp_prod_flag_provider.template
deleted file mode 100644
index f908f12..0000000
--- a/tools/aconfig/templates/cpp_prod_flag_provider.template
+++ /dev/null
@@ -1,24 +0,0 @@
-#pragma once
-
-#include "{header}.h"
-{{ if readwrite }}
-#include <server_configurable_flags/get_flags.h>
-{{ endif }}
-
-namespace {cpp_namespace} \{
-class flag_provider : public flag_provider_interface \{
-public:
- {{ for item in class_elements}}
- virtual bool {item.flag_name}() override \{
- {{ if item.readwrite- }}
- return server_configurable_flags::GetServerConfigurableFlag(
- "{item.device_config_namespace}",
- "{item.device_config_flag}",
- "{item.default_value}") == "true";
- {{ -else- }}
- return {item.default_value};
- {{ -endif }}
- }
- {{ endfor }}
-};
-}
diff --git a/tools/aconfig/templates/cpp_source_file.template b/tools/aconfig/templates/cpp_source_file.template
index d267f03..289e299 100644
--- a/tools/aconfig/templates/cpp_source_file.template
+++ b/tools/aconfig/templates/cpp_source_file.template
@@ -1,8 +1,98 @@
-
#include "{header}.h"
-#include "{header}_flag_provider.h"
+{{ if readwrite }}
+#include <server_configurable_flags/get_flags.h>
+{{ endif }}
namespace {cpp_namespace} \{
+
+{{ if for_test }}
+ class flag_provider : public flag_provider_interface \{
+ private:
+ std::unordered_map<std::string, bool> overrides_;
+
+ public:
+ flag_provider()
+ : overrides_()
+ \{}
+
+ {{ for item in class_elements}}
+ virtual bool {item.flag_name}() override \{
+ auto it = overrides_.find("{item.flag_name}");
+ if (it != overrides_.end()) \{
+ return it->second;
+ } else \{
+ {{ if item.readwrite- }}
+ return server_configurable_flags::GetServerConfigurableFlag(
+ "{item.device_config_namespace}",
+ "{item.device_config_flag}",
+ "{item.default_value}") == "true";
+ {{ -else- }}
+ return {item.default_value};
+ {{ -endif }}
+ }
+ }
+
+ virtual void {item.flag_name}(bool val) override \{
+ overrides_["{item.flag_name}"] = val;
+ }
+ {{ endfor }}
+
+ virtual void reset_flags() override \{
+ overrides_.clear();
+ }
+ };
+
+{{ -else- }}
+
+ class flag_provider : public flag_provider_interface \{
+ public:
+ {{ for item in class_elements}}
+ virtual bool {item.flag_name}() override \{
+ {{ if item.readwrite- }}
+ return server_configurable_flags::GetServerConfigurableFlag(
+ "{item.device_config_namespace}",
+ "{item.device_config_flag}",
+ "{item.default_value}") == "true";
+ {{ -else- }}
+ return {item.default_value};
+ {{ -endif }}
+ }
+ {{ endfor }}
+ };
+
+
+{{ -endif }}
+
+
std::unique_ptr<flag_provider_interface> provider_ =
std::make_unique<flag_provider>();
+
}
+
+
+{{ for item in class_elements}}
+bool {header}_{item.flag_name}() \{
+ {{ if for_test }}
+ return {cpp_namespace}::{item.flag_name}();
+ {{ -else- }}
+ {{ if not item.readwrite- }}
+ return {item.default_value};
+ {{ -else- }}
+ return {cpp_namespace}::{item.flag_name}();
+ {{ -endif }}
+ {{ -endif }}
+}
+
+{{ if for_test }}
+void set_{header}_{item.flag_name}(bool val) \{
+ {cpp_namespace}::{item.flag_name}(val);
+}
+{{ -endif }}
+{{ endfor -}}
+
+{{ if for_test }}
+void {header}_reset_flags() \{
+ {cpp_namespace}::reset_flags();
+}
+{{ -endif }}
+
diff --git a/tools/aconfig/templates/cpp_test_flag_provider.template b/tools/aconfig/templates/cpp_test_flag_provider.template
deleted file mode 100644
index 03f10a5..0000000
--- a/tools/aconfig/templates/cpp_test_flag_provider.template
+++ /dev/null
@@ -1,48 +0,0 @@
-#pragma once
-
-#include "{header}.h"
-
-{{ if readwrite }}
-#include <server_configurable_flags/get_flags.h>
-{{ endif }}
-
-#include <unordered_map>
-#include <string>
-
-namespace {cpp_namespace} \{
-class flag_provider : public flag_provider_interface \{
-private:
- std::unordered_map<std::string, bool> overrides_;
-
-public:
- flag_provider()
- : overrides_()
- \{}
-
- {{ for item in class_elements}}
- virtual bool {item.flag_name}() override \{
- auto it = overrides_.find("{item.flag_name}");
- if (it != overrides_.end()) \{
- return it->second;
- } else \{
- {{ if item.readwrite- }}
- return server_configurable_flags::GetServerConfigurableFlag(
- "{item.device_config_namespace}",
- "{item.device_config_flag}",
- "{item.default_value}") == "true";
- {{ -else- }}
- return {item.default_value};
- {{ -endif }}
- }
- }
-
- virtual void {item.flag_name}(bool val) override \{
- overrides_["{item.flag_name}"] = val;
- }
- {{ endfor }}
-
- virtual void reset_flags() override \{
- overrides_.clear();
- }
-};
-}
diff --git a/tools/aconfig/templates/rust_prod.template b/tools/aconfig/templates/rust_prod.template
index 543107e..d518694 100644
--- a/tools/aconfig/templates/rust_prod.template
+++ b/tools/aconfig/templates/rust_prod.template
@@ -1,7 +1,7 @@
//! codegenerated rust flag lib
/// flag provider
-pub struct FlagProvider
+pub struct FlagProvider;
impl FlagProvider \{
diff --git a/tools/aconfig/tests/AconfigTest.java b/tools/aconfig/tests/AconfigTest.java
index 778a4c6..6681f32 100644
--- a/tools/aconfig/tests/AconfigTest.java
+++ b/tools/aconfig/tests/AconfigTest.java
@@ -1,7 +1,12 @@
+import static com.android.aconfig.test.Flags.FLAG_DISABLED_RO;
+import static com.android.aconfig.test.Flags.FLAG_DISABLED_RW;
+import static com.android.aconfig.test.Flags.FLAG_ENABLED_RO;
+import static com.android.aconfig.test.Flags.FLAG_ENABLED_RW;
import static com.android.aconfig.test.Flags.disabledRo;
import static com.android.aconfig.test.Flags.disabledRw;
import static com.android.aconfig.test.Flags.enabledRo;
import static com.android.aconfig.test.Flags.enabledRw;
+import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
@@ -13,11 +18,13 @@
public final class AconfigTest {
@Test
public void testDisabledReadOnlyFlag() {
+ assertEquals("com.android.aconfig.test.disabled_ro", FLAG_DISABLED_RO);
assertFalse(disabledRo());
}
@Test
public void testEnabledReadOnlyFlag() {
+ assertEquals("com.android.aconfig.test.disabled_rw", FLAG_DISABLED_RW);
// TODO: change to assertTrue(enabledRo()) when the build supports reading tests/*.values
// (currently all flags are assigned the default READ_ONLY + DISABLED)
assertFalse(enabledRo());
@@ -25,11 +32,13 @@
@Test
public void testDisabledReadWriteFlag() {
+ assertEquals("com.android.aconfig.test.enabled_ro", FLAG_ENABLED_RO);
assertFalse(disabledRw());
}
@Test
public void testEnabledReadWriteFlag() {
+ assertEquals("com.android.aconfig.test.enabled_rw", FLAG_ENABLED_RW);
// TODO: change to assertTrue(enabledRw()) when the build supports reading tests/*.values
// (currently all flags are assigned the default READ_ONLY + DISABLED)
assertFalse(enabledRw());
diff --git a/tools/aconfig/tests/aconfig_test.cpp b/tools/aconfig/tests/aconfig_test.cpp
new file mode 100644
index 0000000..10de347
--- /dev/null
+++ b/tools/aconfig/tests/aconfig_test.cpp
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ */
+
+#include "com_android_aconfig_test.h"
+#include "gtest/gtest.h"
+
+TEST(AconfigTest, TestDisabledReadOnlyFlag) {
+ ASSERT_FALSE(com_android_aconfig_test_disabled_ro());
+}
+
+TEST(AconfigTest, TestEnabledReadOnlyFlag) {
+ // TODO: change to assertTrue(enabledRo()) when the build supports reading tests/*.values
+ // (currently all flags are assigned the default READ_ONLY + DISABLED)
+ ASSERT_FALSE(com_android_aconfig_test_enabled_ro());
+}
+
+TEST(AconfigTest, TestDisabledReadWriteFlag) {
+ ASSERT_FALSE(com_android_aconfig_test_disabled_rw());
+}
+
+TEST(AconfigTest, TestEnabledReadWriteFlag) {
+ // TODO: change to assertTrue(enabledRo()) when the build supports reading tests/*.values
+ // (currently all flags are assigned the default READ_ONLY + DISABLED)
+ ASSERT_FALSE(com_android_aconfig_test_enabled_rw());
+}
+
+int main(int argc, char** argv) {
+ ::testing::InitGoogleTest(&argc, argv);
+ return RUN_ALL_TESTS();
+}
diff --git a/tools/aconfig/tests/test.aconfig b/tools/aconfig/tests/test.aconfig
index a8f6652..d7ac919 100644
--- a/tools/aconfig/tests/test.aconfig
+++ b/tools/aconfig/tests/test.aconfig
@@ -2,25 +2,6 @@
# This flag's final value is calculated from:
# - test.aconfig: DISABLED + READ_WRITE (default)
-# - first.values: DISABLED + READ_ONLY
-flag {
- name: "disabled_ro"
- namespace: "aconfig_test"
- description: "This flag is DISABLED + READ_ONLY"
- bug: "123"
-}
-
-# This flag's final value is calculated from:
-# - test.aconfig: DISABLED + READ_WRITE (default)
-flag {
- name: "disabled_rw"
- namespace: "aconfig_test"
- description: "This flag is DISABLED + READ_WRITE"
- bug: "456"
-}
-
-# This flag's final value is calculated from:
-# - test.aconfig: DISABLED + READ_WRITE (default)
# - first.values: DISABLED + READ_WRITE
# - second.values: ENABLED + READ_ONLY
flag {
@@ -40,3 +21,22 @@
description: "This flag is ENABLED + READ_WRITE"
# no bug field: bug is not mandatory
}
+
+# This flag's final value is calculated from:
+# - test.aconfig: DISABLED + READ_WRITE (default)
+# - first.values: DISABLED + READ_ONLY
+flag {
+ name: "disabled_ro"
+ namespace: "aconfig_test"
+ description: "This flag is DISABLED + READ_ONLY"
+ bug: "123"
+}
+
+# This flag's final value is calculated from:
+# - test.aconfig: DISABLED + READ_WRITE (default)
+flag {
+ name: "disabled_rw"
+ namespace: "aconfig_test"
+ description: "This flag is DISABLED + READ_WRITE"
+ bug: "456"
+}