diff --git a/services/core/java/com/android/server/AlarmManagerService.java b/services/core/java/com/android/server/AlarmManagerService.java
index 3904fc9..4330f5d 100644
--- a/services/core/java/com/android/server/AlarmManagerService.java
+++ b/services/core/java/com/android/server/AlarmManagerService.java
@@ -46,7 +46,6 @@
 import android.os.PowerManager;
 import android.os.Process;
 import android.os.RemoteException;
-import android.os.ServiceManager;
 import android.os.SystemClock;
 import android.os.SystemProperties;
 import android.os.UserHandle;
@@ -55,7 +54,6 @@
 import android.text.TextUtils;
 import android.text.format.DateFormat;
 import android.util.ArrayMap;
-import android.util.ArraySet;
 import android.util.KeyValueListParser;
 import android.util.Log;
 import android.util.Slog;
@@ -81,6 +79,7 @@
 import java.util.Random;
 import java.util.TimeZone;
 import java.util.TreeSet;
+import java.util.function.Predicate;
 
 import static android.app.AlarmManager.RTC_WAKEUP;
 import static android.app.AlarmManager.RTC;
@@ -88,11 +87,17 @@
 import static android.app.AlarmManager.ELAPSED_REALTIME;
 
 import com.android.internal.annotations.GuardedBy;
-import com.android.internal.app.IAppOpsCallback;
-import com.android.internal.app.IAppOpsService;
+import com.android.internal.annotations.VisibleForTesting;
 import com.android.internal.util.DumpUtils;
 import com.android.internal.util.LocalLog;
+import com.android.server.ForceAppStandbyTracker.Listener;
 
+/**
+ * Alarm manager implementaion.
+ *
+ * Unit test:
+ atest $ANDROID_BUILD_TOP/frameworks/base/services/tests/servicestests/src/com/android/server/AlarmManagerServiceTest.java
+ */
 class AlarmManagerService extends SystemService {
     private static final int RTC_WAKEUP_MASK = 1 << RTC_WAKEUP;
     private static final int RTC_MASK = 1 << RTC;
@@ -131,13 +136,10 @@
     final LocalLog mLog = new LocalLog(TAG);
 
     AppOpsManager mAppOps;
-    IAppOpsService mAppOpsService;
     DeviceIdleController.LocalService mLocalDeviceIdleController;
 
     final Object mLock = new Object();
 
-    ArraySet<String> mForcedAppStandbyPackages = new ArraySet<>();
-    SparseBooleanArray mForegroundUids = new SparseBooleanArray();
     // List of alarms per uid deferred due to user applied background restrictions on the source app
     SparseArray<ArrayList<Alarm>> mPendingBackgroundAlarms = new SparseArray<>();
     long mNativeData;
@@ -184,12 +186,6 @@
     int mSystemUiUid;
 
     /**
-     * The current set of user whitelisted apps for device idle mode, meaning these are allowed
-     * to freely schedule alarms.
-     */
-    int[] mDeviceIdleUserWhitelist = new int[0];
-
-    /**
      * For each uid, this is the last time we dispatched an "allow while idle" alarm,
      * used to determine the earliest we can dispatch the next such alarm. Times are in the
      * 'elapsed' timebase.
@@ -223,6 +219,8 @@
     private final SparseArray<AlarmManager.AlarmClockInfo> mHandlerSparseAlarmClockArray =
             new SparseArray<>();
 
+    private final ForceAppStandbyTracker mForceAppStandbyTracker;
+
     /**
      * All times are in milliseconds. These constants are kept synchronized with the system
      * global Settings. Any access to this class or its fields should be done while
@@ -757,6 +755,9 @@
     public AlarmManagerService(Context context) {
         super(context);
         mConstants = new Constants(mHandler);
+
+        mForceAppStandbyTracker = ForceAppStandbyTracker.getInstance(context);
+        mForceAppStandbyTracker.addListener(mForceAppStandbyListener);
     }
 
     static long convertToElapsed(long when, int type) {
@@ -894,17 +895,48 @@
         deliverPendingBackgroundAlarmsLocked(alarmsToDeliver, SystemClock.elapsedRealtime());
     }
 
-    void sendPendingBackgroundAlarmsForAppIdLocked(int appId) {
+    /**
+     * Check all alarms in {@link #mPendingBackgroundAlarms} and send the ones that are not
+     * restricted.
+     *
+     * This is only called when the global "force all apps-standby" flag changes or when the
+     * power save whitelist changes, so it's okay to be slow.
+     */
+    void sendAllUnrestrictedPendingBackgroundAlarmsLocked() {
         final ArrayList<Alarm> alarmsToDeliver = new ArrayList<>();
-        for (int i = mPendingBackgroundAlarms.size() - 1; i >= 0; i--) {
-            final int uid = mPendingBackgroundAlarms.keyAt(i);
-            final ArrayList<Alarm> alarmsForUid = mPendingBackgroundAlarms.valueAt(i);
-            if (UserHandle.getAppId(uid) == appId) {
-                alarmsToDeliver.addAll(alarmsForUid);
-                mPendingBackgroundAlarms.removeAt(i);
+
+        findAllUnrestrictedPendingBackgroundAlarmsLockedInner(
+                mPendingBackgroundAlarms, alarmsToDeliver, this::isBackgroundRestricted);
+
+        if (alarmsToDeliver.size() > 0) {
+            deliverPendingBackgroundAlarmsLocked(alarmsToDeliver, SystemClock.elapsedRealtime());
+        }
+    }
+
+    @VisibleForTesting
+    static void findAllUnrestrictedPendingBackgroundAlarmsLockedInner(
+            SparseArray<ArrayList<Alarm>> pendingAlarms, ArrayList<Alarm> unrestrictedAlarms,
+            Predicate<Alarm> isBackgroundRestricted) {
+
+        for (int uidIndex = pendingAlarms.size() - 1; uidIndex >= 0; uidIndex--) {
+            final int uid = pendingAlarms.keyAt(uidIndex);
+            final ArrayList<Alarm> alarmsForUid = pendingAlarms.valueAt(uidIndex);
+
+            for (int alarmIndex = alarmsForUid.size() - 1; alarmIndex >= 0; alarmIndex--) {
+                final Alarm alarm = alarmsForUid.get(alarmIndex);
+
+                if (isBackgroundRestricted.test(alarm)) {
+                    continue;
+                }
+
+                unrestrictedAlarms.add(alarm);
+                alarmsForUid.remove(alarmIndex);
+            }
+
+            if (alarmsForUid.size() == 0) {
+                pendingAlarms.removeAt(uidIndex);
             }
         }
-        deliverPendingBackgroundAlarmsLocked(alarmsToDeliver, SystemClock.elapsedRealtime());
     }
 
     private void deliverPendingBackgroundAlarmsLocked(ArrayList<Alarm> alarms, long nowELAPSED) {
@@ -1234,10 +1266,8 @@
         } catch (RemoteException e) {
             // ignored; both services live in system_server
         }
-        mAppOpsService = IAppOpsService.Stub.asInterface(
-                ServiceManager.getService(Context.APP_OPS_SERVICE));
         publishBinderService(Context.ALARM_SERVICE, mService);
-        publishLocalService(LocalService.class, new LocalService());
+        mForceAppStandbyTracker.start();
     }
 
     @Override
@@ -1247,13 +1277,6 @@
             mAppOps = (AppOpsManager) getContext().getSystemService(Context.APP_OPS_SERVICE);
             mLocalDeviceIdleController
                     = LocalServices.getService(DeviceIdleController.LocalService.class);
-            try {
-                mAppOpsService.startWatchingMode(AppOpsManager.OP_RUN_ANY_IN_BACKGROUND, null,
-                        new AppOpsWatcher());
-            } catch (RemoteException rexc) {
-                // Shouldn't happen as they are in the same process.
-                Slog.e(TAG, "AppOps service not reachable", rexc);
-            }
         }
     }
 
@@ -1582,8 +1605,7 @@
             // timing restrictions.
             } else if (workSource == null && (callingUid < Process.FIRST_APPLICATION_UID
                     || callingUid == mSystemUiUid
-                    || Arrays.binarySearch(mDeviceIdleUserWhitelist,
-                            UserHandle.getAppId(callingUid)) >= 0)) {
+                    || mForceAppStandbyTracker.isUidPowerSaveWhitelisted(callingUid))) {
                 flags |= AlarmManager.FLAG_ALLOW_WHILE_IDLE_UNRESTRICTED;
                 flags &= ~AlarmManager.FLAG_ALLOW_WHILE_IDLE;
             }
@@ -1660,24 +1682,14 @@
         }
     };
 
-    public final class LocalService {
-        public void setDeviceIdleUserWhitelist(int[] appids) {
-            setDeviceIdleUserWhitelistImpl(appids);
-        }
-    }
-
     void dumpImpl(PrintWriter pw) {
         synchronized (mLock) {
             pw.println("Current Alarm Manager state:");
             mConstants.dump(pw);
             pw.println();
 
-            pw.print("  Foreground uids: [");
-            for (int i = 0; i < mForegroundUids.size(); i++) {
-                if (mForegroundUids.valueAt(i)) pw.print(mForegroundUids.keyAt(i) + " ");
-            }
-            pw.println("]");
-            pw.println("  Forced app standby packages: " + mForcedAppStandbyPackages);
+            mForceAppStandbyTracker.dump(pw, "  ");
+
             final long nowRTC = System.currentTimeMillis();
             final long nowELAPSED = SystemClock.elapsedRealtime();
             SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
@@ -1717,7 +1729,6 @@
             pw.print(" set at "); TimeUtils.formatDuration(mLastWakeupSet, nowELAPSED, pw);
             pw.println();
             pw.print("  Num time change events: "); pw.println(mNumTimeChanged);
-            pw.println("  mDeviceIdleUserWhitelist=" + Arrays.toString(mDeviceIdleUserWhitelist));
 
             pw.println();
             pw.println("  Next alarm clock information: ");
@@ -1990,15 +2001,8 @@
 
             mConstants.dumpProto(proto, AlarmManagerServiceProto.SETTINGS);
 
-            final int foregroundUidsSize = mForegroundUids.size();
-            for (int i = 0; i < foregroundUidsSize; i++) {
-                if (mForegroundUids.valueAt(i)) {
-                    proto.write(AlarmManagerServiceProto.FOREGROUND_UIDS, mForegroundUids.keyAt(i));
-                }
-            }
-            for (String pkg : mForcedAppStandbyPackages) {
-                proto.write(AlarmManagerServiceProto.FORCED_APP_STANDBY_PACKAGES, pkg);
-            }
+            mForceAppStandbyTracker.dumpProto(proto,
+                    AlarmManagerServiceProto.FORCE_APP_STANDBY_TRACKER);
 
             proto.write(AlarmManagerServiceProto.IS_INTERACTIVE, mInteractive);
             if (!mInteractive) {
@@ -2022,9 +2026,6 @@
             proto.write(AlarmManagerServiceProto.TIME_SINCE_LAST_WAKEUP_SET_MS,
                     nowElapsed - mLastWakeupSet);
             proto.write(AlarmManagerServiceProto.TIME_CHANGE_EVENT_COUNT, mNumTimeChanged);
-            for (int i : mDeviceIdleUserWhitelist) {
-                proto.write(AlarmManagerServiceProto.DEVICE_IDLE_USER_WHITELIST_APP_IDS, i);
-            }
 
             final TreeSet<Integer> users = new TreeSet<>();
             final int nextAlarmClockForUserSize = mNextAlarmClockForUser.size();
@@ -2266,28 +2267,6 @@
         }
     }
 
-    void setDeviceIdleUserWhitelistImpl(int[] appids) {
-        synchronized (mLock) {
-            // appids are sorted, just send pending alarms for any new appids added to the whitelist
-            int i = 0, j = 0;
-            while (i < appids.length) {
-                while (j < mDeviceIdleUserWhitelist.length
-                        && mDeviceIdleUserWhitelist[j] < appids[i]) {
-                    j++;
-                }
-                if (j < mDeviceIdleUserWhitelist.length
-                        && appids[i] != mDeviceIdleUserWhitelist[j]) {
-                    if (DEBUG_BG_LIMIT) {
-                        Slog.d(TAG, "Sending blocked alarms for whitelisted appid " + appids[j]);
-                    }
-                    sendPendingBackgroundAlarmsForAppIdLocked(appids[j]);
-                }
-                i++;
-            }
-            mDeviceIdleUserWhitelist = appids;
-        }
-    }
-
     AlarmManager.AlarmClockInfo getNextAlarmClockImpl(int userId) {
         synchronized (mLock) {
             return mNextAlarmClockForUser.get(userId);
@@ -2710,9 +2689,7 @@
         final String sourcePackage =
                 (alarm.operation != null) ? alarm.operation.getCreatorPackage() : alarm.packageName;
         final int sourceUid = alarm.creatorUid;
-        return mForcedAppStandbyPackages.contains(sourcePackage) && !mForegroundUids.get(sourceUid)
-                && Arrays.binarySearch(mDeviceIdleUserWhitelist, UserHandle.getAppId(sourceUid))
-                < 0;
+        return mForceAppStandbyTracker.areAlarmsRestricted(sourceUid, sourcePackage);
     }
 
     private native long init();
@@ -2859,7 +2836,8 @@
         }
     }
 
-    private static class Alarm {
+    @VisibleForTesting
+    static class Alarm {
         public final int type;
         public final long origWhen;
         public final boolean wakeup;
@@ -3476,17 +3454,10 @@
                 if (disabled) {
                     removeForStoppedLocked(uid);
                 }
-                mForegroundUids.delete(uid);
             }
         }
 
         @Override public void onUidActive(int uid) {
-            synchronized (mLock) {
-                if (!mForegroundUids.get(uid)) {
-                    mForegroundUids.put(uid, true);
-                    sendPendingBackgroundAlarmsLocked(uid, null);
-                }
-            }
         }
 
         @Override public void onUidIdle(int uid, boolean disabled) {
@@ -3494,7 +3465,6 @@
                 if (disabled) {
                     removeForStoppedLocked(uid);
                 }
-                mForegroundUids.delete(uid);
             }
         }
 
@@ -3502,27 +3472,29 @@
         }
     };
 
-    private final class AppOpsWatcher extends IAppOpsCallback.Stub {
+
+    private final Listener mForceAppStandbyListener = new Listener() {
         @Override
-        public void opChanged(int op, int uid, String packageName) throws RemoteException {
+        public void unblockAllUnrestrictedAlarms() {
             synchronized (mLock) {
-                final int mode = mAppOpsService.checkOperation(op, uid, packageName);
-                if (DEBUG_BG_LIMIT) {
-                    Slog.d(TAG,
-                            "Appop changed for " + uid + ", " + packageName + " to " + mode);
-                }
-                final boolean changed;
-                if (mode != AppOpsManager.MODE_ALLOWED) {
-                    changed = mForcedAppStandbyPackages.add(packageName);
-                } else {
-                    changed = mForcedAppStandbyPackages.remove(packageName);
-                }
-                if (changed && mode == AppOpsManager.MODE_ALLOWED) {
-                    sendPendingBackgroundAlarmsLocked(uid, packageName);
-                }
+                sendAllUnrestrictedPendingBackgroundAlarmsLocked();
             }
         }
-    }
+
+        @Override
+        public void unblockAlarmsForUid(int uid) {
+            synchronized (mLock) {
+                sendPendingBackgroundAlarmsLocked(uid, null);
+            }
+        }
+
+        @Override
+        public void unblockAlarmsForUidPackage(int uid, String packageName) {
+            synchronized (mLock) {
+                sendPendingBackgroundAlarmsLocked(uid, packageName);
+            }
+        }
+    };
 
     private final BroadcastStats getStatsLocked(PendingIntent pi) {
         String pkg = pi.getCreatorPackage();
