Implement user-settable power save whitelist.

The whitelist is now maintained by DeviceIdleController,
which is moving out into its own independent system service.
Network stats now queries it for the whitelist, instead of
collecting that itself.

Also did a few improvements in alarm manager -- made the
code for moving alarms out of the pending list more robust,
and fixed the debug output to always print the contents of
the pending list even if we aren't in a pending state.  (That
would have helped me identify the problem much earlier.)

Change-Id: I0f7119d4c553c3af4d77b2f71246fa6e2c13c561
diff --git a/core/java/android/net/INetworkPolicyManager.aidl b/core/java/android/net/INetworkPolicyManager.aidl
index c722fbc..7f5f377 100644
--- a/core/java/android/net/INetworkPolicyManager.aidl
+++ b/core/java/android/net/INetworkPolicyManager.aidl
@@ -38,8 +38,6 @@
 
     boolean isUidForeground(int uid);
 
-    int[] getPowerSaveAppIdWhitelist();
-
     void registerListener(INetworkPolicyListener listener);
     void unregisterListener(INetworkPolicyListener listener);
 
diff --git a/core/java/android/net/NetworkPolicyManager.java b/core/java/android/net/NetworkPolicyManager.java
index bc03637..b4c7b2b 100644
--- a/core/java/android/net/NetworkPolicyManager.java
+++ b/core/java/android/net/NetworkPolicyManager.java
@@ -129,14 +129,6 @@
         }
     }
 
-    public int[] getPowerSaveAppIdWhitelist() {
-        try {
-            return mService.getPowerSaveAppIdWhitelist();
-        } catch (RemoteException e) {
-            return new int[0];
-        }
-    }
-
     public void registerListener(INetworkPolicyListener listener) {
         try {
             mService.registerListener(listener);
diff --git a/core/java/android/os/IDeviceIdleController.aidl b/core/java/android/os/IDeviceIdleController.aidl
new file mode 100644
index 0000000..3cb29ff
--- /dev/null
+++ b/core/java/android/os/IDeviceIdleController.aidl
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015, The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.os;
+
+/** @hide */
+interface IDeviceIdleController {
+    void addPowerSaveWhitelistApp(String name);
+    void removePowerSaveWhitelistApp(String name);
+    String[] getSystemPowerWhitelist();
+    String[] getFullPowerWhitelist();
+    int[] getAppIdWhitelist();
+}
diff --git a/core/java/android/os/PowerManager.java b/core/java/android/os/PowerManager.java
index 01c9a21..1d9d7d2 100644
--- a/core/java/android/os/PowerManager.java
+++ b/core/java/android/os/PowerManager.java
@@ -920,6 +920,14 @@
             = "android.os.action.DEVICE_IDLE_MODE_CHANGED";
 
     /**
+     * @hide Intent that is broadcast when the set of power save whitelist apps has changed.
+     * This broadcast is only sent to registered receivers.
+     */
+    @SdkConstant(SdkConstant.SdkConstantType.BROADCAST_INTENT_ACTION)
+    public static final String ACTION_POWER_SAVE_WHITELIST_CHANGED
+            = "android.os.action.POWER_SAVE_WHITELIST_CHANGED";
+
+    /**
      * Intent that is broadcast when the state of {@link #isPowerSaveMode()} is about to change.
      * This broadcast is only sent to registered receivers.
      *
diff --git a/core/java/com/android/internal/content/PackageMonitor.java b/core/java/com/android/internal/content/PackageMonitor.java
index eff44bd..481ab0e 100644
--- a/core/java/com/android/internal/content/PackageMonitor.java
+++ b/core/java/com/android/internal/content/PackageMonitor.java
@@ -44,7 +44,6 @@
         sPackageFilt.addAction(Intent.ACTION_PACKAGE_CHANGED);
         sPackageFilt.addAction(Intent.ACTION_QUERY_PACKAGE_RESTART);
         sPackageFilt.addAction(Intent.ACTION_PACKAGE_RESTARTED);
-        sPackageFilt.addAction(Intent.ACTION_UID_REMOVED);
         sPackageFilt.addDataScheme("package");
         sNonDataFilt.addAction(Intent.ACTION_UID_REMOVED);
         sNonDataFilt.addAction(Intent.ACTION_USER_STOPPED);
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index 45c078d..942e6a6 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -79,6 +79,8 @@
 
     <protected-broadcast android:name="android.os.action.POWER_SAVE_MODE_CHANGED" />
     <protected-broadcast android:name="android.os.action.POWER_SAVE_MODE_CHANGING" />
+    <protected-broadcast android:name="android.os.action.DEVICE_IDLE_MODE_CHANGED" />
+    <protected-broadcast android:name="android.os.action.POWER_SAVE_WHITELIST_CHANGED" />
 
     <protected-broadcast android:name="android.os.action.SCREEN_BRIGHTNESS_BOOST_CHANGED" />