From afe55106e57111f57014f952a469a22b19a94603 Mon Sep 17 00:00:00 2001 From: Ted Bauer Date: Mon, 13 Nov 2023 19:06:36 +0000 Subject: Cache Java codegen'd flags in static member variables. By caching flag values directly in member variables instead of caching a HashMap and accessing that, flag reads avoid `hashCode()`, map lookup, and Boolean.parse runtime costs. Flag reads are turning out to have performance problems in hot paths, so this should help to alleviate that. Bug: 309625014 Test: m Change-Id: I923bf6af2ae3fcbbf2fee7126b492a47cd6049ad --- tools/aconfig/src/codegen_java.rs | 80 +++++++++++++++++++-------------------- 1 file changed, 39 insertions(+), 41 deletions(-) (limited to 'tools/aconfig/src/codegen_java.rs') diff --git a/tools/aconfig/src/codegen_java.rs b/tools/aconfig/src/codegen_java.rs index 05ee0d759f..954eccc8f6 100644 --- a/tools/aconfig/src/codegen_java.rs +++ b/tools/aconfig/src/codegen_java.rs @@ -15,6 +15,7 @@ */ use anyhow::Result; +use itertools::Itertools; use serde::Serialize; use std::collections::BTreeSet; use std::path::PathBuf; @@ -34,12 +35,18 @@ where { let flag_elements: Vec = parsed_flags_iter.map(|pf| create_flag_element(package, pf)).collect(); + let namespace_set: BTreeSet = flag_elements + .iter() + .unique_by(|f| &f.device_config_namespace) + .map(|f| f.device_config_namespace.clone()) + .collect(); let properties_set: BTreeSet = flag_elements.iter().map(|fe| format_property_name(&fe.device_config_namespace)).collect(); let is_read_write = flag_elements.iter().any(|elem| elem.is_read_write); let is_test_mode = codegen_mode == CodegenMode::Test; let context = Context { flag_elements, + namespace_set, is_test_mode, is_read_write, properties_set, @@ -75,6 +82,7 @@ where #[derive(Serialize)] struct Context { pub flag_elements: Vec, + pub namespace_set: BTreeSet, pub is_test_mode: bool, pub is_read_write: bool, pub properties_set: BTreeSet, @@ -289,7 +297,31 @@ mod tests { import android.provider.DeviceConfig.Properties; /** @hide */ public final class FeatureFlagsImpl implements FeatureFlags { - private Properties mPropertiesAconfigTest; + private static boolean aconfig_test_is_cached = false; + private static boolean disabledRw = false; + private static boolean enabledRw = true; + + + private void load_overrides_aconfig_test() { + try { + Properties properties = DeviceConfig.getProperties("aconfig_test"); + disabledRw = + properties.getBoolean("com.android.aconfig.test.disabled_rw", false); + enabledRw = + properties.getBoolean("com.android.aconfig.test.enabled_rw", true); + } catch (NullPointerException e) { + throw new RuntimeException( + "Cannot read value from namespace aconfig_test " + + "from DeviceConfig. It could be that the code using flag " + + "executed before SettingsProvider initialization. Please use " + + "fixed read-only flag by adding is_fixed_read_only: true in " + + "flag declaration.", + e + ); + } + aconfig_test_is_cached = true; + } + @Override @UnsupportedAppUsage public boolean disabledRo() { @@ -298,18 +330,10 @@ mod tests { @Override @UnsupportedAppUsage public boolean disabledRw() { - if (mPropertiesAconfigTest == null) { - mPropertiesAconfigTest = - getProperties( - "aconfig_test", - "com.android.aconfig.test.disabled_rw" - ); + if (!aconfig_test_is_cached) { + load_overrides_aconfig_test(); } - return mPropertiesAconfigTest - .getBoolean( - "com.android.aconfig.test.disabled_rw", - false - ); + return disabledRw; } @Override @UnsupportedAppUsage @@ -324,36 +348,10 @@ mod tests { @Override @UnsupportedAppUsage public boolean enabledRw() { - if (mPropertiesAconfigTest == null) { - mPropertiesAconfigTest = - getProperties( - "aconfig_test", - "com.android.aconfig.test.enabled_rw" - ); - } - return mPropertiesAconfigTest - .getBoolean( - "com.android.aconfig.test.enabled_rw", - true - ); - } - private Properties getProperties( - String namespace, - String flagName) { - Properties properties = null; - try { - properties = DeviceConfig.getProperties(namespace); - } catch (NullPointerException e) { - throw new RuntimeException( - "Cannot read value of flag " + flagName + " from DeviceConfig. " - + "It could be that the code using flag executed " - + "before SettingsProvider initialization. " - + "Please use fixed read-only flag by adding " - + "is_fixed_read_only: true in flag declaration.", - e - ); + if (!aconfig_test_is_cached) { + load_overrides_aconfig_test(); } - return properties; + return enabledRw; } } "#; -- cgit v1.2.3-59-g8ed1b