Revert^2 "[res] Don't recalculate configuration twice on init"
This reverts commit d38bd5180b2e39c48a5e3ffd1ea420a747a26d17.
Reason for revert: Forward fix
Bug: 282215580
Bug: 324939476
Change-Id: Ia919e3a7e7188900e4e98c82d3b3f295fb51ca39
diff --git a/core/java/android/app/ResourcesManager.java b/core/java/android/app/ResourcesManager.java
index 24a5157..6255260 100644
--- a/core/java/android/app/ResourcesManager.java
+++ b/core/java/android/app/ResourcesManager.java
@@ -550,7 +550,7 @@
@UnsupportedAppUsage
protected @Nullable AssetManager createAssetManager(@NonNull final ResourcesKey key,
@Nullable ApkAssetsSupplier apkSupplier) {
- final AssetManager.Builder builder = new AssetManager.Builder();
+ final AssetManager.Builder builder = new AssetManager.Builder().setNoInit();
final ArrayList<ApkKey> apkKeys = extractApkKeys(key);
for (int i = 0, n = apkKeys.size(); i < n; i++) {
@@ -1555,7 +1555,7 @@
} else if(overlayPaths == null) {
return ArrayUtils.cloneOrNull(resourceDirs);
} else {
- final ArrayList<String> paths = new ArrayList<>();
+ final var paths = new ArrayList<String>(overlayPaths.length + resourceDirs.length);
for (final String path : overlayPaths) {
paths.add(path);
}
diff --git a/core/java/android/content/res/AssetManager.java b/core/java/android/content/res/AssetManager.java
index 23b9d0b..d259e97 100644
--- a/core/java/android/content/res/AssetManager.java
+++ b/core/java/android/content/res/AssetManager.java
@@ -137,6 +137,8 @@
private ArrayList<ApkAssets> mUserApkAssets = new ArrayList<>();
private ArrayList<ResourcesLoader> mLoaders = new ArrayList<>();
+ private boolean mNoInit = false;
+
public Builder addApkAssets(ApkAssets apkAssets) {
mUserApkAssets.add(apkAssets);
return this;
@@ -147,6 +149,11 @@
return this;
}
+ public Builder setNoInit() {
+ mNoInit = true;
+ return this;
+ }
+
public AssetManager build() {
// Retrieving the system ApkAssets forces their creation as well.
final ApkAssets[] systemApkAssets = getSystem().getApkAssets();
@@ -188,7 +195,7 @@
final AssetManager assetManager = new AssetManager(false /*sentinel*/);
assetManager.mApkAssets = apkAssets;
AssetManager.nativeSetApkAssets(assetManager.mObject, apkAssets,
- false /*invalidateCaches*/);
+ false /*invalidateCaches*/, mNoInit /*preset*/);
assetManager.mLoaders = mLoaders.isEmpty() ? null
: mLoaders.toArray(new ResourcesLoader[0]);
@@ -329,7 +336,7 @@
synchronized (this) {
ensureOpenLocked();
mApkAssets = newApkAssets;
- nativeSetApkAssets(mObject, mApkAssets, invalidateCaches);
+ nativeSetApkAssets(mObject, mApkAssets, invalidateCaches, false);
if (invalidateCaches) {
// Invalidate all caches.
invalidateCachesLocked(-1);
@@ -496,7 +503,7 @@
mApkAssets = Arrays.copyOf(mApkAssets, count + 1);
mApkAssets[count] = assets;
- nativeSetApkAssets(mObject, mApkAssets, true);
+ nativeSetApkAssets(mObject, mApkAssets, true, false);
invalidateCachesLocked(-1);
return count + 1;
}
@@ -1503,12 +1510,29 @@
int navigation, int screenWidth, int screenHeight, int smallestScreenWidthDp,
int screenWidthDp, int screenHeightDp, int screenLayout, int uiMode, int colorMode,
int grammaticalGender, int majorVersion) {
+ setConfigurationInternal(mcc, mnc, defaultLocale, locales, orientation,
+ touchscreen, density, keyboard, keyboardHidden, navigation, screenWidth,
+ screenHeight, smallestScreenWidthDp, screenWidthDp, screenHeightDp,
+ screenLayout, uiMode, colorMode, grammaticalGender, majorVersion, false);
+ }
+
+ /**
+ * Change the configuration used when retrieving resources, and potentially force a refresh of
+ * the state. Not for use by applications.
+ * @hide
+ */
+ void setConfigurationInternal(int mcc, int mnc, String defaultLocale, String[] locales,
+ int orientation, int touchscreen, int density, int keyboard, int keyboardHidden,
+ int navigation, int screenWidth, int screenHeight, int smallestScreenWidthDp,
+ int screenWidthDp, int screenHeightDp, int screenLayout, int uiMode, int colorMode,
+ int grammaticalGender, int majorVersion, boolean forceRefresh) {
synchronized (this) {
ensureValidLocked();
nativeSetConfiguration(mObject, mcc, mnc, defaultLocale, locales, orientation,
touchscreen, density, keyboard, keyboardHidden, navigation, screenWidth,
screenHeight, smallestScreenWidthDp, screenWidthDp, screenHeightDp,
- screenLayout, uiMode, colorMode, grammaticalGender, majorVersion);
+ screenLayout, uiMode, colorMode, grammaticalGender, majorVersion,
+ forceRefresh);
}
}
@@ -1593,13 +1617,13 @@
private static native long nativeCreate();
private static native void nativeDestroy(long ptr);
private static native void nativeSetApkAssets(long ptr, @NonNull ApkAssets[] apkAssets,
- boolean invalidateCaches);
+ boolean invalidateCaches, boolean preset);
private static native void nativeSetConfiguration(long ptr, int mcc, int mnc,
@Nullable String defaultLocale, @NonNull String[] locales, int orientation,
int touchscreen, int density, int keyboard, int keyboardHidden, int navigation,
int screenWidth, int screenHeight, int smallestScreenWidthDp, int screenWidthDp,
int screenHeightDp, int screenLayout, int uiMode, int colorMode, int grammaticalGender,
- int majorVersion);
+ int majorVersion, boolean forceRefresh);
private static native @NonNull SparseArray<String> nativeGetAssignedPackageIdentifiers(
long ptr, boolean includeOverlays, boolean includeLoaders);
diff --git a/core/java/android/content/res/ResourcesImpl.java b/core/java/android/content/res/ResourcesImpl.java
index 5e442b8..079c2c1 100644
--- a/core/java/android/content/res/ResourcesImpl.java
+++ b/core/java/android/content/res/ResourcesImpl.java
@@ -200,7 +200,7 @@
mMetrics.setToDefaults();
mDisplayAdjustments = displayAdjustments;
mConfiguration.setToDefaults();
- updateConfiguration(config, metrics, displayAdjustments.getCompatibilityInfo());
+ updateConfigurationImpl(config, metrics, displayAdjustments.getCompatibilityInfo(), true);
}
public DisplayAdjustments getDisplayAdjustments() {
@@ -402,7 +402,12 @@
}
public void updateConfiguration(Configuration config, DisplayMetrics metrics,
- CompatibilityInfo compat) {
+ CompatibilityInfo compat) {
+ updateConfigurationImpl(config, metrics, compat, false);
+ }
+
+ private void updateConfigurationImpl(Configuration config, DisplayMetrics metrics,
+ CompatibilityInfo compat, boolean forceAssetsRefresh) {
Trace.traceBegin(Trace.TRACE_TAG_RESOURCES, "ResourcesImpl#updateConfiguration");
try {
synchronized (mAccessLock) {
@@ -528,7 +533,7 @@
keyboardHidden = mConfiguration.keyboardHidden;
}
- mAssets.setConfiguration(mConfiguration.mcc, mConfiguration.mnc,
+ mAssets.setConfigurationInternal(mConfiguration.mcc, mConfiguration.mnc,
defaultLocale,
selectedLocales,
mConfiguration.orientation,
@@ -539,7 +544,7 @@
mConfiguration.screenWidthDp, mConfiguration.screenHeightDp,
mConfiguration.screenLayout, mConfiguration.uiMode,
mConfiguration.colorMode, mConfiguration.getGrammaticalGender(),
- Build.VERSION.RESOURCES_SDK_INT);
+ Build.VERSION.RESOURCES_SDK_INT, forceAssetsRefresh);
if (DEBUG_CONFIG) {
Slog.i(TAG, "**** Updating config of " + this + ": final config is "
diff --git a/core/jni/android_util_AssetManager.cpp b/core/jni/android_util_AssetManager.cpp
index 3ee15ab..3d0ab4e 100644
--- a/core/jni/android_util_AssetManager.cpp
+++ b/core/jni/android_util_AssetManager.cpp
@@ -314,7 +314,8 @@
}
static void NativeSetApkAssets(JNIEnv* env, jclass /*clazz*/, jlong ptr,
- jobjectArray apk_assets_array, jboolean invalidate_caches) {
+ jobjectArray apk_assets_array, jboolean invalidate_caches,
+ jboolean preset) {
ATRACE_NAME("AssetManager::SetApkAssets");
const jsize apk_assets_len = env->GetArrayLength(apk_assets_array);
@@ -343,7 +344,11 @@
}
auto assetmanager = LockAndStartAssetManager(ptr);
- assetmanager->SetApkAssets(apk_assets, invalidate_caches);
+ if (preset) {
+ assetmanager->PresetApkAssets(apk_assets);
+ } else {
+ assetmanager->SetApkAssets(apk_assets, invalidate_caches);
+ }
}
static void NativeSetConfiguration(JNIEnv* env, jclass /*clazz*/, jlong ptr, jint mcc, jint mnc,
@@ -353,7 +358,7 @@
jint screen_height, jint smallest_screen_width_dp,
jint screen_width_dp, jint screen_height_dp, jint screen_layout,
jint ui_mode, jint color_mode, jint grammatical_gender,
- jint major_version) {
+ jint major_version, jboolean force_refresh) {
ATRACE_NAME("AssetManager::SetConfiguration");
const jsize locale_count = (locales == NULL) ? 0 : env->GetArrayLength(locales);
@@ -413,7 +418,7 @@
}
auto assetmanager = LockAndStartAssetManager(ptr);
- assetmanager->SetConfigurations(configs);
+ assetmanager->SetConfigurations(std::move(configs), force_refresh != JNI_FALSE);
assetmanager->SetDefaultLocale(default_locale_int);
}
@@ -1522,8 +1527,8 @@
// AssetManager setup methods.
{"nativeCreate", "()J", (void*)NativeCreate},
{"nativeDestroy", "(J)V", (void*)NativeDestroy},
- {"nativeSetApkAssets", "(J[Landroid/content/res/ApkAssets;Z)V", (void*)NativeSetApkAssets},
- {"nativeSetConfiguration", "(JIILjava/lang/String;[Ljava/lang/String;IIIIIIIIIIIIIIII)V",
+ {"nativeSetApkAssets", "(J[Landroid/content/res/ApkAssets;ZZ)V", (void*)NativeSetApkAssets},
+ {"nativeSetConfiguration", "(JIILjava/lang/String;[Ljava/lang/String;IIIIIIIIIIIIIIIIZ)V",
(void*)NativeSetConfiguration},
{"nativeGetAssignedPackageIdentifiers", "(JZZ)Landroid/util/SparseArray;",
(void*)NativeGetAssignedPackageIdentifiers},
diff --git a/libs/androidfw/AssetManager2.cpp b/libs/androidfw/AssetManager2.cpp
index 8748dab..46f636e 100644
--- a/libs/androidfw/AssetManager2.cpp
+++ b/libs/androidfw/AssetManager2.cpp
@@ -117,6 +117,10 @@
return true;
}
+void AssetManager2::PresetApkAssets(ApkAssetsList apk_assets) {
+ BuildDynamicRefTable(apk_assets);
+}
+
bool AssetManager2::SetApkAssets(std::initializer_list<ApkAssetsPtr> apk_assets,
bool invalidate_caches) {
return SetApkAssets(ApkAssetsList(apk_assets.begin(), apk_assets.size()), invalidate_caches);
@@ -432,13 +436,18 @@
return false;
}
-void AssetManager2::SetConfigurations(std::vector<ResTable_config> configurations) {
+void AssetManager2::SetConfigurations(std::vector<ResTable_config> configurations,
+ bool force_refresh) {
int diff = 0;
- if (configurations_.size() != configurations.size()) {
+ if (force_refresh) {
diff = -1;
} else {
- for (int i = 0; i < configurations_.size(); i++) {
- diff |= configurations_[i].diff(configurations[i]);
+ if (configurations_.size() != configurations.size()) {
+ diff = -1;
+ } else {
+ for (int i = 0; i < configurations_.size(); i++) {
+ diff |= configurations_[i].diff(configurations[i]);
+ }
}
}
configurations_ = std::move(configurations);
@@ -775,8 +784,7 @@
bool has_locale = false;
if (result->config.locale == 0) {
if (default_locale_ != 0) {
- ResTable_config conf;
- conf.locale = default_locale_;
+ ResTable_config conf = {.locale = default_locale_};
// Since we know conf has a locale and only a locale, match will tell us if that locale
// matches
has_locale = conf.match(config);
diff --git a/libs/androidfw/include/androidfw/AssetManager2.h b/libs/androidfw/include/androidfw/AssetManager2.h
index d9ff35b..17a8ba6 100644
--- a/libs/androidfw/include/androidfw/AssetManager2.h
+++ b/libs/androidfw/include/androidfw/AssetManager2.h
@@ -124,6 +124,9 @@
// new resource IDs.
bool SetApkAssets(ApkAssetsList apk_assets, bool invalidate_caches = true);
bool SetApkAssets(std::initializer_list<ApkAssetsPtr> apk_assets, bool invalidate_caches = true);
+ // This one is an optimization - it skips all calculations for applying the currently set
+ // configuration, expecting a configuration update later with a forced refresh.
+ void PresetApkAssets(ApkAssetsList apk_assets);
const ApkAssetsPtr& GetApkAssets(ApkAssetsCookie cookie) const;
int GetApkAssetsCount() const {
@@ -156,7 +159,7 @@
// Sets/resets the configuration for this AssetManager. This will cause all
// caches that are related to the configuration change to be invalidated.
- void SetConfigurations(std::vector<ResTable_config> configurations);
+ void SetConfigurations(std::vector<ResTable_config> configurations, bool force_refresh = false);
inline const std::vector<ResTable_config>& GetConfigurations() const {
return configurations_;