From 21fbcd7c05b8eec5ac9097b407277396468964c5 Mon Sep 17 00:00:00 2001 From: Nahun Kim Date: Tue, 22 Sep 2020 19:48:12 +0900 Subject: [PATCH] Fix a timing issue where LauncherApps registers its callback twice There is an edge case while the launcher process is killed and restarted by unexpected behavior. LauncherApps unregisters a listener by being called back onCallbackDied from PackageCallbackList when the launcher process is killed. However the launcher process is immediately restarted and registers a listener in the middle of processing binderDied() even before calling the onCallbackDied() in the binderDied(). This solution is to maintain a boolean, isWatchingPackageBroadcasts, determining whether or not the monitor has been registered. startWatchingPackageBroadcasts() and stopWatchingPackageBroadcasts() are always called with the mListeners lock held, it can check/toggle the state safely in those methods. Test: compile & verify basic functions working Bug: 162753652 Change-Id: If91e4bc32b17b88576777699b3d8d9f409fae91d --- .../com/android/server/pm/LauncherAppsService.java | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/services/core/java/com/android/server/pm/LauncherAppsService.java b/services/core/java/com/android/server/pm/LauncherAppsService.java index 5bbe49088c023..4c1b700d958e9 100644 --- a/services/core/java/com/android/server/pm/LauncherAppsService.java +++ b/services/core/java/com/android/server/pm/LauncherAppsService.java @@ -75,6 +75,7 @@ import android.util.Log; import android.util.Pair; import android.util.Slog; +import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.content.PackageMonitor; import com.android.internal.os.BackgroundThread; @@ -143,6 +144,9 @@ public class LauncherAppsService extends SystemService { private final MyPackageMonitor mPackageMonitor = new MyPackageMonitor(); + @GuardedBy("mListeners") + private boolean mIsWatchingPackageBroadcasts = false; + private final ShortcutChangeHandler mShortcutChangeHandler; private final Handler mCallbackHandler; @@ -281,7 +285,10 @@ public class LauncherAppsService extends SystemService { * Register a receiver to watch for package broadcasts */ private void startWatchingPackageBroadcasts() { - mPackageMonitor.register(mContext, UserHandle.ALL, true, mCallbackHandler); + if (!mIsWatchingPackageBroadcasts) { + mPackageMonitor.register(mContext, UserHandle.ALL, true, mCallbackHandler); + mIsWatchingPackageBroadcasts = true; + } } /** @@ -291,7 +298,10 @@ public class LauncherAppsService extends SystemService { if (DEBUG) { Log.d(TAG, "Stopped watching for packages"); } - mPackageMonitor.unregister(); + if (mIsWatchingPackageBroadcasts) { + mPackageMonitor.unregister(); + mIsWatchingPackageBroadcasts = false; + } } void checkCallbackCount() {