summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Charles Chen <charlesccchen@google.com> 2020-08-25 01:26:30 +0000
committer Android (Google) Code Review <android-gerrit@google.com> 2020-08-25 01:26:30 +0000
commitae905ec585adef7a8bb31e3c04521ebd10ee9280 (patch)
tree45caa9a27bfde759643e40ddbe8b77642ab49f4d
parenta76c1bf32530f1616ae77c3ca3a4125a0b99d4f2 (diff)
parent2de5510bdfcb0e27814bb25adc1aa85c42fa09e0 (diff)
Merge "Fix lock contention in ResourcesManager"
-rw-r--r--apct-tests/perftests/core/src/android/app/ResourcesManagerPerfTest.java19
-rw-r--r--core/java/android/app/ResourcesManager.java36
2 files changed, 38 insertions, 17 deletions
diff --git a/apct-tests/perftests/core/src/android/app/ResourcesManagerPerfTest.java b/apct-tests/perftests/core/src/android/app/ResourcesManagerPerfTest.java
index 050fecde8213..d3938f4c0926 100644
--- a/apct-tests/perftests/core/src/android/app/ResourcesManagerPerfTest.java
+++ b/apct-tests/perftests/core/src/android/app/ResourcesManagerPerfTest.java
@@ -17,7 +17,6 @@ package android.app;
import android.content.Context;
import android.content.res.Configuration;
-import android.content.res.Resources;
import android.perftests.utils.BenchmarkState;
import android.perftests.utils.PerfStatusReporter;
import android.view.Display;
@@ -136,4 +135,22 @@ public class ResourcesManagerPerfTest {
}
}
}
+
+ @Test
+ public void getDisplayMetrics() {
+ ResourcesManager resourcesManager = ResourcesManager.getInstance();
+
+ final BenchmarkState state = mPerfStatusReporter.getBenchmarkState();
+ while (state.keepRunning()) {
+ state.pauseTiming();
+ // Invalidate cache.
+ resourcesManager.applyConfigurationToResourcesLocked(
+ resourcesManager.getConfiguration(), null);
+ state.resumeTiming();
+
+ // Invoke twice for testing cache.
+ resourcesManager.getDisplayMetrics();
+ resourcesManager.getDisplayMetrics();
+ }
+ }
}
diff --git a/core/java/android/app/ResourcesManager.java b/core/java/android/app/ResourcesManager.java
index 7cd3fcad177b..9e4ab33c6aa0 100644
--- a/core/java/android/app/ResourcesManager.java
+++ b/core/java/android/app/ResourcesManager.java
@@ -54,6 +54,7 @@ import java.io.IOException;
import java.io.PrintWriter;
import java.lang.ref.Reference;
import java.lang.ref.ReferenceQueue;
+import java.lang.ref.SoftReference;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.Arrays;
@@ -245,7 +246,7 @@ public class ResourcesManager {
/**
* A cache of DisplayId, DisplayAdjustments to Display.
*/
- private final ArrayMap<Pair<Integer, DisplayAdjustments>, WeakReference<Display>>
+ private final ArrayMap<Pair<Integer, DisplayAdjustments>, SoftReference<Display>>
mAdjustedDisplays = new ArrayMap<>();
/**
@@ -373,25 +374,28 @@ public class ResourcesManager {
? new DisplayAdjustments(displayAdjustments) : new DisplayAdjustments();
final Pair<Integer, DisplayAdjustments> key =
Pair.create(displayId, displayAdjustmentsCopy);
+ SoftReference<Display> sd;
synchronized (this) {
- WeakReference<Display> wd = mAdjustedDisplays.get(key);
- if (wd != null) {
- final Display display = wd.get();
- if (display != null) {
- return display;
- }
- }
- final DisplayManagerGlobal dm = DisplayManagerGlobal.getInstance();
- if (dm == null) {
- // may be null early in system startup
- return null;
- }
- final Display display = dm.getCompatibleDisplay(displayId, key.second);
+ sd = mAdjustedDisplays.get(key);
+ }
+ if (sd != null) {
+ final Display display = sd.get();
if (display != null) {
- mAdjustedDisplays.put(key, new WeakReference<>(display));
+ return display;
+ }
+ }
+ final DisplayManagerGlobal dm = DisplayManagerGlobal.getInstance();
+ if (dm == null) {
+ // may be null early in system startup
+ return null;
+ }
+ final Display display = dm.getCompatibleDisplay(displayId, key.second);
+ if (display != null) {
+ synchronized (this) {
+ mAdjustedDisplays.put(key, new SoftReference<>(display));
}
- return display;
}
+ return display;
}
/**