am de2d961f: am fbefe9bf: Merge "Fix issue #11168649: LRU logic for Chrome renderers seems..." into klp-dev

* commit 'de2d961ff83fbca65bebb9696551cbbc14cad6a5':
  Fix issue #11168649: LRU logic for Chrome renderers seems...
diff --git a/services/java/com/android/server/am/ActiveServices.java b/services/java/com/android/server/am/ActiveServices.java
index a64940c..6186b9e 100644
--- a/services/java/com/android/server/am/ActiveServices.java
+++ b/services/java/com/android/server/am/ActiveServices.java
@@ -564,7 +564,7 @@
                     if (r.isForeground) {
                         r.isForeground = false;
                         if (r.app != null) {
-                            mAm.updateLruProcessLocked(r.app, false, false);
+                            mAm.updateLruProcessLocked(r.app, false, null);
                             updateServiceForegroundLocked(r.app, true);
                         }
                     }
@@ -597,6 +597,42 @@
         }
     }
 
+    private boolean updateServiceClientActivitiesLocked(ProcessRecord proc,
+            ConnectionRecord modCr) {
+        if (modCr != null && modCr.binding.client != null) {
+            if (modCr.binding.client.activities.size() <= 0) {
+                // This connection is from a client without activities, so adding
+                // and removing is not interesting.
+                return false;
+            }
+        }
+
+        boolean anyClientActivities = false;
+        for (int i=proc.services.size()-1; i>=0 && !anyClientActivities; i--) {
+            ServiceRecord sr = proc.services.valueAt(i);
+            for (int conni=sr.connections.size()-1; conni>=0 && !anyClientActivities; conni--) {
+                ArrayList<ConnectionRecord> clist = sr.connections.valueAt(conni);
+                for (int cri=clist.size()-1; cri>=0; cri--) {
+                    ConnectionRecord cr = clist.get(cri);
+                    if (cr.binding.client == null || cr.binding.client == proc) {
+                        // Binding to ourself is not interesting.
+                        continue;
+                    }
+                    if (cr.binding.client.activities.size() > 0) {
+                        anyClientActivities = true;
+                        break;
+                    }
+                }
+            }
+        }
+        if (anyClientActivities != proc.hasClientActivities) {
+            proc.hasClientActivities = anyClientActivities;
+            mAm.updateLruProcessLocked(proc, anyClientActivities, null);
+            return true;
+        }
+        return false;
+    }
+
     int bindServiceLocked(IApplicationThread caller, IBinder token,
             Intent service, String resolvedType,
             IServiceConnection connection, int flags, int userId) {
@@ -698,6 +734,9 @@
             if ((c.flags&Context.BIND_ABOVE_CLIENT) != 0) {
                 b.client.hasAboveClient = true;
             }
+            if (s.app != null) {
+                updateServiceClientActivitiesLocked(s.app, c);
+            }
             clist = mServiceConnections.get(binder);
             if (clist == null) {
                 clist = new ArrayList<ConnectionRecord>();
@@ -714,6 +753,7 @@
 
             if (s.app != null) {
                 // This could have made the service more important.
+                mAm.updateLruProcessLocked(s.app, s.app.hasClientActivities, b.client);
                 mAm.updateOomAdjLocked(s.app);
             }
 
@@ -1316,7 +1356,8 @@
 
         app.services.add(r);
         bumpServiceExecutingLocked(r, execInFg, "create");
-        mAm.updateLruProcessLocked(app, true, false);
+        mAm.updateLruProcessLocked(app, false, null);
+        mAm.updateOomAdjLocked();
 
         boolean created = false;
         try {
@@ -1601,6 +1642,9 @@
             if ((c.flags&Context.BIND_ABOVE_CLIENT) != 0) {
                 b.client.updateHasAboveClientLocked();
             }
+            if (s.app != null) {
+                updateServiceClientActivitiesLocked(s.app, c);
+            }
         }
         clist = mServiceConnections.get(binder);
         if (clist != null) {
@@ -1621,6 +1665,13 @@
                     && b.intent.hasBound) {
                 try {
                     bumpServiceExecutingLocked(s, false, "unbind");
+                    if (b.client != s.app && (c.flags&Context.BIND_WAIVE_PRIORITY) == 0
+                            && s.app.setProcState <= ActivityManager.PROCESS_STATE_RECEIVER) {
+                        // If this service's process is not already in the cached list,
+                        // then update it in the LRU list here because this may be causing
+                        // it to go down there and we want it to start out near the top.
+                        mAm.updateLruProcessLocked(s.app, false, null);
+                    }
                     mAm.updateOomAdjLocked(s.app);
                     b.intent.hasBound = false;
                     // Assume the client doesn't want to know about a rebind;
diff --git a/services/java/com/android/server/am/ActivityManagerService.java b/services/java/com/android/server/am/ActivityManagerService.java
index db49358..0507e60 100644
--- a/services/java/com/android/server/am/ActivityManagerService.java
+++ b/services/java/com/android/server/am/ActivityManagerService.java
@@ -34,7 +34,6 @@
 import com.android.internal.annotations.GuardedBy;
 import com.android.internal.app.IAppOpsService;
 import com.android.internal.app.ProcessStats;
-import com.android.internal.app.ResolverActivity;
 import com.android.internal.os.BackgroundThread;
 import com.android.internal.os.BatteryStatsImpl;
 import com.android.internal.os.ProcessCpuTracker;
@@ -218,6 +217,7 @@
     static final boolean DEBUG_IMMERSIVE = localLOGV || false;
     static final boolean DEBUG_MU = localLOGV || false;
     static final boolean DEBUG_OOM_ADJ = localLOGV || false;
+    static final boolean DEBUG_LRU = localLOGV || false;
     static final boolean DEBUG_PAUSE = localLOGV || false;
     static final boolean DEBUG_POWER = localLOGV || false;
     static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false;
@@ -1743,7 +1743,8 @@
                 synchronized (mSelf.mPidsSelfLocked) {
                     mSelf.mPidsSelfLocked.put(app.pid, app);
                 }
-                mSelf.updateLruProcessLocked(app, true, false);
+                mSelf.updateLruProcessLocked(app, false, null);
+                mSelf.updateOomAdjLocked();
             }
         } catch (PackageManager.NameNotFoundException e) {
             throw new RuntimeException(
@@ -2269,7 +2270,7 @@
 
         int lrui = mLruProcesses.lastIndexOf(app);
         if (lrui < 0) {
-            Log.wtf(TAG, "Adding dependent process " + app + " not on LRU list: "
+            Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: "
                     + what + " " + obj + " from " + srcApp);
             return index;
         }
@@ -2289,6 +2290,8 @@
         if (index > 0) {
             index--;
         }
+        if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index
+                + " in LRU list: " + app);
         mLruProcesses.add(index, app);
         return index;
     }
@@ -2306,8 +2309,9 @@
         }
     }
 
-    final void updateLruProcessLocked(ProcessRecord app, boolean oomAdj, boolean activityChange) {
-        final boolean hasActivity = app.activities.size() > 0;
+    final void updateLruProcessLocked(ProcessRecord app, boolean activityChange,
+            ProcessRecord client) {
+        final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities;
         final boolean hasService = false; // not impl yet. app.services.size() > 0;
         if (!activityChange && hasActivity) {
             // The process has activties, so we are only going to allow activity-based
@@ -2321,8 +2325,65 @@
         final long now = SystemClock.uptimeMillis();
         app.lastActivityTime = now;
 
+        // First a quick reject: if the app is already at the position we will
+        // put it, then there is nothing to do.
+        if (hasActivity) {
+            final int N = mLruProcesses.size();
+            if (N > 0 && mLruProcesses.get(N-1) == app) {
+                if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app);
+                return;
+            }
+        } else {
+            if (mLruProcessServiceStart > 0
+                    && mLruProcesses.get(mLruProcessServiceStart-1) == app) {
+                if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app);
+                return;
+            }
+        }
+
         int lrui = mLruProcesses.lastIndexOf(app);
 
+        if (app.persistent && lrui >= 0) {
+            // We don't care about the position of persistent processes, as long as
+            // they are in the list.
+            if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app);
+            return;
+        }
+
+        /* In progress: compute new position first, so we can avoid doing work
+           if the process is not actually going to move.  Not yet working.
+        int addIndex;
+        int nextIndex;
+        boolean inActivity = false, inService = false;
+        if (hasActivity) {
+            // Process has activities, put it at the very tipsy-top.
+            addIndex = mLruProcesses.size();
+            nextIndex = mLruProcessServiceStart;
+            inActivity = true;
+        } else if (hasService) {
+            // Process has services, put it at the top of the service list.
+            addIndex = mLruProcessActivityStart;
+            nextIndex = mLruProcessServiceStart;
+            inActivity = true;
+            inService = true;
+        } else  {
+            // Process not otherwise of interest, it goes to the top of the non-service area.
+            addIndex = mLruProcessServiceStart;
+            if (client != null) {
+                int clientIndex = mLruProcesses.lastIndexOf(client);
+                if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating "
+                        + app);
+                if (clientIndex >= 0 && addIndex > clientIndex) {
+                    addIndex = clientIndex;
+                }
+            }
+            nextIndex = addIndex > 0 ? addIndex-1 : addIndex;
+        }
+
+        Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act="
+                + mLruProcessActivityStart + "): " + app);
+        */
+
         if (lrui >= 0) {
             if (lrui < mLruProcessActivityStart) {
                 mLruProcessActivityStart--;
@@ -2330,23 +2391,91 @@
             if (lrui < mLruProcessServiceStart) {
                 mLruProcessServiceStart--;
             }
+            /*
+            if (addIndex > lrui) {
+                addIndex--;
+            }
+            if (nextIndex > lrui) {
+                nextIndex--;
+            }
+            */
             mLruProcesses.remove(lrui);
         }
 
+        /*
+        mLruProcesses.add(addIndex, app);
+        if (inActivity) {
+            mLruProcessActivityStart++;
+        }
+        if (inService) {
+            mLruProcessActivityStart++;
+        }
+        */
+
         int nextIndex;
         if (hasActivity) {
-            // Process has activities, put it at the very tipsy-top.
-            mLruProcesses.add(app);
-            nextIndex = mLruProcessActivityStart;
+            final int N = mLruProcesses.size();
+            if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) {
+                // Process doesn't have activities, but has clients with
+                // activities...  move it up, but one below the top (the top
+                // should always have a real activity).
+                if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app);
+                mLruProcesses.add(N-1, app);
+                // To keep it from spamming the LRU list (by making a bunch of clients),
+                // we will push down any other entries owned by the app.
+                final int uid = app.info.uid;
+                for (int i=N-2; i>mLruProcessActivityStart; i--) {
+                    ProcessRecord subProc = mLruProcesses.get(i);
+                    if (subProc.info.uid == uid) {
+                        // We want to push this one down the list.  If the process after
+                        // it is for the same uid, however, don't do so, because we don't
+                        // want them internally to be re-ordered.
+                        if (mLruProcesses.get(i-1).info.uid != uid) {
+                            if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i
+                                    + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1));
+                            ProcessRecord tmp = mLruProcesses.get(i);
+                            mLruProcesses.set(i, mLruProcesses.get(i-1));
+                            mLruProcesses.set(i-1, tmp);
+                            i--;
+                        }
+                    } else {
+                        // A gap, we can stop here.
+                        break;
+                    }
+                }
+            } else {
+                // Process has activities, put it at the very tipsy-top.
+                if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app);
+                mLruProcesses.add(app);
+            }
+            nextIndex = mLruProcessServiceStart;
         } else if (hasService) {
             // Process has services, put it at the top of the service list.
+            if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app);
             mLruProcesses.add(mLruProcessActivityStart, app);
             nextIndex = mLruProcessServiceStart;
             mLruProcessActivityStart++;
         } else  {
             // Process not otherwise of interest, it goes to the top of the non-service area.
-            mLruProcesses.add(mLruProcessServiceStart, app);
-            nextIndex = mLruProcessServiceStart-1;
+            int index = mLruProcessServiceStart;
+            if (client != null) {
+                // If there is a client, don't allow the process to be moved up higher
+                // in the list than that client.
+                int clientIndex = mLruProcesses.lastIndexOf(client);
+                if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client
+                        + " when updating " + app);
+                if (clientIndex <= lrui) {
+                    // Don't allow the client index restriction to push it down farther in the
+                    // list than it already is.
+                    clientIndex = lrui;
+                }
+                if (clientIndex >= 0 && index > clientIndex) {
+                    index = clientIndex;
+                }
+            }
+            if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app);
+            mLruProcesses.add(index, app);
+            nextIndex = index-1;
             mLruProcessActivityStart++;
             mLruProcessServiceStart++;
         }
@@ -2357,23 +2486,19 @@
             ConnectionRecord cr = app.connections.valueAt(j);
             if (cr.binding != null && !cr.serviceDead && cr.binding.service != null
                     && cr.binding.service.app != null
-                    && cr.binding.service.app.lruSeq != mLruSeq) {
+                    && cr.binding.service.app.lruSeq != mLruSeq
+                    && !cr.binding.service.app.persistent) {
                 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex,
                         "service connection", cr, app);
             }
         }
         for (int j=app.conProviders.size()-1; j>=0; j--) {
             ContentProviderRecord cpr = app.conProviders.get(j).provider;
-            if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq) {
+            if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) {
                 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex,
                         "provider reference", cpr, app);
             }
         }
-
-        //Slog.i(TAG, "Putting proc to front: " + app.processName);
-        if (oomAdj) {
-            updateOomAdjLocked();
-        }
     }
 
     final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) {
@@ -4831,7 +4956,7 @@
                     isRestrictedBackupMode || !normalMode, app.persistent,
                     new Configuration(mConfiguration), app.compat, getCommonServicesLocked(),
                     mCoreSettingsObserver.getCoreSettingsLocked());
-            updateLruProcessLocked(app, false, false);
+            updateLruProcessLocked(app, false, null);
             app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis();
         } catch (Exception e) {
             // todo: Yikes!  What should we do?  For now we will try to
@@ -7419,7 +7544,7 @@
                         // make sure to count it as being accessed and thus
                         // back up on the LRU list.  This is good because
                         // content providers are often expensive to start.
-                        updateLruProcessLocked(cpr.proc, false, false);
+                        updateLruProcessLocked(cpr.proc, false, null);
                     }
                 }
 
@@ -8028,7 +8153,8 @@
             if (isolated) {
                 mIsolatedProcesses.put(app.uid, app);
             }
-            updateLruProcessLocked(app, true, false);
+            updateLruProcessLocked(app, false, null);
+            updateOomAdjLocked();
         }
 
         // This package really, really can not be stopped.
@@ -10101,7 +10227,7 @@
         if (app.persistent) {
             outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT;
         }
-        if (app.hasActivities) {
+        if (app.activities.size() > 0) {
             outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES;
         }
         outInfo.lastTrimLevel = app.trimMemoryLevel;
@@ -11857,7 +11983,7 @@
                 thread = r.thread;
                 pid = r.pid;
                 oomAdj = r.getSetAdjWithServices();
-                hasActivities = r.hasActivities;
+                hasActivities = r.activities.size() > 0;
             }
             if (thread != null) {
                 if (!isCheckinRequest && dumpDetails) {
@@ -14079,7 +14205,6 @@
         app.adjTarget = null;
         app.empty = false;
         app.cached = false;
-        app.hasClientActivities = false;
 
         final int activitiesSize = app.activities.size();
 
@@ -14089,7 +14214,6 @@
             app.adjType = "fixed";
             app.adjSeq = mAdjSeq;
             app.curRawAdj = app.maxAdj;
-            app.hasActivities = false;
             app.foregroundActivities = false;
             app.keeping = true;
             app.curSchedGroup = Process.THREAD_GROUP_DEFAULT;
@@ -14101,16 +14225,12 @@
             app.systemNoUi = true;
             if (app == TOP_APP) {
                 app.systemNoUi = false;
-                app.hasActivities = true;
             } else if (activitiesSize > 0) {
                 for (int j = 0; j < activitiesSize; j++) {
                     final ActivityRecord r = app.activities.get(j);
                     if (r.visible) {
                         app.systemNoUi = false;
                     }
-                    if (r.app == app) {
-                        app.hasActivities = true;
-                    }
                 }
             }
             if (!app.systemNoUi) {
@@ -14121,7 +14241,6 @@
 
         app.keeping = false;
         app.systemNoUi = false;
-        app.hasActivities = false;
 
         // Determine the importance of the process, starting with most
         // important to least, and assign an appropriate OOM adjustment.
@@ -14138,7 +14257,6 @@
             app.adjType = "top-activity";
             foregroundActivities = true;
             interesting = true;
-            app.hasActivities = true;
             procState = ActivityManager.PROCESS_STATE_TOP;
         } else if (app.instrumentationClass != null) {
             // Don't want to kill running instrumentation.
@@ -14187,7 +14305,6 @@
                             + app + "?!?");
                     continue;
                 }
-                app.hasActivities = true;
                 if (r.visible) {
                     // App has a visible activity; only upgrade adjustment.
                     if (adj > ProcessList.VISIBLE_APP_ADJ) {
@@ -14436,27 +14553,6 @@
                                     clientAdj = adj;
                                 }
                             }
-                        } else if ((cr.flags&Context.BIND_AUTO_CREATE) != 0) {
-                            if ((cr.flags&Context.BIND_NOT_VISIBLE) == 0) {
-                                // If this connection is keeping the service
-                                // created, then we want to try to better follow
-                                // its memory management semantics for activities.
-                                // That is, if it is sitting in the background
-                                // LRU list as a cached process (with activities),
-                                // we don't want the service it is connected to
-                                // to go into the empty LRU and quickly get killed,
-                                // because all we'll do is just end up restarting
-                                // the service.
-                                if (client.hasActivities) {
-                                    if (procState >
-                                            ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT) {
-                                        procState =
-                                                ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT;
-                                        app.adjType = "cch-client-act";
-                                    }
-                                    app.hasClientActivities = true;
-                                }
-                            }
                         }
                         if (adj > clientAdj) {
                             // If this process has recently shown UI, and
@@ -14674,6 +14770,12 @@
             }
         }
 
+        if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY && app.hasClientActivities) {
+            // This is a cached process, but with client activities.  Mark it so.
+            procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT;
+            app.adjType = "cch-client-act";
+        }
+
         if (adj == ProcessList.SERVICE_ADJ) {
             if (doingAll) {
                 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3);
@@ -15302,7 +15404,6 @@
         // application processes based on their current state.
         int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ;
         int nextCachedAdj = curCachedAdj+1;
-        int curClientCachedAdj = curCachedAdj+1;
         int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ;
         int nextEmptyAdj = curEmptyAdj+2;
         for (int i=N-1; i>=0; i--) {
@@ -15317,11 +15418,15 @@
                 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) {
                     switch (app.curProcState) {
                         case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY:
+                        case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT:
                             // This process is a cached process holding activities...
                             // assign it the next cached value for that type, and then
                             // step that cached level.
                             app.curRawAdj = curCachedAdj;
                             app.curAdj = app.modifyRawOomAdj(curCachedAdj);
+                            if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i
+                                    + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj
+                                    + ")");
                             if (curCachedAdj != nextCachedAdj) {
                                 stepCached++;
                                 if (stepCached >= cachedFactor) {
@@ -15331,25 +15436,9 @@
                                     if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) {
                                         nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ;
                                     }
-                                    if (curClientCachedAdj <= curCachedAdj) {
-                                        curClientCachedAdj = curCachedAdj + 1;
-                                        if (curClientCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) {
-                                            curClientCachedAdj = ProcessList.CACHED_APP_MAX_ADJ;
-                                        }
-                                    }
                                 }
                             }
                             break;
-                        case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT:
-                            // Special case for cached client processes...  just step
-                            // down from after regular cached processes.
-                            app.curRawAdj = curClientCachedAdj;
-                            app.curAdj = app.modifyRawOomAdj(curClientCachedAdj);
-                            curClientCachedAdj++;
-                            if (curClientCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) {
-                                curClientCachedAdj = ProcessList.CACHED_APP_MAX_ADJ;
-                            }
-                            break;
                         default:
                             // For everything else, assign next empty cached process
                             // level and bump that up.  Note that this means that
@@ -15358,6 +15447,9 @@
                             // state is still as a service), which is what we want.
                             app.curRawAdj = curEmptyAdj;
                             app.curAdj = app.modifyRawOomAdj(curEmptyAdj);
+                            if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i
+                                    + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj
+                                    + ")");
                             if (curEmptyAdj != nextEmptyAdj) {
                                 stepEmpty++;
                                 if (stepEmpty >= emptyFactor) {
diff --git a/services/java/com/android/server/am/ActivityStack.java b/services/java/com/android/server/am/ActivityStack.java
index 44ff3bc..e87bc52 100644
--- a/services/java/com/android/server/am/ActivityStack.java
+++ b/services/java/com/android/server/am/ActivityStack.java
@@ -61,7 +61,6 @@
 import android.content.res.Configuration;
 import android.content.res.Resources;
 import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
 import android.net.Uri;
 import android.os.Binder;
 import android.os.Bundle;
@@ -1398,7 +1397,7 @@
             if (next.app != null && next.app.thread != null) {
                 // No reason to do full oom adj update here; we'll let that
                 // happen whenever it needs to later.
-                mService.updateLruProcessLocked(next.app, false, true);
+                mService.updateLruProcessLocked(next.app, true, null);
             }
             if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
             return true;
@@ -1526,8 +1525,9 @@
             mResumedActivity = next;
             next.task.touchActiveTime();
             mService.addRecentTaskLocked(next.task);
-            mService.updateLruProcessLocked(next.app, true, true);
+            mService.updateLruProcessLocked(next.app, true, null);
             updateLRUListLocked(next);
+            mService.updateOomAdjLocked();
 
             // Have the window manager re-evaluate the orientation of
             // the screen based on the new activity order.
@@ -2781,7 +2781,7 @@
                 }
                 if (r.app.activities.isEmpty()) {
                     // No longer have activities, so update LRU list and oom adj.
-                    mService.updateLruProcessLocked(r.app, false, false);
+                    mService.updateLruProcessLocked(r.app, false, null);
                     mService.updateOomAdjLocked();
                 }
             }
diff --git a/services/java/com/android/server/am/ActivityStackSupervisor.java b/services/java/com/android/server/am/ActivityStackSupervisor.java
index 7650a65..8251364 100644
--- a/services/java/com/android/server/am/ActivityStackSupervisor.java
+++ b/services/java/com/android/server/am/ActivityStackSupervisor.java
@@ -905,7 +905,8 @@
         if (idx < 0) {
             app.activities.add(r);
         }
-        mService.updateLruProcessLocked(app, true, true);
+        mService.updateLruProcessLocked(app, true, null);
+        mService.updateOomAdjLocked();
 
         final ActivityStack stack = r.task.stack;
         try {
diff --git a/services/java/com/android/server/am/BroadcastQueue.java b/services/java/com/android/server/am/BroadcastQueue.java
index 5e80135..dd3d8aa 100644
--- a/services/java/com/android/server/am/BroadcastQueue.java
+++ b/services/java/com/android/server/am/BroadcastQueue.java
@@ -220,7 +220,8 @@
         r.curApp = app;
         app.curReceiver = r;
         app.forceProcessStateUpTo(ActivityManager.PROCESS_STATE_RECEIVER);
-        mService.updateLruProcessLocked(app, true, false);
+        mService.updateLruProcessLocked(app, false, null);
+        mService.updateOomAdjLocked();
 
         // Tell the application to launch this receiver.
         r.intent.setComponent(r.curComponent);
diff --git a/services/java/com/android/server/am/ProcessRecord.java b/services/java/com/android/server/am/ProcessRecord.java
index 486e916..187cd44 100644
--- a/services/java/com/android/server/am/ProcessRecord.java
+++ b/services/java/com/android/server/am/ProcessRecord.java
@@ -86,7 +86,6 @@
     boolean keeping;            // Actively running code so don't kill due to that?
     boolean setIsForeground;    // Running foreground UI when last set?
     boolean notCachedSinceIdle; // Has this process not been in a cached state since last idle?
-    boolean hasActivities;      // Are there any activities running in this process?
     boolean hasClientActivities;  // Are there any client services with activities?
     boolean hasStartedServices; // Are there any started services running in this process?
     boolean foregroundServices; // Running any services that are foreground?
@@ -265,9 +264,8 @@
             pw.print(prefix); pw.print("persistent="); pw.print(persistent);
                     pw.print(" removed="); pw.println(removed);
         }
-        if (hasActivities || hasClientActivities || foregroundActivities) {
-            pw.print(prefix); pw.print("hasActivities="); pw.print(hasActivities);
-                    pw.print(" hasClientActivities="); pw.print(hasClientActivities);
+        if (hasClientActivities || foregroundActivities) {
+            pw.print(prefix); pw.print("hasClientActivities="); pw.print(hasClientActivities);
                     pw.print(" foregroundActivities="); pw.println(foregroundActivities);
         }
         if (hasStartedServices) {