Merge commit \'bce5116b8d10c91436445cd0a0830bb51702bfd4\' into HEAD
am: 2e8c3c11b7

* commit '2e8c3c11b7f482f01b1ff76a6217eaf129253809':
diff --git a/core/java/android/app/Notification.java b/core/java/android/app/Notification.java
index 55aec59..21060e4 100644
--- a/core/java/android/app/Notification.java
+++ b/core/java/android/app/Notification.java
@@ -3972,7 +3972,9 @@
         @Override
         public void purgeResources() {
             super.purgeResources();
-            if (mPicture != null && mPicture.isMutable()) {
+            if (mPicture != null &&
+                mPicture.isMutable() &&
+                mPicture.getAllocationByteCount() >= (128 * (1 << 10))) {
                 mPicture = mPicture.createAshmemBitmap();
             }
             if (mBigLargeIcon != null) {
diff --git a/core/java/android/app/usage/UsageStatsManagerInternal.java b/core/java/android/app/usage/UsageStatsManagerInternal.java
index 948ea1e..498ff81 100644
--- a/core/java/android/app/usage/UsageStatsManagerInternal.java
+++ b/core/java/android/app/usage/UsageStatsManagerInternal.java
@@ -71,10 +71,11 @@
      * Could be hours, could be days, who knows?
      *
      * @param packageName
+     * @param uidForAppId The uid of the app, which will be used for its app id
      * @param userId
      * @return
      */
-    public abstract boolean isAppIdle(String packageName, int userId);
+    public abstract boolean isAppIdle(String packageName, int uidForAppId, int userId);
 
     /**
      * Returns all of the uids for a given user where all packages associating with that uid
diff --git a/core/java/android/content/Intent.java b/core/java/android/content/Intent.java
index 3d0c572..9bd61d3 100644
--- a/core/java/android/content/Intent.java
+++ b/core/java/android/content/Intent.java
@@ -1649,6 +1649,14 @@
             = "android.intent.extra.GET_PERMISSIONS_APP_LABEL_LIST_RESULT";
 
     /**
+     * Boolean list describing if the app is a system app for apps that have one or more runtime
+     * permissions.
+     * @hide
+     */
+    public static final String EXTRA_GET_PERMISSIONS_IS_SYSTEM_APP_LIST_RESULT
+            = "android.intent.extra.GET_PERMISSIONS_IS_SYSTEM_APP_LIST_RESULT";
+
+    /**
      * Required extra to be sent with {@link #ACTION_GET_PERMISSIONS_COUNT} broadcasts.
      * @hide
      */
diff --git a/core/java/android/content/pm/IPackageManager.aidl b/core/java/android/content/pm/IPackageManager.aidl
index a5e9faf..fec2c44 100644
--- a/core/java/android/content/pm/IPackageManager.aidl
+++ b/core/java/android/content/pm/IPackageManager.aidl
@@ -63,7 +63,9 @@
     boolean isPackageAvailable(String packageName, int userId);
     PackageInfo getPackageInfo(String packageName, int flags, int userId);
     int getPackageUid(String packageName, int userId);
+    int getPackageUidEtc(String packageName, int flags, int userId);
     int[] getPackageGids(String packageName, int userId);
+    int[] getPackageGidsEtc(String packageName, int flags, int userId);
 
     String[] currentToCanonicalPackageNames(in String[] names);
     String[] canonicalToCurrentPackageNames(in String[] names);
diff --git a/core/jni/android/graphics/Bitmap.cpp b/core/jni/android/graphics/Bitmap.cpp
index e6c7c2b..703a9bd 100755
--- a/core/jni/android/graphics/Bitmap.cpp
+++ b/core/jni/android/graphics/Bitmap.cpp
@@ -28,6 +28,7 @@
 #include <cutils/ashmem.h>
 
 #define DEBUG_PARCEL 0
+#define ASHMEM_BITMAP_MIN_SIZE (128 * (1 << 10))
 
 namespace android {
 
@@ -993,7 +994,7 @@
 
     // Map the bitmap in place from the ashmem region if possible otherwise copy.
     Bitmap* nativeBitmap;
-    if (blob.fd() >= 0 && (blob.isMutable() || !isMutable)) {
+    if (blob.fd() >= 0 && (blob.isMutable() || !isMutable) && (size >= ASHMEM_BITMAP_MIN_SIZE)) {
 #if DEBUG_PARCEL
         ALOGD("Bitmap.createFromParcel: mapped contents of %s bitmap from %s blob "
                 "(fds %s)",
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index 09cceb6..28933e1 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -2120,7 +2120,7 @@
     <!-- Allows an application to grant specific permissions.
          @hide -->
     <permission android:name="android.permission.GRANT_RUNTIME_PERMISSIONS"
-        android:protectionLevel="signature|installer" />
+        android:protectionLevel="signature|installer|verifier" />
 
     <!-- Allows an app that has this permission and the permissions to install packages
          to request certain runtime permissions to be granted at installation.
diff --git a/core/res/res/values/dimens.xml b/core/res/res/values/dimens.xml
index 3223940..a6342c2 100644
--- a/core/res/res/values/dimens.xml
+++ b/core/res/res/values/dimens.xml
@@ -364,11 +364,6 @@
 
     <dimen name="resolver_max_width">480dp</dimen>
 
-    <!-- @deprecated Use config_windowOutsetBottom instead.
-         Size of the offset applied to the position of the circular mask. This
-         is only used on circular displays. In the case where there is no
-         "chin", this will default to 0 -->
-    <dimen name="circular_display_mask_offset">0px</dimen>
     <!-- Amount to reduce the size of the circular mask by (to compensate for
          aliasing effects). This is only used on circular displays. -->
     <dimen name="circular_display_mask_thickness">1px</dimen>
diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml
index 7754f86..cbccd19 100644
--- a/core/res/res/values/symbols.xml
+++ b/core/res/res/values/symbols.xml
@@ -445,7 +445,6 @@
   <java-symbol type="dimen" name="notification_large_icon_circle_padding" />
   <java-symbol type="dimen" name="notification_badge_size" />
   <java-symbol type="dimen" name="immersive_mode_cling_width" />
-  <java-symbol type="dimen" name="circular_display_mask_offset" />
   <java-symbol type="dimen" name="accessibility_magnification_indicator_width" />
   <java-symbol type="dimen" name="circular_display_mask_thickness" />
 
diff --git a/graphics/java/android/graphics/drawable/Icon.java b/graphics/java/android/graphics/drawable/Icon.java
index 26232a9..44d7530 100644
--- a/graphics/java/android/graphics/drawable/Icon.java
+++ b/graphics/java/android/graphics/drawable/Icon.java
@@ -382,7 +382,9 @@
      * @hide
      */
     public void convertToAshmem() {
-        if (mType == TYPE_BITMAP && getBitmap().isMutable()) {
+        if (mType == TYPE_BITMAP &&
+            getBitmap().isMutable() &&
+            getBitmap().getAllocationByteCount() >= (128 * (1 << 10))) {
             setBitmap(getBitmap().createAshmemBitmap());
         }
     }
diff --git a/libs/hwui/Android.common.mk b/libs/hwui/Android.common.mk
index 38e8be9..c80f2cf 100644
--- a/libs/hwui/Android.common.mk
+++ b/libs/hwui/Android.common.mk
@@ -1,6 +1,9 @@
 # getConfig in external/skia/include/core/SkBitmap.h is deprecated.
 # Allow Gnu extension: in-class initializer of static 'const float' member.
 # DeferredLayerUpdater.h: private field 'mRenderThread' is not used.
+
+LOCAL_CLANG := true
+
 LOCAL_CLANG_CFLAGS += \
     -Wno-deprecated-declarations \
     -Wno-gnu-static-float-init \
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PanelView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PanelView.java
index c6743e7..e03bcfb 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PanelView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PanelView.java
@@ -123,7 +123,6 @@
     };
 
     protected void onExpandingFinished() {
-        endClosing();
         mBar.onExpandingFinished();
     }
 
@@ -138,6 +137,7 @@
     }
 
     protected final void notifyExpandingFinished() {
+        endClosing();
         if (mExpanding) {
             mExpanding = false;
             onExpandingFinished();
diff --git a/services/core/java/com/android/server/AppOpsService.java b/services/core/java/com/android/server/AppOpsService.java
index c373fb8..96c1e2a 100644
--- a/services/core/java/com/android/server/AppOpsService.java
+++ b/services/core/java/com/android/server/AppOpsService.java
@@ -39,7 +39,6 @@
 import android.content.pm.ApplicationInfo;
 import android.content.pm.IPackageManager;
 import android.content.pm.PackageManager;
-import android.content.pm.PackageManager.NameNotFoundException;
 import android.media.AudioAttributes;
 import android.os.AsyncTask;
 import android.os.Binder;
@@ -263,12 +262,12 @@
                 Iterator<Ops> it = pkgs.values().iterator();
                 while (it.hasNext()) {
                     Ops ops = it.next();
-                    int curUid;
+                    int curUid = -1;
                     try {
-                        curUid = mContext.getPackageManager().getPackageUid(ops.packageName,
+                        curUid = AppGlobals.getPackageManager().getPackageUidEtc(ops.packageName,
+                                PackageManager.GET_UNINSTALLED_PACKAGES,
                                 UserHandle.getUserId(ops.uidState.uid));
-                    } catch (NameNotFoundException e) {
-                        curUid = -1;
+                    } catch (RemoteException ignored) {
                     }
                     if (curUid != ops.uidState.uid) {
                         Slog.i(TAG, "Pruning old package " + ops.packageName
diff --git a/services/core/java/com/android/server/NetworkTimeUpdateService.java b/services/core/java/com/android/server/NetworkTimeUpdateService.java
index a0d305c..3f0664d 100644
--- a/services/core/java/com/android/server/NetworkTimeUpdateService.java
+++ b/services/core/java/com/android/server/NetworkTimeUpdateService.java
@@ -30,6 +30,7 @@
 import android.os.Looper;
 import android.os.Message;
 import android.os.SystemClock;
+import android.os.PowerManager;
 import android.provider.Settings;
 import android.util.Log;
 import android.util.NtpTrustedTime;
@@ -75,6 +76,7 @@
     private SettingsObserver mSettingsObserver;
     // The last time that we successfully fetched the NTP time.
     private long mLastNtpFetchTime = NOT_SET;
+    private final PowerManager.WakeLock mWakeLock;
 
     // Normal polling frequency
     private final long mPollingIntervalMs;
@@ -104,6 +106,9 @@
                 com.android.internal.R.integer.config_ntpRetry);
         mTimeErrorThresholdMs = mContext.getResources().getInteger(
                 com.android.internal.R.integer.config_ntpThreshold);
+
+        mWakeLock = ((PowerManager) context.getSystemService(Context.POWER_SERVICE)).newWakeLock(
+                PowerManager.PARTIAL_WAKE_LOCK, TAG);
     }
 
     /** Initialize the receivers and initiate the first NTP request */
@@ -148,7 +153,15 @@
     private void onPollNetworkTime(int event) {
         // If Automatic time is not set, don't bother.
         if (!isAutomaticTimeRequested()) return;
+        mWakeLock.acquire();
+        try {
+            onPollNetworkTimeUnderWakeLock(event);
+        } finally {
+            mWakeLock.release();
+        }
+    }
 
+    private void onPollNetworkTimeUnderWakeLock(int event) {
         final long refTime = SystemClock.elapsedRealtime();
         // If NITZ time was received less than mPollingIntervalMs time ago,
         // no need to sync to NTP.
diff --git a/services/core/java/com/android/server/accounts/AccountManagerService.java b/services/core/java/com/android/server/accounts/AccountManagerService.java
index d5e9a32..3c6de07 100644
--- a/services/core/java/com/android/server/accounts/AccountManagerService.java
+++ b/services/core/java/com/android/server/accounts/AccountManagerService.java
@@ -3791,7 +3791,6 @@
         boolean isPermitted =
                 isPermitted(opPackageName, callingUid, Manifest.permission.GET_ACCOUNTS,
                         Manifest.permission.GET_ACCOUNTS_PRIVILEGED);
-        Log.i(TAG, String.format("getTypesVisibleToCaller: isPermitted? %s", isPermitted));
         return getTypesForCaller(callingUid, userId, isPermitted);
     }
 
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 61707a8..9aa6a64 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -369,6 +369,10 @@
     // we will consider it to be doing interaction for usage stats.
     static final int SERVICE_USAGE_INTERACTION_TIME = 30*60*1000;
 
+    // Maximum amount of time we will allow to elapse before re-reporting usage stats
+    // interaction with foreground processes.
+    static final long USAGE_STATS_INTERACTION_INTERVAL = 24*60*60*1000L;
+
     // Maximum number of users we allow to be running at a time.
     static final int MAX_RUNNING_USERS = 3;
 
@@ -18674,7 +18678,8 @@
         }
     }
 
-    private final boolean applyOomAdjLocked(ProcessRecord app, boolean doingAll, long now) {
+    private final boolean applyOomAdjLocked(ProcessRecord app, boolean doingAll, long now,
+            long nowElapsed) {
         boolean success = true;
 
         if (app.curRawAdj != app.setRawAdj) {
@@ -18778,7 +18783,7 @@
         if (app.setProcState != app.curProcState) {
             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
                     "Proc state change of " + app.processName
-                    + " to " + app.curProcState);
+                            + " to " + app.curProcState);
             boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE;
             boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE;
             if (setImportant && !curImportant) {
@@ -18789,14 +18794,14 @@
                 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
                 synchronized (stats) {
                     app.lastWakeTime = stats.getProcessWakeTime(app.info.uid,
-                            app.pid, SystemClock.elapsedRealtime());
+                            app.pid, nowElapsed);
                 }
                 app.lastCpuTime = app.curCpuTime;
 
             }
             // Inform UsageStats of important process state change
             // Must be called before updating setProcState
-            maybeUpdateUsageStatsLocked(app);
+            maybeUpdateUsageStatsLocked(app, nowElapsed);
 
             app.setProcState = app.curProcState;
             if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) {
@@ -18807,6 +18812,11 @@
             } else {
                 app.procStateChanged = true;
             }
+        } else if (app.reportedInteraction && (nowElapsed-app.interactionEventTime)
+                > USAGE_STATS_INTERACTION_INTERVAL) {
+            // For apps that sit around for a long time in the interactive state, we need
+            // to report this at least once a day so they don't go idle.
+            maybeUpdateUsageStatsLocked(app, nowElapsed);
         }
 
         if (changes != 0) {
@@ -18901,7 +18911,7 @@
         }
     }
 
-    private void maybeUpdateUsageStatsLocked(ProcessRecord app) {
+    private void maybeUpdateUsageStatsLocked(ProcessRecord app, long nowElapsed) {
         if (DEBUG_USAGE_STATS) {
             Slog.d(TAG, "Checking proc [" + Arrays.toString(app.getPackageList())
                     + "] state changes: old = " + app.setProcState + ", new = "
@@ -18918,19 +18928,20 @@
             isInteraction = true;
             app.fgInteractionTime = 0;
         } else if (app.curProcState <= ActivityManager.PROCESS_STATE_TOP_SLEEPING) {
-            final long now = SystemClock.elapsedRealtime();
             if (app.fgInteractionTime == 0) {
-                app.fgInteractionTime = now;
+                app.fgInteractionTime = nowElapsed;
                 isInteraction = false;
             } else {
-                isInteraction = now > app.fgInteractionTime + SERVICE_USAGE_INTERACTION_TIME;
+                isInteraction = nowElapsed > app.fgInteractionTime + SERVICE_USAGE_INTERACTION_TIME;
             }
         } else {
             isInteraction = app.curProcState
                     <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND;
             app.fgInteractionTime = 0;
         }
-        if (isInteraction && !app.reportedInteraction) {
+        if (isInteraction && (!app.reportedInteraction
+                || (nowElapsed-app.interactionEventTime) > USAGE_STATS_INTERACTION_INTERVAL)) {
+            app.interactionEventTime = nowElapsed;
             String[] packages = app.getPackageList();
             if (packages != null) {
                 for (int i = 0; i < packages.length; i++) {
@@ -18940,6 +18951,9 @@
             }
         }
         app.reportedInteraction = isInteraction;
+        if (!isInteraction) {
+            app.interactionEventTime = 0;
+        }
     }
 
     private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) {
@@ -18962,7 +18976,7 @@
 
         computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now);
 
-        return applyOomAdjLocked(app, doingAll, now);
+        return applyOomAdjLocked(app, doingAll, now, SystemClock.elapsedRealtime());
     }
 
     final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground,
@@ -19054,6 +19068,7 @@
         final ActivityRecord TOP_ACT = resumedAppLocked();
         final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null;
         final long now = SystemClock.uptimeMillis();
+        final long nowElapsed = SystemClock.elapsedRealtime();
         final long oldTime = now - ProcessList.MAX_EMPTY_TIME;
         final int N = mLruProcesses.size();
 
@@ -19180,7 +19195,7 @@
                     }
                 }
 
-                applyOomAdjLocked(app, true, now);
+                applyOomAdjLocked(app, true, now, nowElapsed);
 
                 // Count the number of process types.
                 switch (app.curProcState) {
diff --git a/services/core/java/com/android/server/am/ProcessRecord.java b/services/core/java/com/android/server/am/ProcessRecord.java
index bd31a21..697b4e2 100644
--- a/services/core/java/com/android/server/am/ProcessRecord.java
+++ b/services/core/java/com/android/server/am/ProcessRecord.java
@@ -114,6 +114,7 @@
     boolean killed;             // True once we know the process has been killed
     boolean procStateChanged;   // Keep track of whether we changed 'setAdj'.
     boolean reportedInteraction;// Whether we have told usage stats about it being an interaction
+    long interactionEventTime;  // The time we sent the last interaction event
     long fgInteractionTime;     // When we became foreground for interaction purposes
     String waitingToKill;       // Process is waiting to be killed when in the bg, and reason
     IBinder forcingToForeground;// Token that is forcing this process to be foreground
@@ -297,6 +298,10 @@
         if (reportedInteraction || fgInteractionTime != 0) {
             pw.print(prefix); pw.print("reportedInteraction=");
             pw.print(reportedInteraction);
+            if (interactionEventTime != 0) {
+                pw.print(" time=");
+                TimeUtils.formatDuration(interactionEventTime, SystemClock.elapsedRealtime(), pw);
+            }
             if (fgInteractionTime != 0) {
                 pw.print(" fgInteractionTime=");
                 TimeUtils.formatDuration(fgInteractionTime, SystemClock.elapsedRealtime(), pw);
diff --git a/services/core/java/com/android/server/content/AppIdleMonitor.java b/services/core/java/com/android/server/content/AppIdleMonitor.java
index fe5c2da..2d768d8 100644
--- a/services/core/java/com/android/server/content/AppIdleMonitor.java
+++ b/services/core/java/com/android/server/content/AppIdleMonitor.java
@@ -50,8 +50,8 @@
         }
     }
 
-    boolean isAppIdle(String packageName, int userId) {
-        return !mAppIdleParoleOn && mUsageStats.isAppIdle(packageName, userId);
+    boolean isAppIdle(String packageName, int uidForAppId, int userId) {
+        return !mAppIdleParoleOn && mUsageStats.isAppIdle(packageName, uidForAppId, userId);
     }
 
     @Override
diff --git a/services/core/java/com/android/server/content/SyncManager.java b/services/core/java/com/android/server/content/SyncManager.java
index b61f90e..3ec0bee 100644
--- a/services/core/java/com/android/server/content/SyncManager.java
+++ b/services/core/java/com/android/server/content/SyncManager.java
@@ -2623,9 +2623,18 @@
                         continue;
                     }
                     String packageName = getPackageName(op.target);
+                    ApplicationInfo ai = null;
+                    if (packageName != null) {
+                        try {
+                            ai = mContext.getPackageManager().getApplicationInfo(packageName,
+                                    PackageManager.GET_UNINSTALLED_PACKAGES
+                                    | PackageManager.GET_DISABLED_COMPONENTS);
+                        } catch (NameNotFoundException e) {
+                        }
+                    }
                     // If app is considered idle, then skip for now and backoff
-                    if (packageName != null
-                            && mAppIdleMonitor.isAppIdle(packageName, op.target.userId)) {
+                    if (ai != null
+                            && mAppIdleMonitor.isAppIdle(packageName, ai.uid, op.target.userId)) {
                         increaseBackoffSetting(op);
                         op.appIdle = true;
                         if (isLoggable) {
diff --git a/services/core/java/com/android/server/job/controllers/AppIdleController.java b/services/core/java/com/android/server/job/controllers/AppIdleController.java
index 02d4f40..6fc02f6 100644
--- a/services/core/java/com/android/server/job/controllers/AppIdleController.java
+++ b/services/core/java/com/android/server/job/controllers/AppIdleController.java
@@ -67,7 +67,7 @@
             mTrackedTasks.add(jobStatus);
             String packageName = jobStatus.job.getService().getPackageName();
             final boolean appIdle = !mAppIdleParoleOn && mUsageStatsInternal.isAppIdle(packageName,
-                    jobStatus.getUserId());
+                    jobStatus.uId, jobStatus.getUserId());
             if (DEBUG) {
                 Slog.d(LOG_TAG, "Start tracking, setting idle state of "
                         + packageName + " to " + appIdle);
@@ -108,7 +108,7 @@
             for (JobStatus task : mTrackedTasks) {
                 String packageName = task.job.getService().getPackageName();
                 final boolean appIdle = !mAppIdleParoleOn && mUsageStatsInternal.isAppIdle(packageName,
-                        task.getUserId());
+                        task.uId, task.getUserId());
                 if (DEBUG) {
                     Slog.d(LOG_TAG, "Setting idle state of " + packageName + " to " + appIdle);
                 }
diff --git a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
index 7c9c018..1b08c2f 100644
--- a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
+++ b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
@@ -2316,7 +2316,7 @@
         final int userId = UserHandle.getUserId(uid);
 
         for (String packageName : packages) {
-            if (!mUsageStats.isAppIdle(packageName, userId)) {
+            if (!mUsageStats.isAppIdle(packageName, uid, userId)) {
                 return false;
             }
         }
diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java
index 7bca867..b90922a 100644
--- a/services/core/java/com/android/server/pm/PackageManagerService.java
+++ b/services/core/java/com/android/server/pm/PackageManagerService.java
@@ -1719,7 +1719,9 @@
                 BasePermission bp = mSettings.mPermissions.get(permission);
                 if (bp != null && (bp.isRuntime() || bp.isDevelopment())
                         && (grantedPermissions == null
-                               || ArrayUtils.contains(grantedPermissions, permission))) {
+                               || ArrayUtils.contains(grantedPermissions, permission))
+                        && (getPermissionFlags(permission, pkg.packageName, userId)
+                                & PackageManager.FLAG_PERMISSION_SYSTEM_FIXED) == 0) {
                     grantRuntimePermission(pkg.packageName, permission, userId);
                 }
             }
@@ -2736,26 +2738,38 @@
 
     @Override
     public int getPackageUid(String packageName, int userId) {
+        return getPackageUidEtc(packageName, 0, userId);
+    }
+
+    @Override
+    public int getPackageUidEtc(String packageName, int flags, int userId) {
         if (!sUserManager.exists(userId)) return -1;
         enforceCrossUserPermission(Binder.getCallingUid(), userId, false, false, "get package uid");
 
         // reader
         synchronized (mPackages) {
-            PackageParser.Package p = mPackages.get(packageName);
-            if(p != null) {
+            final PackageParser.Package p = mPackages.get(packageName);
+            if (p != null) {
                 return UserHandle.getUid(userId, p.applicationInfo.uid);
             }
-            PackageSetting ps = mSettings.mPackages.get(packageName);
-            if((ps == null) || (ps.pkg == null) || (ps.pkg.applicationInfo == null)) {
-                return -1;
+            if ((flags & PackageManager.GET_UNINSTALLED_PACKAGES) != 0) {
+                final PackageSetting ps = mSettings.mPackages.get(packageName);
+                if (ps != null) {
+                    return UserHandle.getUid(userId, ps.appId);
+                }
             }
-            p = ps.pkg;
-            return p != null ? UserHandle.getUid(userId, p.applicationInfo.uid) : -1;
         }
+
+        return -1;
     }
 
     @Override
-    public int[] getPackageGids(String packageName, int userId) throws RemoteException {
+    public int[] getPackageGids(String packageName, int userId) {
+        return getPackageGidsEtc(packageName, 0, userId);
+    }
+
+    @Override
+    public int[] getPackageGidsEtc(String packageName, int flags, int userId) {
         if (!sUserManager.exists(userId)) {
             return null;
         }
@@ -2765,14 +2779,17 @@
 
         // reader
         synchronized (mPackages) {
-            PackageParser.Package p = mPackages.get(packageName);
-            if (DEBUG_PACKAGE_INFO) {
-                Log.v(TAG, "getPackageGids" + packageName + ": " + p);
-            }
+            final PackageParser.Package p = mPackages.get(packageName);
             if (p != null) {
                 PackageSetting ps = (PackageSetting) p.mExtras;
                 return ps.getPermissionsState().computeGids(userId);
             }
+            if ((flags & PackageManager.GET_UNINSTALLED_PACKAGES) != 0) {
+                final PackageSetting ps = mSettings.mPackages.get(packageName);
+                if (ps != null) {
+                    return ps.getPermissionsState().computeGids(userId);
+                }
+            }
         }
 
         return null;
diff --git a/services/core/java/com/android/server/pm/PackageSettingBase.java b/services/core/java/com/android/server/pm/PackageSettingBase.java
index bbdfe31..78328f5 100644
--- a/services/core/java/com/android/server/pm/PackageSettingBase.java
+++ b/services/core/java/com/android/server/pm/PackageSettingBase.java
@@ -239,6 +239,7 @@
         keySetData = base.keySetData;
         verificationInfo = base.verificationInfo;
         installerPackageName = base.installerPackageName;
+        volumeUuid = base.volumeUuid;
     }
 
     private PackageUserState modifyUserState(int userId) {
diff --git a/services/usage/java/com/android/server/usage/UsageStatsService.java b/services/usage/java/com/android/server/usage/UsageStatsService.java
index 5ad796f..2b8afba 100644
--- a/services/usage/java/com/android/server/usage/UsageStatsService.java
+++ b/services/usage/java/com/android/server/usage/UsageStatsService.java
@@ -385,9 +385,11 @@
                         timeNow);
                 final int packageCount = packages.size();
                 for (int p = 0; p < packageCount; p++) {
-                    final String packageName = packages.get(p).packageName;
-                    final boolean isIdle = isAppIdleFiltered(packageName, userId, service, timeNow,
-                            screenOnTime);
+                    final PackageInfo pi = packages.get(p);
+                    final String packageName = pi.packageName;
+                    final boolean isIdle = isAppIdleFiltered(packageName,
+                            UserHandle.getAppId(pi.applicationInfo.uid),
+                            userId, service, timeNow, screenOnTime);
                     mHandler.sendMessage(mHandler.obtainMessage(MSG_INFORM_LISTENERS,
                             userId, isIdle ? 1 : 0, packageName));
                     mAppIdleHistory.addEntry(packageName, userId, isIdle, timeNow);
@@ -769,10 +771,17 @@
         if (mAppIdleParoled) {
             return false;
         }
-        return isAppIdleFiltered(packageName, userId, timeNow);
+        try {
+            ApplicationInfo ai = getContext().getPackageManager().getApplicationInfo(packageName,
+                    PackageManager.GET_UNINSTALLED_PACKAGES
+                            | PackageManager.GET_DISABLED_COMPONENTS);
+            return isAppIdleFiltered(packageName, ai.uid, userId, timeNow);
+        } catch (PackageManager.NameNotFoundException e) {
+        }
+        return false;
     }
 
-    boolean isAppIdleFiltered(String packageName, int userId, long timeNow) {
+    boolean isAppIdleFiltered(String packageName, int uidForAppId, int userId, long timeNow) {
         final UserUsageStatsService userService;
         final long screenOnTime;
         synchronized (mLock) {
@@ -782,7 +791,8 @@
             userService = getUserDataAndInitializeIfNeededLocked(userId, timeNow);
             screenOnTime = getScreenOnTimeLocked(timeNow);
         }
-        return isAppIdleFiltered(packageName, userId, userService, timeNow, screenOnTime);
+        return isAppIdleFiltered(packageName, UserHandle.getAppId(uidForAppId), userId,
+                userService, timeNow, screenOnTime);
     }
 
     /**
@@ -791,14 +801,22 @@
      * This happens if the device is plugged in or temporarily allowed to make exceptions.
      * Called by interface impls.
      */
-    private boolean isAppIdleFiltered(String packageName, int userId,
+    private boolean isAppIdleFiltered(String packageName, int appId, int userId,
             UserUsageStatsService userService, long timeNow, long screenOnTime) {
         if (packageName == null) return false;
         // If not enabled at all, of course nobody is ever idle.
         if (!mAppIdleEnabled) {
             return false;
         }
-        if (packageName.equals("android")) return false;
+        if (appId < Process.FIRST_APPLICATION_UID) {
+            // System uids never go idle.
+            return false;
+        }
+        if (packageName.equals("android")) {
+            // Nor does the framework (which should be redundant with the above, but for MR1 we will
+            // retain this for safety).
+            return false;
+        }
         try {
             // We allow all whitelisted apps, including those that don't want to be whitelisted
             // for idle mode, because app idle (aka app standby) is really not as big an issue
@@ -865,8 +883,8 @@
             ApplicationInfo ai = apps.get(i);
 
             // Check whether this app is idle.
-            boolean idle = isAppIdleFiltered(ai.packageName, userId, userService, timeNow,
-                    screenOnTime);
+            boolean idle = isAppIdleFiltered(ai.packageName, UserHandle.getAppId(ai.uid),
+                    userId, userService, timeNow, screenOnTime);
 
             int index = uidStates.indexOfKey(ai.uid);
             if (index < 0) {
@@ -1352,8 +1370,8 @@
         }
 
         @Override
-        public boolean isAppIdle(String packageName, int userId) {
-            return UsageStatsService.this.isAppIdleFiltered(packageName, userId, -1);
+        public boolean isAppIdle(String packageName, int uidForAppId, int userId) {
+            return UsageStatsService.this.isAppIdleFiltered(packageName, uidForAppId, userId, -1);
         }
 
         @Override
diff --git a/services/usb/java/com/android/server/usb/UsbDeviceManager.java b/services/usb/java/com/android/server/usb/UsbDeviceManager.java
index 49062d0..81ca6a3 100644
--- a/services/usb/java/com/android/server/usb/UsbDeviceManager.java
+++ b/services/usb/java/com/android/server/usb/UsbDeviceManager.java
@@ -716,6 +716,8 @@
                         if (active && mCurrentUser != UserHandle.USER_NULL) {
                             Slog.v(TAG, "Current user switched to " + mCurrentUser
                                     + "; resetting USB host stack for MTP or PTP");
+                            // avoid leaking sensitive data from previous user
+                            mUsbDataUnlocked = false;
                             setEnabledFunctions(mCurrentFunctions, true);
                         }
                         mCurrentUser = msg.arg1;
diff --git a/telephony/java/android/telephony/SubscriptionInfo.java b/telephony/java/android/telephony/SubscriptionInfo.java
index e11c8d3..d1d6e0d 100644
--- a/telephony/java/android/telephony/SubscriptionInfo.java
+++ b/telephony/java/android/telephony/SubscriptionInfo.java
@@ -332,9 +332,24 @@
         return 0;
     }
 
+    /**
+     * @hide
+     */
+    public static String givePrintableIccid(String iccId) {
+        String iccIdToPrint = null;
+        if (iccId != null) {
+            if (iccId.length() > 9) {
+                iccIdToPrint = iccId.substring(0, 9) + "XXXXXXXXXXX";
+            } else {
+                iccIdToPrint = iccId;
+            }
+        }
+        return iccIdToPrint;
+    }
+
     @Override
     public String toString() {
-        String iccIdToPrint = mIccId != null ? mIccId.substring(0, 9) + "XXXXXXXXXXX" : null;
+        String iccIdToPrint = givePrintableIccid(mIccId);
         return "{id=" + mId + ", iccId=" + iccIdToPrint + " simSlotIndex=" + mSimSlotIndex
                 + " displayName=" + mDisplayName + " carrierName=" + mCarrierName
                 + " nameSource=" + mNameSource + " iconTint=" + mIconTint
diff --git a/telephony/java/com/android/ims/ImsCallProfile.java b/telephony/java/com/android/ims/ImsCallProfile.java
index f263b4d..5f84e0c 100644
--- a/telephony/java/com/android/ims/ImsCallProfile.java
+++ b/telephony/java/com/android/ims/ImsCallProfile.java
@@ -178,6 +178,7 @@
      *  Codec: Codec info.
      *  DisplayText: Display text for the call.
      *  AdditionalCallInfo: Additional call info.
+     *  CallRadioTech: The radio tech on which the call is placed.
      */
     public static final String EXTRA_OI = "oi";
     public static final String EXTRA_CNA = "cna";
@@ -188,6 +189,21 @@
     public static final String EXTRA_DISPLAY_TEXT = "DisplayText";
     public static final String EXTRA_ADDITIONAL_CALL_INFO = "AdditionalCallInfo";
 
+    /**
+     * Extra key which the RIL can use to indicate the radio technology used for a call.
+     * Valid values are:
+     * {@link android.telephony.ServiceState#RIL_RADIO_TECHNOLOGY_LTE},
+     * {@link android.telephony.ServiceState#RIL_RADIO_TECHNOLOGY_IWLAN}, and the other defined
+     * {@code RIL_RADIO_TECHNOLOGY_*} constants.
+     * Note: Despite the fact the {@link android.telephony.ServiceState} values are integer
+     * constants, the values passed for the {@link #EXTRA_CALL_RAT_TYPE} should be strings (e.g.
+     * "14" vs (int) 14).
+     * Note: This is used by {@link com.android.internal.telephony.imsphone.ImsPhoneConnection#
+     *      updateWifiStateFromExtras(Bundle)} to determine whether to set the
+     * {@link android.telecom.Connection#CAPABILITY_WIFI} capability on a connection.
+     */
+    public static final String EXTRA_CALL_RAT_TYPE = "CallRadioTech";
+
     public int mServiceType;
     public int mCallType;
     public int mRestrictCause = CALL_RESTRICT_CAUSE_NONE;