From 8dc32f1aad4c339ea3a20ef1e29b01d5381e7664 Mon Sep 17 00:00:00 2001 From: lpeter Date: Tue, 18 Feb 2025 11:57:13 +0000 Subject: According to the user Id to cache the ServiceInfo. Currently it saves the ServiceInfo into the cache by using the ComponentName as the key, it will return the wrong ServiceInfo to other user. It needs to accord to the user Id to cache the ServiceInfo. Flag: android.content.pm.optimize_parsing_in_registered_services_cache Bug: 396226221 Test: atest RegisteredServicesCacheTest Change-Id: I8221e586273f78b561d7ba7ebc4e2375abc075ec --- .../content/pm/RegisteredServicesCache.java | 36 +++++++++++++--------- 1 file changed, 21 insertions(+), 15 deletions(-) diff --git a/core/java/android/content/pm/RegisteredServicesCache.java b/core/java/android/content/pm/RegisteredServicesCache.java index 10d3051cff6f..ded35b23608d 100644 --- a/core/java/android/content/pm/RegisteredServicesCache.java +++ b/core/java/android/content/pm/RegisteredServicesCache.java @@ -31,13 +31,13 @@ import android.os.Environment; import android.os.Handler; import android.os.UserHandle; import android.os.UserManager; -import android.util.ArrayMap; import android.util.AtomicFile; import android.util.AttributeSet; import android.util.IntArray; import android.util.Log; import android.util.Slog; import android.util.SparseArray; +import android.util.SparseArrayMap; import android.util.Xml; import com.android.internal.annotations.GuardedBy; @@ -98,15 +98,16 @@ public abstract class RegisteredServicesCache { @GuardedBy("mServicesLock") private final SparseArray> mUserServices = new SparseArray>(2); - @GuardedBy("mServiceInfoCaches") - private final ArrayMap> mServiceInfoCaches = new ArrayMap<>(); + @GuardedBy("mUserIdToServiceInfoCaches") + private final SparseArrayMap> mUserIdToServiceInfoCaches = + new SparseArrayMap<>(); private final Handler mBackgroundHandler; private final Runnable mClearServiceInfoCachesRunnable = new Runnable() { public void run() { - synchronized (mServiceInfoCaches) { - mServiceInfoCaches.clear(); + synchronized (mUserIdToServiceInfoCaches) { + mUserIdToServiceInfoCaches.clear(); } } }; @@ -537,8 +538,8 @@ public abstract class RegisteredServicesCache { Slog.d(TAG, "Fail to get the PackageInfo in generateServicesMap: " + e); } if (lastUpdateTime >= 0) { - ServiceInfo serviceInfo = getServiceInfoFromServiceCache(componentName, - lastUpdateTime); + ServiceInfo serviceInfo = getServiceInfoFromServiceCache(userId, + componentName, lastUpdateTime); if (serviceInfo != null) { serviceInfos.add(serviceInfo); continue; @@ -553,8 +554,8 @@ public abstract class RegisteredServicesCache { } serviceInfos.add(info); if (Flags.optimizeParsingInRegisteredServicesCache()) { - synchronized (mServiceInfoCaches) { - mServiceInfoCaches.put(componentName, info); + synchronized (mUserIdToServiceInfoCaches) { + mUserIdToServiceInfoCaches.add(userId, componentName, info); } } } catch (XmlPullParserException | IOException e) { @@ -563,8 +564,8 @@ public abstract class RegisteredServicesCache { } if (Flags.optimizeParsingInRegisteredServicesCache()) { - synchronized (mServiceInfoCaches) { - if (!mServiceInfoCaches.isEmpty()) { + synchronized (mUserIdToServiceInfoCaches) { + if (mUserIdToServiceInfoCaches.numMaps() > 0) { mBackgroundHandler.removeCallbacks(mClearServiceInfoCachesRunnable); mBackgroundHandler.postDelayed(mClearServiceInfoCachesRunnable, SERVICE_INFO_CACHES_TIMEOUT_MILLIS); @@ -873,6 +874,11 @@ public abstract class RegisteredServicesCache { synchronized (mServicesLock) { mUserServices.remove(userId); } + if (Flags.optimizeParsingInRegisteredServicesCache()) { + synchronized (mUserIdToServiceInfoCaches) { + mUserIdToServiceInfoCaches.delete(userId); + } + } } @VisibleForTesting @@ -916,10 +922,10 @@ public abstract class RegisteredServicesCache { mContext.unregisterReceiver(mUserRemovedReceiver); } - private ServiceInfo getServiceInfoFromServiceCache(@NonNull ComponentName componentName, - long lastUpdateTime) { - synchronized (mServiceInfoCaches) { - ServiceInfo serviceCache = mServiceInfoCaches.get(componentName); + private ServiceInfo getServiceInfoFromServiceCache(int userId, + @NonNull ComponentName componentName, long lastUpdateTime) { + synchronized (mUserIdToServiceInfoCaches) { + ServiceInfo serviceCache = mUserIdToServiceInfoCaches.get(userId, componentName); if (serviceCache != null && serviceCache.lastUpdateTime == lastUpdateTime) { return serviceCache; } -- cgit v1.2.3-59-g8ed1b