Home | History | Annotate | Download | only in am
      1 /*
      2  * Copyright (C) 2013 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.server.am;
     18 
     19 import static android.Manifest.permission.START_ANY_ACTIVITY;
     20 import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
     21 import static android.content.Intent.FLAG_ACTIVITY_TASK_ON_HOME;
     22 import static android.content.pm.PackageManager.PERMISSION_GRANTED;
     23 import static com.android.server.am.ActivityManagerService.localLOGV;
     24 import static com.android.server.am.ActivityManagerService.DEBUG_CONFIGURATION;
     25 import static com.android.server.am.ActivityManagerService.DEBUG_FOCUS;
     26 import static com.android.server.am.ActivityManagerService.DEBUG_PAUSE;
     27 import static com.android.server.am.ActivityManagerService.DEBUG_RESULTS;
     28 import static com.android.server.am.ActivityManagerService.DEBUG_STACK;
     29 import static com.android.server.am.ActivityManagerService.DEBUG_SWITCH;
     30 import static com.android.server.am.ActivityManagerService.DEBUG_TASKS;
     31 import static com.android.server.am.ActivityManagerService.DEBUG_USER_LEAVING;
     32 import static com.android.server.am.ActivityManagerService.FIRST_SUPERVISOR_STACK_MSG;
     33 import static com.android.server.am.ActivityManagerService.TAG;
     34 
     35 import android.app.Activity;
     36 import android.app.ActivityManager;
     37 import android.app.ActivityOptions;
     38 import android.app.AppGlobals;
     39 import android.app.IActivityManager;
     40 import android.app.IApplicationThread;
     41 import android.app.IThumbnailReceiver;
     42 import android.app.PendingIntent;
     43 import android.app.ActivityManager.RunningTaskInfo;
     44 import android.app.IActivityManager.WaitResult;
     45 import android.app.ResultInfo;
     46 import android.content.ComponentName;
     47 import android.content.Context;
     48 import android.content.IIntentSender;
     49 import android.content.Intent;
     50 import android.content.IntentSender;
     51 import android.content.pm.ActivityInfo;
     52 import android.content.pm.ApplicationInfo;
     53 import android.content.pm.PackageManager;
     54 import android.content.pm.ResolveInfo;
     55 import android.content.res.Configuration;
     56 import android.os.Binder;
     57 import android.os.Bundle;
     58 import android.os.Debug;
     59 import android.os.Handler;
     60 import android.os.IBinder;
     61 import android.os.Looper;
     62 import android.os.Message;
     63 import android.os.ParcelFileDescriptor;
     64 import android.os.PowerManager;
     65 import android.os.Process;
     66 import android.os.RemoteException;
     67 import android.os.SystemClock;
     68 import android.os.UserHandle;
     69 import android.util.EventLog;
     70 import android.util.Slog;
     71 import android.util.SparseIntArray;
     72 
     73 import com.android.internal.app.HeavyWeightSwitcherActivity;
     74 import com.android.internal.os.TransferPipe;
     75 import com.android.server.am.ActivityManagerService.PendingActivityLaunch;
     76 import com.android.server.am.ActivityStack.ActivityState;
     77 import com.android.server.wm.StackBox;
     78 import com.android.server.wm.WindowManagerService;
     79 
     80 import java.io.FileDescriptor;
     81 import java.io.IOException;
     82 import java.io.PrintWriter;
     83 import java.util.ArrayList;
     84 import java.util.List;
     85 
     86 public final class ActivityStackSupervisor {
     87     static final boolean DEBUG = ActivityManagerService.DEBUG || false;
     88     static final boolean DEBUG_ADD_REMOVE = DEBUG || false;
     89     static final boolean DEBUG_APP = DEBUG || false;
     90     static final boolean DEBUG_SAVED_STATE = DEBUG || false;
     91     static final boolean DEBUG_STATES = DEBUG || false;
     92     static final boolean DEBUG_IDLE = DEBUG || false;
     93 
     94     public static final int HOME_STACK_ID = 0;
     95 
     96     /** How long we wait until giving up on the last activity telling us it is idle. */
     97     static final int IDLE_TIMEOUT = 10*1000;
     98 
     99     /** How long we can hold the sleep wake lock before giving up. */
    100     static final int SLEEP_TIMEOUT = 5*1000;
    101 
    102     // How long we can hold the launch wake lock before giving up.
    103     static final int LAUNCH_TIMEOUT = 10*1000;
    104 
    105     static final int IDLE_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG;
    106     static final int IDLE_NOW_MSG = FIRST_SUPERVISOR_STACK_MSG + 1;
    107     static final int RESUME_TOP_ACTIVITY_MSG = FIRST_SUPERVISOR_STACK_MSG + 2;
    108     static final int SLEEP_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG + 3;
    109     static final int LAUNCH_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG + 4;
    110 
    111     // For debugging to make sure the caller when acquiring/releasing our
    112     // wake lock is the system process.
    113     static final boolean VALIDATE_WAKE_LOCK_CALLER = false;
    114 
    115     final ActivityManagerService mService;
    116     final Context mContext;
    117     final Looper mLooper;
    118 
    119     final ActivityStackSupervisorHandler mHandler;
    120 
    121     /** Short cut */
    122     WindowManagerService mWindowManager;
    123 
    124     /** Dismiss the keyguard after the next activity is displayed? */
    125     boolean mDismissKeyguardOnNextActivity = false;
    126 
    127     /** Identifier counter for all ActivityStacks */
    128     private int mLastStackId = HOME_STACK_ID;
    129 
    130     /** Task identifier that activities are currently being started in.  Incremented each time a
    131      * new task is created. */
    132     private int mCurTaskId = 0;
    133 
    134     /** The current user */
    135     private int mCurrentUser;
    136 
    137     /** The stack containing the launcher app */
    138     private ActivityStack mHomeStack;
    139 
    140     /** The non-home stack currently receiving input or launching the next activity. If home is
    141      * in front then mHomeStack overrides mFocusedStack.
    142      * DO NOT ACCESS DIRECTLY - It may be null, use getFocusedStack() */
    143     private ActivityStack mFocusedStack;
    144 
    145     /** All the non-launcher stacks */
    146     private ArrayList<ActivityStack> mStacks = new ArrayList<ActivityStack>();
    147 
    148     private static final int STACK_STATE_HOME_IN_FRONT = 0;
    149     private static final int STACK_STATE_HOME_TO_BACK = 1;
    150     private static final int STACK_STATE_HOME_IN_BACK = 2;
    151     private static final int STACK_STATE_HOME_TO_FRONT = 3;
    152     private int mStackState = STACK_STATE_HOME_IN_FRONT;
    153 
    154     /** List of activities that are waiting for a new activity to become visible before completing
    155      * whatever operation they are supposed to do. */
    156     final ArrayList<ActivityRecord> mWaitingVisibleActivities = new ArrayList<ActivityRecord>();
    157 
    158     /** List of processes waiting to find out about the next visible activity. */
    159     final ArrayList<IActivityManager.WaitResult> mWaitingActivityVisible =
    160             new ArrayList<IActivityManager.WaitResult>();
    161 
    162     /** List of processes waiting to find out about the next launched activity. */
    163     final ArrayList<IActivityManager.WaitResult> mWaitingActivityLaunched =
    164             new ArrayList<IActivityManager.WaitResult>();
    165 
    166     /** List of activities that are ready to be stopped, but waiting for the next activity to
    167      * settle down before doing so. */
    168     final ArrayList<ActivityRecord> mStoppingActivities = new ArrayList<ActivityRecord>();
    169 
    170     /** List of activities that are ready to be finished, but waiting for the previous activity to
    171      * settle down before doing so.  It contains ActivityRecord objects. */
    172     final ArrayList<ActivityRecord> mFinishingActivities = new ArrayList<ActivityRecord>();
    173 
    174     /** List of activities that are in the process of going to sleep. */
    175     final ArrayList<ActivityRecord> mGoingToSleepActivities = new ArrayList<ActivityRecord>();
    176 
    177     /** List of ActivityRecord objects that have been finished and must still report back to a
    178      * pending thumbnail receiver. */
    179     final ArrayList<ActivityRecord> mCancelledThumbnails = new ArrayList<ActivityRecord>();
    180 
    181     /** Used on user changes */
    182     final ArrayList<UserStartedState> mStartingUsers = new ArrayList<UserStartedState>();
    183 
    184     /** Set to indicate whether to issue an onUserLeaving callback when a newly launched activity
    185      * is being brought in front of us. */
    186     boolean mUserLeaving = false;
    187 
    188     /** Set when we have taken too long waiting to go to sleep. */
    189     boolean mSleepTimeout = false;
    190 
    191     /**
    192      * We don't want to allow the device to go to sleep while in the process
    193      * of launching an activity.  This is primarily to allow alarm intent
    194      * receivers to launch an activity and get that to run before the device
    195      * goes back to sleep.
    196      */
    197     final PowerManager.WakeLock mLaunchingActivity;
    198 
    199     /**
    200      * Set when the system is going to sleep, until we have
    201      * successfully paused the current activity and released our wake lock.
    202      * At that point the system is allowed to actually sleep.
    203      */
    204     final PowerManager.WakeLock mGoingToSleep;
    205 
    206     /** Stack id of the front stack when user switched, indexed by userId. */
    207     SparseIntArray mUserStackInFront = new SparseIntArray(2);
    208 
    209     public ActivityStackSupervisor(ActivityManagerService service, Context context,
    210             Looper looper) {
    211         mService = service;
    212         mContext = context;
    213         mLooper = looper;
    214         PowerManager pm = (PowerManager)context.getSystemService(Context.POWER_SERVICE);
    215         mGoingToSleep = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "ActivityManager-Sleep");
    216         mHandler = new ActivityStackSupervisorHandler(looper);
    217         if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) {
    218             throw new IllegalStateException("Calling must be system uid");
    219         }
    220         mLaunchingActivity =
    221                 pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "ActivityManager-Launch");
    222         mLaunchingActivity.setReferenceCounted(false);
    223     }
    224 
    225     void setWindowManager(WindowManagerService wm) {
    226         mWindowManager = wm;
    227         mHomeStack = new ActivityStack(mService, mContext, mLooper, HOME_STACK_ID);
    228         mStacks.add(mHomeStack);
    229     }
    230 
    231     void dismissKeyguard() {
    232         if (ActivityManagerService.DEBUG_LOCKSCREEN) mService.logLockScreen("");
    233         if (mDismissKeyguardOnNextActivity) {
    234             mDismissKeyguardOnNextActivity = false;
    235             mWindowManager.dismissKeyguard();
    236         }
    237     }
    238 
    239     ActivityStack getFocusedStack() {
    240         if (mFocusedStack == null) {
    241             return mHomeStack;
    242         }
    243         switch (mStackState) {
    244             case STACK_STATE_HOME_IN_FRONT:
    245             case STACK_STATE_HOME_TO_FRONT:
    246                 return mHomeStack;
    247             case STACK_STATE_HOME_IN_BACK:
    248             case STACK_STATE_HOME_TO_BACK:
    249             default:
    250                 return mFocusedStack;
    251         }
    252     }
    253 
    254     ActivityStack getLastStack() {
    255         switch (mStackState) {
    256             case STACK_STATE_HOME_IN_FRONT:
    257             case STACK_STATE_HOME_TO_BACK:
    258                 return mHomeStack;
    259             case STACK_STATE_HOME_TO_FRONT:
    260             case STACK_STATE_HOME_IN_BACK:
    261             default:
    262                 return mFocusedStack;
    263         }
    264     }
    265 
    266     boolean isFrontStack(ActivityStack stack) {
    267         return !(stack.isHomeStack() ^ getFocusedStack().isHomeStack());
    268     }
    269 
    270     void moveHomeStack(boolean toFront) {
    271         final boolean homeInFront = isFrontStack(mHomeStack);
    272         if (homeInFront ^ toFront) {
    273             if (DEBUG_STACK) Slog.d(TAG, "moveHomeTask: mStackState old=" +
    274                     stackStateToString(mStackState) + " new=" + stackStateToString(homeInFront ?
    275                     STACK_STATE_HOME_TO_BACK : STACK_STATE_HOME_TO_FRONT));
    276             mStackState = homeInFront ? STACK_STATE_HOME_TO_BACK : STACK_STATE_HOME_TO_FRONT;
    277         }
    278     }
    279 
    280     void moveHomeToTop() {
    281         moveHomeStack(true);
    282         mHomeStack.moveHomeTaskToTop();
    283     }
    284 
    285     boolean resumeHomeActivity(ActivityRecord prev) {
    286         moveHomeToTop();
    287         if (prev != null) {
    288             prev.task.mOnTopOfHome = false;
    289         }
    290         ActivityRecord r = mHomeStack.topRunningActivityLocked(null);
    291         if (r != null && r.isHomeActivity()) {
    292             mService.setFocusedActivityLocked(r);
    293             return resumeTopActivitiesLocked(mHomeStack, prev, null);
    294         }
    295         return mService.startHomeActivityLocked(mCurrentUser);
    296     }
    297 
    298     void setDismissKeyguard(boolean dismiss) {
    299         if (ActivityManagerService.DEBUG_LOCKSCREEN) mService.logLockScreen(" dismiss=" + dismiss);
    300         mDismissKeyguardOnNextActivity = dismiss;
    301     }
    302 
    303     TaskRecord anyTaskForIdLocked(int id) {
    304         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    305             ActivityStack stack = mStacks.get(stackNdx);
    306             TaskRecord task = stack.taskForIdLocked(id);
    307             if (task != null) {
    308                 return task;
    309             }
    310         }
    311         return null;
    312     }
    313 
    314     ActivityRecord isInAnyStackLocked(IBinder token) {
    315         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    316             final ActivityRecord r = mStacks.get(stackNdx).isInStackLocked(token);
    317             if (r != null) {
    318                 return r;
    319             }
    320         }
    321         return null;
    322     }
    323 
    324     int getNextTaskId() {
    325         do {
    326             mCurTaskId++;
    327             if (mCurTaskId <= 0) {
    328                 mCurTaskId = 1;
    329             }
    330         } while (anyTaskForIdLocked(mCurTaskId) != null);
    331         return mCurTaskId;
    332     }
    333 
    334     void removeTask(TaskRecord task) {
    335         mWindowManager.removeTask(task.taskId);
    336         final ActivityStack stack = task.stack;
    337         final ActivityRecord r = stack.mResumedActivity;
    338         if (r != null && r.task == task) {
    339             stack.mResumedActivity = null;
    340         }
    341         if (stack.removeTask(task) && !stack.isHomeStack()) {
    342             if (DEBUG_STACK) Slog.i(TAG, "removeTask: removing stack " + stack);
    343             mStacks.remove(stack);
    344             final int stackId = stack.mStackId;
    345             final int nextStackId = mWindowManager.removeStack(stackId);
    346             // TODO: Perhaps we need to let the ActivityManager determine the next focus...
    347             if (mFocusedStack == null || mFocusedStack.mStackId == stackId) {
    348                 // If this is the last app stack, set mFocusedStack to null.
    349                 mFocusedStack = nextStackId == HOME_STACK_ID ? null : getStack(nextStackId);
    350             }
    351         }
    352     }
    353 
    354     ActivityRecord resumedAppLocked() {
    355         ActivityStack stack = getFocusedStack();
    356         if (stack == null) {
    357             return null;
    358         }
    359         ActivityRecord resumedActivity = stack.mResumedActivity;
    360         if (resumedActivity == null || resumedActivity.app == null) {
    361             resumedActivity = stack.mPausingActivity;
    362             if (resumedActivity == null || resumedActivity.app == null) {
    363                 resumedActivity = stack.topRunningActivityLocked(null);
    364             }
    365         }
    366         return resumedActivity;
    367     }
    368 
    369     boolean attachApplicationLocked(ProcessRecord app, boolean headless) throws Exception {
    370         boolean didSomething = false;
    371         final String processName = app.processName;
    372         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    373             final ActivityStack stack = mStacks.get(stackNdx);
    374             if (!isFrontStack(stack)) {
    375                 continue;
    376             }
    377             ActivityRecord hr = stack.topRunningActivityLocked(null);
    378             if (hr != null) {
    379                 if (hr.app == null && app.uid == hr.info.applicationInfo.uid
    380                         && processName.equals(hr.processName)) {
    381                     try {
    382                         if (headless) {
    383                             Slog.e(TAG, "Starting activities not supported on headless device: "
    384                                     + hr);
    385                         } else if (realStartActivityLocked(hr, app, true, true)) {
    386                             didSomething = true;
    387                         }
    388                     } catch (Exception e) {
    389                         Slog.w(TAG, "Exception in new application when starting activity "
    390                               + hr.intent.getComponent().flattenToShortString(), e);
    391                         throw e;
    392                     }
    393                 }
    394             }
    395         }
    396         if (!didSomething) {
    397             ensureActivitiesVisibleLocked(null, 0);
    398         }
    399         return didSomething;
    400     }
    401 
    402     boolean allResumedActivitiesIdle() {
    403         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    404             final ActivityStack stack = mStacks.get(stackNdx);
    405             if (!isFrontStack(stack)) {
    406                 continue;
    407             }
    408             final ActivityRecord resumedActivity = stack.mResumedActivity;
    409             if (resumedActivity == null || !resumedActivity.idle) {
    410                 return false;
    411             }
    412         }
    413         return true;
    414     }
    415 
    416     boolean allResumedActivitiesComplete() {
    417         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    418             final ActivityStack stack = mStacks.get(stackNdx);
    419             if (isFrontStack(stack)) {
    420                 final ActivityRecord r = stack.mResumedActivity;
    421                 if (r != null && r.state != ActivityState.RESUMED) {
    422                     return false;
    423                 }
    424             }
    425         }
    426         // TODO: Not sure if this should check if all Paused are complete too.
    427         switch (mStackState) {
    428             case STACK_STATE_HOME_TO_BACK:
    429                 if (DEBUG_STACK) Slog.d(TAG, "allResumedActivitiesComplete: mStackState old=" +
    430                         stackStateToString(STACK_STATE_HOME_TO_BACK) + " new=" +
    431                         stackStateToString(STACK_STATE_HOME_IN_BACK));
    432                 mStackState = STACK_STATE_HOME_IN_BACK;
    433                 break;
    434             case STACK_STATE_HOME_TO_FRONT:
    435                 if (DEBUG_STACK) Slog.d(TAG, "allResumedActivitiesComplete: mStackState old=" +
    436                         stackStateToString(STACK_STATE_HOME_TO_FRONT) + " new=" +
    437                         stackStateToString(STACK_STATE_HOME_IN_FRONT));
    438                 mStackState = STACK_STATE_HOME_IN_FRONT;
    439                 break;
    440         }
    441         return true;
    442     }
    443 
    444     boolean allResumedActivitiesVisible() {
    445         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    446             final ActivityStack stack = mStacks.get(stackNdx);
    447             final ActivityRecord r = stack.mResumedActivity;
    448             if (r != null && (!r.nowVisible || r.waitingVisible)) {
    449                 return false;
    450             }
    451         }
    452         return true;
    453     }
    454 
    455     /**
    456      * Pause all activities in either all of the stacks or just the back stacks.
    457      * @param userLeaving Passed to pauseActivity() to indicate whether to call onUserLeaving().
    458      * @return true if any activity was paused as a result of this call.
    459      */
    460     boolean pauseBackStacks(boolean userLeaving) {
    461         boolean someActivityPaused = false;
    462         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    463             final ActivityStack stack = mStacks.get(stackNdx);
    464             if (!isFrontStack(stack) && stack.mResumedActivity != null) {
    465                 if (DEBUG_STATES) Slog.d(TAG, "pauseBackStacks: stack=" + stack +
    466                         " mResumedActivity=" + stack.mResumedActivity);
    467                 stack.startPausingLocked(userLeaving, false);
    468                 someActivityPaused = true;
    469             }
    470         }
    471         return someActivityPaused;
    472     }
    473 
    474     boolean allPausedActivitiesComplete() {
    475         boolean pausing = true;
    476         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    477             final ActivityStack stack = mStacks.get(stackNdx);
    478             final ActivityRecord r = stack.mPausingActivity;
    479             if (r != null && r.state != ActivityState.PAUSED
    480                     && r.state != ActivityState.STOPPED
    481                     && r.state != ActivityState.STOPPING) {
    482                 if (DEBUG_STATES) {
    483                     Slog.d(TAG, "allPausedActivitiesComplete: r=" + r + " state=" + r.state);
    484                     pausing = false;
    485                 } else {
    486                     return false;
    487                 }
    488             }
    489         }
    490         return pausing;
    491     }
    492 
    493     void reportActivityVisibleLocked(ActivityRecord r) {
    494         for (int i = mWaitingActivityVisible.size()-1; i >= 0; i--) {
    495             WaitResult w = mWaitingActivityVisible.get(i);
    496             w.timeout = false;
    497             if (r != null) {
    498                 w.who = new ComponentName(r.info.packageName, r.info.name);
    499             }
    500             w.totalTime = SystemClock.uptimeMillis() - w.thisTime;
    501             w.thisTime = w.totalTime;
    502         }
    503         mService.notifyAll();
    504         dismissKeyguard();
    505     }
    506 
    507     void reportActivityLaunchedLocked(boolean timeout, ActivityRecord r,
    508             long thisTime, long totalTime) {
    509         for (int i = mWaitingActivityLaunched.size() - 1; i >= 0; i--) {
    510             WaitResult w = mWaitingActivityLaunched.remove(i);
    511             w.timeout = timeout;
    512             if (r != null) {
    513                 w.who = new ComponentName(r.info.packageName, r.info.name);
    514             }
    515             w.thisTime = thisTime;
    516             w.totalTime = totalTime;
    517         }
    518         mService.notifyAll();
    519     }
    520 
    521     ActivityRecord topRunningActivityLocked() {
    522         final ActivityStack focusedStack = getFocusedStack();
    523         ActivityRecord r = focusedStack.topRunningActivityLocked(null);
    524         if (r != null) {
    525             return r;
    526         }
    527 
    528         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
    529             final ActivityStack stack = mStacks.get(stackNdx);
    530             if (stack != focusedStack && isFrontStack(stack)) {
    531                 r = stack.topRunningActivityLocked(null);
    532                 if (r != null) {
    533                     return r;
    534                 }
    535             }
    536         }
    537         return null;
    538     }
    539 
    540     ActivityRecord getTasksLocked(int maxNum, IThumbnailReceiver receiver,
    541             PendingThumbnailsRecord pending, List<RunningTaskInfo> list) {
    542         ActivityRecord r = null;
    543 
    544         // Gather all of the running tasks for each stack into runningTaskLists.
    545         final int numStacks = mStacks.size();
    546         ArrayList<RunningTaskInfo>[] runningTaskLists = new ArrayList[numStacks];
    547         for (int stackNdx = numStacks - 1; stackNdx >= 0; --stackNdx) {
    548             final ActivityStack stack = mStacks.get(stackNdx);
    549             ArrayList<RunningTaskInfo> stackTaskList = new ArrayList<RunningTaskInfo>();
    550             runningTaskLists[stackNdx] = stackTaskList;
    551             final ActivityRecord ar = stack.getTasksLocked(receiver, pending, stackTaskList);
    552             if (isFrontStack(stack)) {
    553                 r = ar;
    554             }
    555         }
    556 
    557         // The lists are already sorted from most recent to oldest. Just pull the most recent off
    558         // each list and add it to list. Stop when all lists are empty or maxNum reached.
    559         while (maxNum > 0) {
    560             long mostRecentActiveTime = Long.MIN_VALUE;
    561             ArrayList<RunningTaskInfo> selectedStackList = null;
    562             for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
    563                 ArrayList<RunningTaskInfo> stackTaskList = runningTaskLists[stackNdx];
    564                 if (!stackTaskList.isEmpty()) {
    565                     final long lastActiveTime = stackTaskList.get(0).lastActiveTime;
    566                     if (lastActiveTime > mostRecentActiveTime) {
    567                         mostRecentActiveTime = lastActiveTime;
    568                         selectedStackList = stackTaskList;
    569                     }
    570                 }
    571             }
    572             if (selectedStackList != null) {
    573                 list.add(selectedStackList.remove(0));
    574                 --maxNum;
    575             } else {
    576                 break;
    577             }
    578         }
    579 
    580         return r;
    581     }
    582 
    583     ActivityInfo resolveActivity(Intent intent, String resolvedType, int startFlags,
    584             String profileFile, ParcelFileDescriptor profileFd, int userId) {
    585         // Collect information about the target of the Intent.
    586         ActivityInfo aInfo;
    587         try {
    588             ResolveInfo rInfo =
    589                 AppGlobals.getPackageManager().resolveIntent(
    590                         intent, resolvedType,
    591                         PackageManager.MATCH_DEFAULT_ONLY
    592                                     | ActivityManagerService.STOCK_PM_FLAGS, userId);
    593             aInfo = rInfo != null ? rInfo.activityInfo : null;
    594         } catch (RemoteException e) {
    595             aInfo = null;
    596         }
    597 
    598         if (aInfo != null) {
    599             // Store the found target back into the intent, because now that
    600             // we have it we never want to do this again.  For example, if the
    601             // user navigates back to this point in the history, we should
    602             // always restart the exact same activity.
    603             intent.setComponent(new ComponentName(
    604                     aInfo.applicationInfo.packageName, aInfo.name));
    605 
    606             // Don't debug things in the system process
    607             if ((startFlags&ActivityManager.START_FLAG_DEBUG) != 0) {
    608                 if (!aInfo.processName.equals("system")) {
    609                     mService.setDebugApp(aInfo.processName, true, false);
    610                 }
    611             }
    612 
    613             if ((startFlags&ActivityManager.START_FLAG_OPENGL_TRACES) != 0) {
    614                 if (!aInfo.processName.equals("system")) {
    615                     mService.setOpenGlTraceApp(aInfo.applicationInfo, aInfo.processName);
    616                 }
    617             }
    618 
    619             if (profileFile != null) {
    620                 if (!aInfo.processName.equals("system")) {
    621                     mService.setProfileApp(aInfo.applicationInfo, aInfo.processName,
    622                             profileFile, profileFd,
    623                             (startFlags&ActivityManager.START_FLAG_AUTO_STOP_PROFILER) != 0);
    624                 }
    625             }
    626         }
    627         return aInfo;
    628     }
    629 
    630     void startHomeActivity(Intent intent, ActivityInfo aInfo) {
    631         moveHomeToTop();
    632         startActivityLocked(null, intent, null, aInfo, null, null, 0, 0, 0, null, 0,
    633                 null, false, null);
    634     }
    635 
    636     final int startActivityMayWait(IApplicationThread caller, int callingUid,
    637             String callingPackage, Intent intent, String resolvedType, IBinder resultTo,
    638             String resultWho, int requestCode, int startFlags, String profileFile,
    639             ParcelFileDescriptor profileFd, WaitResult outResult, Configuration config,
    640             Bundle options, int userId) {
    641         // Refuse possible leaked file descriptors
    642         if (intent != null && intent.hasFileDescriptors()) {
    643             throw new IllegalArgumentException("File descriptors passed in Intent");
    644         }
    645         boolean componentSpecified = intent.getComponent() != null;
    646 
    647         // Don't modify the client's object!
    648         intent = new Intent(intent);
    649 
    650         // Collect information about the target of the Intent.
    651         ActivityInfo aInfo = resolveActivity(intent, resolvedType, startFlags,
    652                 profileFile, profileFd, userId);
    653 
    654         synchronized (mService) {
    655             int callingPid;
    656             if (callingUid >= 0) {
    657                 callingPid = -1;
    658             } else if (caller == null) {
    659                 callingPid = Binder.getCallingPid();
    660                 callingUid = Binder.getCallingUid();
    661             } else {
    662                 callingPid = callingUid = -1;
    663             }
    664 
    665             final ActivityStack stack = getFocusedStack();
    666             stack.mConfigWillChange = config != null
    667                     && mService.mConfiguration.diff(config) != 0;
    668             if (DEBUG_CONFIGURATION) Slog.v(TAG,
    669                     "Starting activity when config will change = " + stack.mConfigWillChange);
    670 
    671             final long origId = Binder.clearCallingIdentity();
    672 
    673             if (aInfo != null &&
    674                     (aInfo.applicationInfo.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) {
    675                 // This may be a heavy-weight process!  Check to see if we already
    676                 // have another, different heavy-weight process running.
    677                 if (aInfo.processName.equals(aInfo.applicationInfo.packageName)) {
    678                     if (mService.mHeavyWeightProcess != null &&
    679                             (mService.mHeavyWeightProcess.info.uid != aInfo.applicationInfo.uid ||
    680                             !mService.mHeavyWeightProcess.processName.equals(aInfo.processName))) {
    681                         int realCallingUid = callingUid;
    682                         if (caller != null) {
    683                             ProcessRecord callerApp = mService.getRecordForAppLocked(caller);
    684                             if (callerApp != null) {
    685                                 realCallingUid = callerApp.info.uid;
    686                             } else {
    687                                 Slog.w(TAG, "Unable to find app for caller " + caller
    688                                       + " (pid=" + callingPid + ") when starting: "
    689                                       + intent.toString());
    690                                 ActivityOptions.abort(options);
    691                                 return ActivityManager.START_PERMISSION_DENIED;
    692                             }
    693                         }
    694 
    695                         IIntentSender target = mService.getIntentSenderLocked(
    696                                 ActivityManager.INTENT_SENDER_ACTIVITY, "android",
    697                                 realCallingUid, userId, null, null, 0, new Intent[] { intent },
    698                                 new String[] { resolvedType }, PendingIntent.FLAG_CANCEL_CURRENT
    699                                 | PendingIntent.FLAG_ONE_SHOT, null);
    700 
    701                         Intent newIntent = new Intent();
    702                         if (requestCode >= 0) {
    703                             // Caller is requesting a result.
    704                             newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_HAS_RESULT, true);
    705                         }
    706                         newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_INTENT,
    707                                 new IntentSender(target));
    708                         if (mService.mHeavyWeightProcess.activities.size() > 0) {
    709                             ActivityRecord hist = mService.mHeavyWeightProcess.activities.get(0);
    710                             newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_CUR_APP,
    711                                     hist.packageName);
    712                             newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_CUR_TASK,
    713                                     hist.task.taskId);
    714                         }
    715                         newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_NEW_APP,
    716                                 aInfo.packageName);
    717                         newIntent.setFlags(intent.getFlags());
    718                         newIntent.setClassName("android",
    719                                 HeavyWeightSwitcherActivity.class.getName());
    720                         intent = newIntent;
    721                         resolvedType = null;
    722                         caller = null;
    723                         callingUid = Binder.getCallingUid();
    724                         callingPid = Binder.getCallingPid();
    725                         componentSpecified = true;
    726                         try {
    727                             ResolveInfo rInfo =
    728                                 AppGlobals.getPackageManager().resolveIntent(
    729                                         intent, null,
    730                                         PackageManager.MATCH_DEFAULT_ONLY
    731                                         | ActivityManagerService.STOCK_PM_FLAGS, userId);
    732                             aInfo = rInfo != null ? rInfo.activityInfo : null;
    733                             aInfo = mService.getActivityInfoForUser(aInfo, userId);
    734                         } catch (RemoteException e) {
    735                             aInfo = null;
    736                         }
    737                     }
    738                 }
    739             }
    740 
    741             int res = startActivityLocked(caller, intent, resolvedType,
    742                     aInfo, resultTo, resultWho, requestCode, callingPid, callingUid,
    743                     callingPackage, startFlags, options, componentSpecified, null);
    744 
    745             if (stack.mConfigWillChange) {
    746                 // If the caller also wants to switch to a new configuration,
    747                 // do so now.  This allows a clean switch, as we are waiting
    748                 // for the current activity to pause (so we will not destroy
    749                 // it), and have not yet started the next activity.
    750                 mService.enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION,
    751                         "updateConfiguration()");
    752                 stack.mConfigWillChange = false;
    753                 if (DEBUG_CONFIGURATION) Slog.v(TAG,
    754                         "Updating to new configuration after starting activity.");
    755                 mService.updateConfigurationLocked(config, null, false, false);
    756             }
    757 
    758             Binder.restoreCallingIdentity(origId);
    759 
    760             if (outResult != null) {
    761                 outResult.result = res;
    762                 if (res == ActivityManager.START_SUCCESS) {
    763                     mWaitingActivityLaunched.add(outResult);
    764                     do {
    765                         try {
    766                             mService.wait();
    767                         } catch (InterruptedException e) {
    768                         }
    769                     } while (!outResult.timeout && outResult.who == null);
    770                 } else if (res == ActivityManager.START_TASK_TO_FRONT) {
    771                     ActivityRecord r = stack.topRunningActivityLocked(null);
    772                     if (r.nowVisible) {
    773                         outResult.timeout = false;
    774                         outResult.who = new ComponentName(r.info.packageName, r.info.name);
    775                         outResult.totalTime = 0;
    776                         outResult.thisTime = 0;
    777                     } else {
    778                         outResult.thisTime = SystemClock.uptimeMillis();
    779                         mWaitingActivityVisible.add(outResult);
    780                         do {
    781                             try {
    782                                 mService.wait();
    783                             } catch (InterruptedException e) {
    784                             }
    785                         } while (!outResult.timeout && outResult.who == null);
    786                     }
    787                 }
    788             }
    789 
    790             return res;
    791         }
    792     }
    793 
    794     final int startActivities(IApplicationThread caller, int callingUid, String callingPackage,
    795             Intent[] intents, String[] resolvedTypes, IBinder resultTo,
    796             Bundle options, int userId) {
    797         if (intents == null) {
    798             throw new NullPointerException("intents is null");
    799         }
    800         if (resolvedTypes == null) {
    801             throw new NullPointerException("resolvedTypes is null");
    802         }
    803         if (intents.length != resolvedTypes.length) {
    804             throw new IllegalArgumentException("intents are length different than resolvedTypes");
    805         }
    806 
    807 
    808         int callingPid;
    809         if (callingUid >= 0) {
    810             callingPid = -1;
    811         } else if (caller == null) {
    812             callingPid = Binder.getCallingPid();
    813             callingUid = Binder.getCallingUid();
    814         } else {
    815             callingPid = callingUid = -1;
    816         }
    817         final long origId = Binder.clearCallingIdentity();
    818         try {
    819             synchronized (mService) {
    820                 ActivityRecord[] outActivity = new ActivityRecord[1];
    821                 for (int i=0; i<intents.length; i++) {
    822                     Intent intent = intents[i];
    823                     if (intent == null) {
    824                         continue;
    825                     }
    826 
    827                     // Refuse possible leaked file descriptors
    828                     if (intent != null && intent.hasFileDescriptors()) {
    829                         throw new IllegalArgumentException("File descriptors passed in Intent");
    830                     }
    831 
    832                     boolean componentSpecified = intent.getComponent() != null;
    833 
    834                     // Don't modify the client's object!
    835                     intent = new Intent(intent);
    836 
    837                     // Collect information about the target of the Intent.
    838                     ActivityInfo aInfo = resolveActivity(intent, resolvedTypes[i],
    839                             0, null, null, userId);
    840                     // TODO: New, check if this is correct
    841                     aInfo = mService.getActivityInfoForUser(aInfo, userId);
    842 
    843                     if (aInfo != null &&
    844                             (aInfo.applicationInfo.flags & ApplicationInfo.FLAG_CANT_SAVE_STATE)
    845                                     != 0) {
    846                         throw new IllegalArgumentException(
    847                                 "FLAG_CANT_SAVE_STATE not supported here");
    848                     }
    849 
    850                     Bundle theseOptions;
    851                     if (options != null && i == intents.length-1) {
    852                         theseOptions = options;
    853                     } else {
    854                         theseOptions = null;
    855                     }
    856                     int res = startActivityLocked(caller, intent, resolvedTypes[i],
    857                             aInfo, resultTo, null, -1, callingPid, callingUid, callingPackage,
    858                             0, theseOptions, componentSpecified, outActivity);
    859                     if (res < 0) {
    860                         return res;
    861                     }
    862 
    863                     resultTo = outActivity[0] != null ? outActivity[0].appToken : null;
    864                 }
    865             }
    866         } finally {
    867             Binder.restoreCallingIdentity(origId);
    868         }
    869 
    870         return ActivityManager.START_SUCCESS;
    871     }
    872 
    873     final boolean realStartActivityLocked(ActivityRecord r,
    874             ProcessRecord app, boolean andResume, boolean checkConfig)
    875             throws RemoteException {
    876 
    877         r.startFreezingScreenLocked(app, 0);
    878         if (false) Slog.d(TAG, "realStartActivity: setting app visibility true");
    879         mWindowManager.setAppVisibility(r.appToken, true);
    880 
    881         // schedule launch ticks to collect information about slow apps.
    882         r.startLaunchTickingLocked();
    883 
    884         // Have the window manager re-evaluate the orientation of
    885         // the screen based on the new activity order.  Note that
    886         // as a result of this, it can call back into the activity
    887         // manager with a new orientation.  We don't care about that,
    888         // because the activity is not currently running so we are
    889         // just restarting it anyway.
    890         if (checkConfig) {
    891             Configuration config = mWindowManager.updateOrientationFromAppTokens(
    892                     mService.mConfiguration,
    893                     r.mayFreezeScreenLocked(app) ? r.appToken : null);
    894             mService.updateConfigurationLocked(config, r, false, false);
    895         }
    896 
    897         r.app = app;
    898         app.waitingToKill = null;
    899         r.launchCount++;
    900         r.lastLaunchTime = SystemClock.uptimeMillis();
    901 
    902         if (localLOGV) Slog.v(TAG, "Launching: " + r);
    903 
    904         int idx = app.activities.indexOf(r);
    905         if (idx < 0) {
    906             app.activities.add(r);
    907         }
    908         mService.updateLruProcessLocked(app, true, null);
    909         mService.updateOomAdjLocked();
    910 
    911         final ActivityStack stack = r.task.stack;
    912         try {
    913             if (app.thread == null) {
    914                 throw new RemoteException();
    915             }
    916             List<ResultInfo> results = null;
    917             List<Intent> newIntents = null;
    918             if (andResume) {
    919                 results = r.results;
    920                 newIntents = r.newIntents;
    921             }
    922             if (DEBUG_SWITCH) Slog.v(TAG, "Launching: " + r
    923                     + " icicle=" + r.icicle
    924                     + " with results=" + results + " newIntents=" + newIntents
    925                     + " andResume=" + andResume);
    926             if (andResume) {
    927                 EventLog.writeEvent(EventLogTags.AM_RESTART_ACTIVITY,
    928                         r.userId, System.identityHashCode(r),
    929                         r.task.taskId, r.shortComponentName);
    930             }
    931             if (r.isHomeActivity() && r.isNotResolverActivity()) {
    932                 // Home process is the root process of the task.
    933                 mService.mHomeProcess = r.task.mActivities.get(0).app;
    934             }
    935             mService.ensurePackageDexOpt(r.intent.getComponent().getPackageName());
    936             r.sleeping = false;
    937             r.forceNewConfig = false;
    938             mService.showAskCompatModeDialogLocked(r);
    939             r.compat = mService.compatibilityInfoForPackageLocked(r.info.applicationInfo);
    940             String profileFile = null;
    941             ParcelFileDescriptor profileFd = null;
    942             boolean profileAutoStop = false;
    943             if (mService.mProfileApp != null && mService.mProfileApp.equals(app.processName)) {
    944                 if (mService.mProfileProc == null || mService.mProfileProc == app) {
    945                     mService.mProfileProc = app;
    946                     profileFile = mService.mProfileFile;
    947                     profileFd = mService.mProfileFd;
    948                     profileAutoStop = mService.mAutoStopProfiler;
    949                 }
    950             }
    951             app.hasShownUi = true;
    952             app.pendingUiClean = true;
    953             if (profileFd != null) {
    954                 try {
    955                     profileFd = profileFd.dup();
    956                 } catch (IOException e) {
    957                     if (profileFd != null) {
    958                         try {
    959                             profileFd.close();
    960                         } catch (IOException o) {
    961                         }
    962                         profileFd = null;
    963                     }
    964                 }
    965             }
    966             app.forceProcessStateUpTo(ActivityManager.PROCESS_STATE_TOP);
    967             app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken,
    968                     System.identityHashCode(r), r.info,
    969                     new Configuration(mService.mConfiguration), r.compat,
    970                     app.repProcState, r.icicle, results, newIntents, !andResume,
    971                     mService.isNextTransitionForward(), profileFile, profileFd,
    972                     profileAutoStop);
    973 
    974             if ((app.info.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) {
    975                 // This may be a heavy-weight process!  Note that the package
    976                 // manager will ensure that only activity can run in the main
    977                 // process of the .apk, which is the only thing that will be
    978                 // considered heavy-weight.
    979                 if (app.processName.equals(app.info.packageName)) {
    980                     if (mService.mHeavyWeightProcess != null
    981                             && mService.mHeavyWeightProcess != app) {
    982                         Slog.w(TAG, "Starting new heavy weight process " + app
    983                                 + " when already running "
    984                                 + mService.mHeavyWeightProcess);
    985                     }
    986                     mService.mHeavyWeightProcess = app;
    987                     Message msg = mService.mHandler.obtainMessage(
    988                             ActivityManagerService.POST_HEAVY_NOTIFICATION_MSG);
    989                     msg.obj = r;
    990                     mService.mHandler.sendMessage(msg);
    991                 }
    992             }
    993 
    994         } catch (RemoteException e) {
    995             if (r.launchFailed) {
    996                 // This is the second time we failed -- finish activity
    997                 // and give up.
    998                 Slog.e(TAG, "Second failure launching "
    999                       + r.intent.getComponent().flattenToShortString()
   1000                       + ", giving up", e);
   1001                 mService.appDiedLocked(app, app.pid, app.thread);
   1002                 stack.requestFinishActivityLocked(r.appToken, Activity.RESULT_CANCELED, null,
   1003                         "2nd-crash", false);
   1004                 return false;
   1005             }
   1006 
   1007             // This is the first time we failed -- restart process and
   1008             // retry.
   1009             app.activities.remove(r);
   1010             throw e;
   1011         }
   1012 
   1013         r.launchFailed = false;
   1014         if (stack.updateLRUListLocked(r)) {
   1015             Slog.w(TAG, "Activity " + r
   1016                   + " being launched, but already in LRU list");
   1017         }
   1018 
   1019         if (andResume) {
   1020             // As part of the process of launching, ActivityThread also performs
   1021             // a resume.
   1022             stack.minimalResumeActivityLocked(r);
   1023         } else {
   1024             // This activity is not starting in the resumed state... which
   1025             // should look like we asked it to pause+stop (but remain visible),
   1026             // and it has done so and reported back the current icicle and
   1027             // other state.
   1028             if (DEBUG_STATES) Slog.v(TAG, "Moving to STOPPED: " + r
   1029                     + " (starting in stopped state)");
   1030             r.state = ActivityState.STOPPED;
   1031             r.stopped = true;
   1032         }
   1033 
   1034         // Launch the new version setup screen if needed.  We do this -after-
   1035         // launching the initial activity (that is, home), so that it can have
   1036         // a chance to initialize itself while in the background, making the
   1037         // switch back to it faster and look better.
   1038         if (isFrontStack(stack)) {
   1039             mService.startSetupActivityLocked();
   1040         }
   1041 
   1042         return true;
   1043     }
   1044 
   1045     void startSpecificActivityLocked(ActivityRecord r,
   1046             boolean andResume, boolean checkConfig) {
   1047         // Is this activity's application already running?
   1048         ProcessRecord app = mService.getProcessRecordLocked(r.processName,
   1049                 r.info.applicationInfo.uid, true);
   1050 
   1051         r.task.stack.setLaunchTime(r);
   1052 
   1053         if (app != null && app.thread != null) {
   1054             try {
   1055                 if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0
   1056                         || !"android".equals(r.info.packageName)) {
   1057                     // Don't add this if it is a platform component that is marked
   1058                     // to run in multiple processes, because this is actually
   1059                     // part of the framework so doesn't make sense to track as a
   1060                     // separate apk in the process.
   1061                     app.addPackage(r.info.packageName, mService.mProcessStats);
   1062                 }
   1063                 realStartActivityLocked(r, app, andResume, checkConfig);
   1064                 return;
   1065             } catch (RemoteException e) {
   1066                 Slog.w(TAG, "Exception when starting activity "
   1067                         + r.intent.getComponent().flattenToShortString(), e);
   1068             }
   1069 
   1070             // If a dead object exception was thrown -- fall through to
   1071             // restart the application.
   1072         }
   1073 
   1074         mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
   1075                 "activity", r.intent.getComponent(), false, false, true);
   1076     }
   1077 
   1078     final int startActivityLocked(IApplicationThread caller,
   1079             Intent intent, String resolvedType, ActivityInfo aInfo, IBinder resultTo,
   1080             String resultWho, int requestCode,
   1081             int callingPid, int callingUid, String callingPackage, int startFlags, Bundle options,
   1082             boolean componentSpecified, ActivityRecord[] outActivity) {
   1083         int err = ActivityManager.START_SUCCESS;
   1084 
   1085         ProcessRecord callerApp = null;
   1086         if (caller != null) {
   1087             callerApp = mService.getRecordForAppLocked(caller);
   1088             if (callerApp != null) {
   1089                 callingPid = callerApp.pid;
   1090                 callingUid = callerApp.info.uid;
   1091             } else {
   1092                 Slog.w(TAG, "Unable to find app for caller " + caller
   1093                       + " (pid=" + callingPid + ") when starting: "
   1094                       + intent.toString());
   1095                 err = ActivityManager.START_PERMISSION_DENIED;
   1096             }
   1097         }
   1098 
   1099         if (err == ActivityManager.START_SUCCESS) {
   1100             final int userId = aInfo != null ? UserHandle.getUserId(aInfo.applicationInfo.uid) : 0;
   1101             Slog.i(TAG, "START u" + userId + " {" + intent.toShortString(true, true, true, false)
   1102                     + "} from pid " + (callerApp != null ? callerApp.pid : callingPid));
   1103         }
   1104 
   1105         ActivityRecord sourceRecord = null;
   1106         ActivityRecord resultRecord = null;
   1107         if (resultTo != null) {
   1108             sourceRecord = isInAnyStackLocked(resultTo);
   1109             if (DEBUG_RESULTS) Slog.v(
   1110                 TAG, "Will send result to " + resultTo + " " + sourceRecord);
   1111             if (sourceRecord != null) {
   1112                 if (requestCode >= 0 && !sourceRecord.finishing) {
   1113                     resultRecord = sourceRecord;
   1114                 }
   1115             }
   1116         }
   1117         ActivityStack resultStack = resultRecord == null ? null : resultRecord.task.stack;
   1118 
   1119         int launchFlags = intent.getFlags();
   1120 
   1121         if ((launchFlags&Intent.FLAG_ACTIVITY_FORWARD_RESULT) != 0
   1122                 && sourceRecord != null) {
   1123             // Transfer the result target from the source activity to the new
   1124             // one being started, including any failures.
   1125             if (requestCode >= 0) {
   1126                 ActivityOptions.abort(options);
   1127                 return ActivityManager.START_FORWARD_AND_REQUEST_CONFLICT;
   1128             }
   1129             resultRecord = sourceRecord.resultTo;
   1130             resultWho = sourceRecord.resultWho;
   1131             requestCode = sourceRecord.requestCode;
   1132             sourceRecord.resultTo = null;
   1133             if (resultRecord != null) {
   1134                 resultRecord.removeResultsLocked(
   1135                     sourceRecord, resultWho, requestCode);
   1136             }
   1137         }
   1138 
   1139         if (err == ActivityManager.START_SUCCESS && intent.getComponent() == null) {
   1140             // We couldn't find a class that can handle the given Intent.
   1141             // That's the end of that!
   1142             err = ActivityManager.START_INTENT_NOT_RESOLVED;
   1143         }
   1144 
   1145         if (err == ActivityManager.START_SUCCESS && aInfo == null) {
   1146             // We couldn't find the specific class specified in the Intent.
   1147             // Also the end of the line.
   1148             err = ActivityManager.START_CLASS_NOT_FOUND;
   1149         }
   1150 
   1151         if (err != ActivityManager.START_SUCCESS) {
   1152             if (resultRecord != null) {
   1153                 resultStack.sendActivityResultLocked(-1,
   1154                     resultRecord, resultWho, requestCode,
   1155                     Activity.RESULT_CANCELED, null);
   1156             }
   1157             setDismissKeyguard(false);
   1158             ActivityOptions.abort(options);
   1159             return err;
   1160         }
   1161 
   1162         final int startAnyPerm = mService.checkPermission(
   1163                 START_ANY_ACTIVITY, callingPid, callingUid);
   1164         final int componentPerm = mService.checkComponentPermission(aInfo.permission, callingPid,
   1165                 callingUid, aInfo.applicationInfo.uid, aInfo.exported);
   1166         if (startAnyPerm != PERMISSION_GRANTED && componentPerm != PERMISSION_GRANTED) {
   1167             if (resultRecord != null) {
   1168                 resultStack.sendActivityResultLocked(-1,
   1169                     resultRecord, resultWho, requestCode,
   1170                     Activity.RESULT_CANCELED, null);
   1171             }
   1172             setDismissKeyguard(false);
   1173             String msg;
   1174             if (!aInfo.exported) {
   1175                 msg = "Permission Denial: starting " + intent.toString()
   1176                         + " from " + callerApp + " (pid=" + callingPid
   1177                         + ", uid=" + callingUid + ")"
   1178                         + " not exported from uid " + aInfo.applicationInfo.uid;
   1179             } else {
   1180                 msg = "Permission Denial: starting " + intent.toString()
   1181                         + " from " + callerApp + " (pid=" + callingPid
   1182                         + ", uid=" + callingUid + ")"
   1183                         + " requires " + aInfo.permission;
   1184             }
   1185             Slog.w(TAG, msg);
   1186             throw new SecurityException(msg);
   1187         }
   1188 
   1189         boolean abort = !mService.mIntentFirewall.checkStartActivity(intent, callingUid,
   1190                 callingPid, resolvedType, aInfo.applicationInfo);
   1191 
   1192         if (mService.mController != null) {
   1193             try {
   1194                 // The Intent we give to the watcher has the extra data
   1195                 // stripped off, since it can contain private information.
   1196                 Intent watchIntent = intent.cloneFilter();
   1197                 abort |= !mService.mController.activityStarting(watchIntent,
   1198                         aInfo.applicationInfo.packageName);
   1199             } catch (RemoteException e) {
   1200                 mService.mController = null;
   1201             }
   1202         }
   1203 
   1204         if (abort) {
   1205             if (resultRecord != null) {
   1206                 resultStack.sendActivityResultLocked(-1, resultRecord, resultWho, requestCode,
   1207                         Activity.RESULT_CANCELED, null);
   1208             }
   1209             // We pretend to the caller that it was really started, but
   1210             // they will just get a cancel result.
   1211             setDismissKeyguard(false);
   1212             ActivityOptions.abort(options);
   1213             return ActivityManager.START_SUCCESS;
   1214         }
   1215 
   1216         ActivityRecord r = new ActivityRecord(mService, callerApp, callingUid, callingPackage,
   1217                 intent, resolvedType, aInfo, mService.mConfiguration,
   1218                 resultRecord, resultWho, requestCode, componentSpecified, this);
   1219         if (outActivity != null) {
   1220             outActivity[0] = r;
   1221         }
   1222 
   1223         final ActivityStack stack = getFocusedStack();
   1224         if (stack.mResumedActivity == null
   1225                 || stack.mResumedActivity.info.applicationInfo.uid != callingUid) {
   1226             if (!mService.checkAppSwitchAllowedLocked(callingPid, callingUid, "Activity start")) {
   1227                 PendingActivityLaunch pal =
   1228                         new PendingActivityLaunch(r, sourceRecord, startFlags, stack);
   1229                 mService.mPendingActivityLaunches.add(pal);
   1230                 setDismissKeyguard(false);
   1231                 ActivityOptions.abort(options);
   1232                 return ActivityManager.START_SWITCHES_CANCELED;
   1233             }
   1234         }
   1235 
   1236         if (mService.mDidAppSwitch) {
   1237             // This is the second allowed switch since we stopped switches,
   1238             // so now just generally allow switches.  Use case: user presses
   1239             // home (switches disabled, switch to home, mDidAppSwitch now true);
   1240             // user taps a home icon (coming from home so allowed, we hit here
   1241             // and now allow anyone to switch again).
   1242             mService.mAppSwitchesAllowedTime = 0;
   1243         } else {
   1244             mService.mDidAppSwitch = true;
   1245         }
   1246 
   1247         mService.doPendingActivityLaunchesLocked(false);
   1248 
   1249         err = startActivityUncheckedLocked(r, sourceRecord, startFlags, true, options);
   1250 
   1251         if (allPausedActivitiesComplete()) {
   1252             // If someone asked to have the keyguard dismissed on the next
   1253             // activity start, but we are not actually doing an activity
   1254             // switch...  just dismiss the keyguard now, because we
   1255             // probably want to see whatever is behind it.
   1256             dismissKeyguard();
   1257         }
   1258         return err;
   1259     }
   1260 
   1261     ActivityStack adjustStackFocus(ActivityRecord r) {
   1262         final TaskRecord task = r.task;
   1263         if (r.isApplicationActivity() || (task != null && task.isApplicationTask())) {
   1264             if (task != null) {
   1265                 final ActivityStack taskStack = task.stack;
   1266                 if (mFocusedStack != taskStack) {
   1267                     if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG,
   1268                             "adjustStackFocus: Setting focused stack to r=" + r + " task=" + task);
   1269                     mFocusedStack = taskStack.isHomeStack() ? null : taskStack;
   1270                 } else {
   1271                     if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG,
   1272                         "adjustStackFocus: Focused stack already=" + mFocusedStack);
   1273                 }
   1274                 return taskStack;
   1275             }
   1276 
   1277             if (mFocusedStack != null) {
   1278                 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG,
   1279                         "adjustStackFocus: Have a focused stack=" + mFocusedStack);
   1280                 return mFocusedStack;
   1281             }
   1282 
   1283             for (int stackNdx = mStacks.size() - 1; stackNdx > 0; --stackNdx) {
   1284                 ActivityStack stack = mStacks.get(stackNdx);
   1285                 if (!stack.isHomeStack()) {
   1286                     if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG,
   1287                             "adjustStackFocus: Setting focused stack=" + stack);
   1288                     mFocusedStack = stack;
   1289                     return mFocusedStack;
   1290                 }
   1291             }
   1292 
   1293             // Time to create the first app stack for this user.
   1294             int stackId =
   1295                     mService.createStack(-1, HOME_STACK_ID, StackBox.TASK_STACK_GOES_OVER, 1.0f);
   1296             if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, "adjustStackFocus: New stack r=" + r +
   1297                     " stackId=" + stackId);
   1298             mFocusedStack = getStack(stackId);
   1299             return mFocusedStack;
   1300         }
   1301         return mHomeStack;
   1302     }
   1303 
   1304     void setFocusedStack(ActivityRecord r) {
   1305         if (r == null) {
   1306             return;
   1307         }
   1308         if (!r.isApplicationActivity() || (r.task != null && !r.task.isApplicationTask())) {
   1309             if (mStackState != STACK_STATE_HOME_IN_FRONT) {
   1310                 if (DEBUG_STACK || DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: mStackState old=" +
   1311                         stackStateToString(mStackState) + " new=" +
   1312                         stackStateToString(STACK_STATE_HOME_TO_FRONT) +
   1313                         " Callers=" + Debug.getCallers(3));
   1314                 mStackState = STACK_STATE_HOME_TO_FRONT;
   1315             }
   1316         } else {
   1317             if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG,
   1318                     "setFocusedStack: Setting focused stack to r=" + r + " task=" + r.task +
   1319                     " Callers=" + Debug.getCallers(3));
   1320             final ActivityStack taskStack = r.task.stack;
   1321             mFocusedStack = taskStack.isHomeStack() ? null : taskStack;
   1322             if (mStackState != STACK_STATE_HOME_IN_BACK) {
   1323                 if (DEBUG_STACK) Slog.d(TAG, "setFocusedStack: mStackState old=" +
   1324                         stackStateToString(mStackState) + " new=" +
   1325                         stackStateToString(STACK_STATE_HOME_TO_BACK) +
   1326                         " Callers=" + Debug.getCallers(3));
   1327                 mStackState = STACK_STATE_HOME_TO_BACK;
   1328             }
   1329         }
   1330     }
   1331 
   1332     final int startActivityUncheckedLocked(ActivityRecord r,
   1333             ActivityRecord sourceRecord, int startFlags, boolean doResume,
   1334             Bundle options) {
   1335         final Intent intent = r.intent;
   1336         final int callingUid = r.launchedFromUid;
   1337 
   1338         int launchFlags = intent.getFlags();
   1339 
   1340         // We'll invoke onUserLeaving before onPause only if the launching
   1341         // activity did not explicitly state that this is an automated launch.
   1342         mUserLeaving = (launchFlags&Intent.FLAG_ACTIVITY_NO_USER_ACTION) == 0;
   1343         if (DEBUG_USER_LEAVING) Slog.v(TAG, "startActivity() => mUserLeaving=" + mUserLeaving);
   1344 
   1345         // If the caller has asked not to resume at this point, we make note
   1346         // of this in the record so that we can skip it when trying to find
   1347         // the top running activity.
   1348         if (!doResume) {
   1349             r.delayedResume = true;
   1350         }
   1351 
   1352         ActivityRecord notTop = (launchFlags&Intent.FLAG_ACTIVITY_PREVIOUS_IS_TOP) != 0 ? r : null;
   1353 
   1354         // If the onlyIfNeeded flag is set, then we can do this if the activity
   1355         // being launched is the same as the one making the call...  or, as
   1356         // a special case, if we do not know the caller then we count the
   1357         // current top activity as the caller.
   1358         if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) {
   1359             ActivityRecord checkedCaller = sourceRecord;
   1360             if (checkedCaller == null) {
   1361                 checkedCaller = getFocusedStack().topRunningNonDelayedActivityLocked(notTop);
   1362             }
   1363             if (!checkedCaller.realActivity.equals(r.realActivity)) {
   1364                 // Caller is not the same as launcher, so always needed.
   1365                 startFlags &= ~ActivityManager.START_FLAG_ONLY_IF_NEEDED;
   1366             }
   1367         }
   1368 
   1369         if (sourceRecord == null) {
   1370             // This activity is not being started from another...  in this
   1371             // case we -always- start a new task.
   1372             if ((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) {
   1373                 Slog.w(TAG, "startActivity called from non-Activity context; forcing " +
   1374                         "Intent.FLAG_ACTIVITY_NEW_TASK for: " + intent);
   1375                 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK;
   1376             }
   1377         } else if (sourceRecord.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) {
   1378             // The original activity who is starting us is running as a single
   1379             // instance...  this new activity it is starting must go on its
   1380             // own task.
   1381             launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK;
   1382         } else if (r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE
   1383                 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK) {
   1384             // The activity being started is a single instance...  it always
   1385             // gets launched into its own task.
   1386             launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK;
   1387         }
   1388 
   1389         ActivityInfo newTaskInfo = null;
   1390         Intent newTaskIntent = null;
   1391         final ActivityStack sourceStack;
   1392         if (sourceRecord != null) {
   1393             if (sourceRecord.finishing) {
   1394                 // If the source is finishing, we can't further count it as our source.  This
   1395                 // is because the task it is associated with may now be empty and on its way out,
   1396                 // so we don't want to blindly throw it in to that task.  Instead we will take
   1397                 // the NEW_TASK flow and try to find a task for it. But save the task information
   1398                 // so it can be used when creating the new task.
   1399                 if ((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) {
   1400                     Slog.w(TAG, "startActivity called from finishing " + sourceRecord
   1401                             + "; forcing " + "Intent.FLAG_ACTIVITY_NEW_TASK for: " + intent);
   1402                     launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK;
   1403                     newTaskInfo = sourceRecord.info;
   1404                     newTaskIntent = sourceRecord.task.intent;
   1405                 }
   1406                 sourceRecord = null;
   1407                 sourceStack = null;
   1408             } else {
   1409                 sourceStack = sourceRecord.task.stack;
   1410             }
   1411         } else {
   1412             sourceStack = null;
   1413         }
   1414 
   1415         if (r.resultTo != null && (launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
   1416             // For whatever reason this activity is being launched into a new
   1417             // task...  yet the caller has requested a result back.  Well, that
   1418             // is pretty messed up, so instead immediately send back a cancel
   1419             // and let the new task continue launched as normal without a
   1420             // dependency on its originator.
   1421             Slog.w(TAG, "Activity is launching as a new task, so cancelling activity result.");
   1422             r.resultTo.task.stack.sendActivityResultLocked(-1,
   1423                     r.resultTo, r.resultWho, r.requestCode,
   1424                 Activity.RESULT_CANCELED, null);
   1425             r.resultTo = null;
   1426         }
   1427 
   1428         boolean addingToTask = false;
   1429         boolean movedHome = false;
   1430         TaskRecord reuseTask = null;
   1431         ActivityStack targetStack;
   1432         if (((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0 &&
   1433                 (launchFlags&Intent.FLAG_ACTIVITY_MULTIPLE_TASK) == 0)
   1434                 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK
   1435                 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) {
   1436             // If bring to front is requested, and no result is requested, and
   1437             // we can find a task that was started with this same
   1438             // component, then instead of launching bring that one to the front.
   1439             if (r.resultTo == null) {
   1440                 // See if there is a task to bring to the front.  If this is
   1441                 // a SINGLE_INSTANCE activity, there can be one and only one
   1442                 // instance of it in the history, and it is always in its own
   1443                 // unique task, so we do a special search.
   1444                 ActivityRecord intentActivity = r.launchMode != ActivityInfo.LAUNCH_SINGLE_INSTANCE
   1445                         ? findTaskLocked(r)
   1446                         : findActivityLocked(intent, r.info);
   1447                 if (intentActivity != null) {
   1448                     if (r.task == null) {
   1449                         r.task = intentActivity.task;
   1450                     }
   1451                     targetStack = intentActivity.task.stack;
   1452                     targetStack.mLastPausedActivity = null;
   1453                     if (DEBUG_TASKS) Slog.d(TAG, "Bring to front target: " + targetStack
   1454                             + " from " + intentActivity);
   1455                     moveHomeStack(targetStack.isHomeStack());
   1456                     if (intentActivity.task.intent == null) {
   1457                         // This task was started because of movement of
   1458                         // the activity based on affinity...  now that we
   1459                         // are actually launching it, we can assign the
   1460                         // base intent.
   1461                         intentActivity.task.setIntent(intent, r.info);
   1462                     }
   1463                     // If the target task is not in the front, then we need
   1464                     // to bring it to the front...  except...  well, with
   1465                     // SINGLE_TASK_LAUNCH it's not entirely clear.  We'd like
   1466                     // to have the same behavior as if a new instance was
   1467                     // being started, which means not bringing it to the front
   1468                     // if the caller is not itself in the front.
   1469                     final ActivityStack lastStack = getLastStack();
   1470                     ActivityRecord curTop = lastStack == null?
   1471                             null : lastStack.topRunningNonDelayedActivityLocked(notTop);
   1472                     if (curTop != null && (curTop.task != intentActivity.task ||
   1473                             curTop.task != lastStack.topTask())) {
   1474                         r.intent.addFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT);
   1475                         if (sourceRecord == null || (sourceStack.topActivity() != null &&
   1476                                 sourceStack.topActivity().task == sourceRecord.task)) {
   1477                             // We really do want to push this one into the
   1478                             // user's face, right now.
   1479                             movedHome = true;
   1480                             targetStack.moveTaskToFrontLocked(intentActivity.task, r, options);
   1481                             if ((launchFlags &
   1482                                     (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME))
   1483                                     == (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME)) {
   1484                                 // Caller wants to appear on home activity.
   1485                                 intentActivity.task.mOnTopOfHome = true;
   1486                             }
   1487                             options = null;
   1488                         }
   1489                     }
   1490                     // If the caller has requested that the target task be
   1491                     // reset, then do so.
   1492                     if ((launchFlags&Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) != 0) {
   1493                         intentActivity = targetStack.resetTaskIfNeededLocked(intentActivity, r);
   1494                     }
   1495                     if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) {
   1496                         // We don't need to start a new activity, and
   1497                         // the client said not to do anything if that
   1498                         // is the case, so this is it!  And for paranoia, make
   1499                         // sure we have correctly resumed the top activity.
   1500                         if (doResume) {
   1501                             resumeTopActivitiesLocked(targetStack, null, options);
   1502                         } else {
   1503                             ActivityOptions.abort(options);
   1504                         }
   1505                         if (r.task == null)  Slog.v(TAG,
   1506                                 "startActivityUncheckedLocked: task left null",
   1507                                 new RuntimeException("here").fillInStackTrace());
   1508                         return ActivityManager.START_RETURN_INTENT_TO_CALLER;
   1509                     }
   1510                     if ((launchFlags &
   1511                             (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK))
   1512                             == (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK)) {
   1513                         // The caller has requested to completely replace any
   1514                         // existing task with its new activity.  Well that should
   1515                         // not be too hard...
   1516                         reuseTask = intentActivity.task;
   1517                         reuseTask.performClearTaskLocked();
   1518                         reuseTask.setIntent(r.intent, r.info);
   1519                     } else if ((launchFlags&Intent.FLAG_ACTIVITY_CLEAR_TOP) != 0
   1520                             || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK
   1521                             || r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) {
   1522                         // In this situation we want to remove all activities
   1523                         // from the task up to the one being started.  In most
   1524                         // cases this means we are resetting the task to its
   1525                         // initial state.
   1526                         ActivityRecord top =
   1527                                 intentActivity.task.performClearTaskLocked(r, launchFlags);
   1528                         if (top != null) {
   1529                             if (top.frontOfTask) {
   1530                                 // Activity aliases may mean we use different
   1531                                 // intents for the top activity, so make sure
   1532                                 // the task now has the identity of the new
   1533                                 // intent.
   1534                                 top.task.setIntent(r.intent, r.info);
   1535                             }
   1536                             ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT,
   1537                                     r, top.task);
   1538                             top.deliverNewIntentLocked(callingUid, r.intent);
   1539                         } else {
   1540                             // A special case: we need to
   1541                             // start the activity because it is not currently
   1542                             // running, and the caller has asked to clear the
   1543                             // current task to have this activity at the top.
   1544                             addingToTask = true;
   1545                             // Now pretend like this activity is being started
   1546                             // by the top of its task, so it is put in the
   1547                             // right place.
   1548                             sourceRecord = intentActivity;
   1549                         }
   1550                     } else if (r.realActivity.equals(intentActivity.task.realActivity)) {
   1551                         // In this case the top activity on the task is the
   1552                         // same as the one being launched, so we take that
   1553                         // as a request to bring the task to the foreground.
   1554                         // If the top activity in the task is the root
   1555                         // activity, deliver this new intent to it if it
   1556                         // desires.
   1557                         if (((launchFlags&Intent.FLAG_ACTIVITY_SINGLE_TOP) != 0
   1558                                 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP)
   1559                                 && intentActivity.realActivity.equals(r.realActivity)) {
   1560                             ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r,
   1561                                     intentActivity.task);
   1562                             if (intentActivity.frontOfTask) {
   1563                                 intentActivity.task.setIntent(r.intent, r.info);
   1564                             }
   1565                             intentActivity.deliverNewIntentLocked(callingUid, r.intent);
   1566                         } else if (!r.intent.filterEquals(intentActivity.task.intent)) {
   1567                             // In this case we are launching the root activity
   1568                             // of the task, but with a different intent.  We
   1569                             // should start a new instance on top.
   1570                             addingToTask = true;
   1571                             sourceRecord = intentActivity;
   1572                         }
   1573                     } else if ((launchFlags&Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) == 0) {
   1574                         // In this case an activity is being launched in to an
   1575                         // existing task, without resetting that task.  This
   1576                         // is typically the situation of launching an activity
   1577                         // from a notification or shortcut.  We want to place
   1578                         // the new activity on top of the current task.
   1579                         addingToTask = true;
   1580                         sourceRecord = intentActivity;
   1581                     } else if (!intentActivity.task.rootWasReset) {
   1582                         // In this case we are launching in to an existing task
   1583                         // that has not yet been started from its front door.
   1584                         // The current task has been brought to the front.
   1585                         // Ideally, we'd probably like to place this new task
   1586                         // at the bottom of its stack, but that's a little hard
   1587                         // to do with the current organization of the code so
   1588                         // for now we'll just drop it.
   1589                         intentActivity.task.setIntent(r.intent, r.info);
   1590                     }
   1591                     if (!addingToTask && reuseTask == null) {
   1592                         // We didn't do anything...  but it was needed (a.k.a., client
   1593                         // don't use that intent!)  And for paranoia, make
   1594                         // sure we have correctly resumed the top activity.
   1595                         if (doResume) {
   1596                             targetStack.resumeTopActivityLocked(null, options);
   1597                         } else {
   1598                             ActivityOptions.abort(options);
   1599                         }
   1600                         if (r.task == null)  Slog.v(TAG,
   1601                             "startActivityUncheckedLocked: task left null",
   1602                             new RuntimeException("here").fillInStackTrace());
   1603                         return ActivityManager.START_TASK_TO_FRONT;
   1604                     }
   1605                 }
   1606             }
   1607         }
   1608 
   1609         //String uri = r.intent.toURI();
   1610         //Intent intent2 = new Intent(uri);
   1611         //Slog.i(TAG, "Given intent: " + r.intent);
   1612         //Slog.i(TAG, "URI is: " + uri);
   1613         //Slog.i(TAG, "To intent: " + intent2);
   1614 
   1615         if (r.packageName != null) {
   1616             // If the activity being launched is the same as the one currently
   1617             // at the top, then we need to check if it should only be launched
   1618             // once.
   1619             ActivityStack topStack = getFocusedStack();
   1620             ActivityRecord top = topStack.topRunningNonDelayedActivityLocked(notTop);
   1621             if (top != null && r.resultTo == null) {
   1622                 if (top.realActivity.equals(r.realActivity) && top.userId == r.userId) {
   1623                     if (top.app != null && top.app.thread != null) {
   1624                         if ((launchFlags&Intent.FLAG_ACTIVITY_SINGLE_TOP) != 0
   1625                             || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP
   1626                             || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK) {
   1627                             ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, top,
   1628                                     top.task);
   1629                             // For paranoia, make sure we have correctly
   1630                             // resumed the top activity.
   1631                             topStack.mLastPausedActivity = null;
   1632                             if (doResume) {
   1633                                 resumeTopActivitiesLocked();
   1634                             }
   1635                             ActivityOptions.abort(options);
   1636                             if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) {
   1637                                 // We don't need to start a new activity, and
   1638                                 // the client said not to do anything if that
   1639                                 // is the case, so this is it!
   1640                                 if (r.task == null)  Slog.v(TAG,
   1641                                     "startActivityUncheckedLocked: task left null",
   1642                                     new RuntimeException("here").fillInStackTrace());
   1643                                 return ActivityManager.START_RETURN_INTENT_TO_CALLER;
   1644                             }
   1645                             top.deliverNewIntentLocked(callingUid, r.intent);
   1646                             if (r.task == null)  Slog.v(TAG,
   1647                                 "startActivityUncheckedLocked: task left null",
   1648                                 new RuntimeException("here").fillInStackTrace());
   1649                             return ActivityManager.START_DELIVERED_TO_TOP;
   1650                         }
   1651                     }
   1652                 }
   1653             }
   1654 
   1655         } else {
   1656             if (r.resultTo != null) {
   1657                 r.resultTo.task.stack.sendActivityResultLocked(-1, r.resultTo, r.resultWho,
   1658                         r.requestCode, Activity.RESULT_CANCELED, null);
   1659             }
   1660             ActivityOptions.abort(options);
   1661             if (r.task == null)  Slog.v(TAG,
   1662                 "startActivityUncheckedLocked: task left null",
   1663                 new RuntimeException("here").fillInStackTrace());
   1664             return ActivityManager.START_CLASS_NOT_FOUND;
   1665         }
   1666 
   1667         boolean newTask = false;
   1668         boolean keepCurTransition = false;
   1669 
   1670         // Should this be considered a new task?
   1671         if (r.resultTo == null && !addingToTask
   1672                 && (launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
   1673             targetStack = adjustStackFocus(r);
   1674             moveHomeStack(targetStack.isHomeStack());
   1675             if (reuseTask == null) {
   1676                 r.setTask(targetStack.createTaskRecord(getNextTaskId(),
   1677                         newTaskInfo != null ? newTaskInfo : r.info,
   1678                         newTaskIntent != null ? newTaskIntent : intent,
   1679                         true), null, true);
   1680                 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r + " in new task " +
   1681                         r.task);
   1682             } else {
   1683                 r.setTask(reuseTask, reuseTask, true);
   1684             }
   1685             newTask = true;
   1686             if (!movedHome) {
   1687                 if ((launchFlags &
   1688                         (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_TASK_ON_HOME))
   1689                         == (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_TASK_ON_HOME)) {
   1690                     // Caller wants to appear on home activity, so before starting
   1691                     // their own activity we will bring home to the front.
   1692                     r.task.mOnTopOfHome = true;
   1693                 }
   1694             }
   1695         } else if (sourceRecord != null) {
   1696             TaskRecord sourceTask = sourceRecord.task;
   1697             targetStack = sourceTask.stack;
   1698             moveHomeStack(targetStack.isHomeStack());
   1699             if (!addingToTask &&
   1700                     (launchFlags&Intent.FLAG_ACTIVITY_CLEAR_TOP) != 0) {
   1701                 // In this case, we are adding the activity to an existing
   1702                 // task, but the caller has asked to clear that task if the
   1703                 // activity is already running.
   1704                 ActivityRecord top = sourceTask.performClearTaskLocked(r, launchFlags);
   1705                 keepCurTransition = true;
   1706                 if (top != null) {
   1707                     ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, top.task);
   1708                     top.deliverNewIntentLocked(callingUid, r.intent);
   1709                     // For paranoia, make sure we have correctly
   1710                     // resumed the top activity.
   1711                     targetStack.mLastPausedActivity = null;
   1712                     if (doResume) {
   1713                         targetStack.resumeTopActivityLocked(null);
   1714                     }
   1715                     ActivityOptions.abort(options);
   1716                     if (r.task == null)  Slog.w(TAG,
   1717                         "startActivityUncheckedLocked: task left null",
   1718                         new RuntimeException("here").fillInStackTrace());
   1719                     return ActivityManager.START_DELIVERED_TO_TOP;
   1720                 }
   1721             } else if (!addingToTask &&
   1722                     (launchFlags&Intent.FLAG_ACTIVITY_REORDER_TO_FRONT) != 0) {
   1723                 // In this case, we are launching an activity in our own task
   1724                 // that may already be running somewhere in the history, and
   1725                 // we want to shuffle it to the front of the stack if so.
   1726                 final ActivityRecord top = sourceTask.findActivityInHistoryLocked(r);
   1727                 if (top != null) {
   1728                     final TaskRecord task = top.task;
   1729                     task.moveActivityToFrontLocked(top);
   1730                     ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, task);
   1731                     top.updateOptionsLocked(options);
   1732                     top.deliverNewIntentLocked(callingUid, r.intent);
   1733                     targetStack.mLastPausedActivity = null;
   1734                     if (doResume) {
   1735                         targetStack.resumeTopActivityLocked(null);
   1736                     }
   1737                     return ActivityManager.START_DELIVERED_TO_TOP;
   1738                 }
   1739             }
   1740             // An existing activity is starting this new activity, so we want
   1741             // to keep the new one in the same task as the one that is starting
   1742             // it.
   1743             r.setTask(sourceTask, sourceRecord.thumbHolder, false);
   1744             if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r
   1745                     + " in existing task " + r.task + " from source " + sourceRecord);
   1746 
   1747         } else {
   1748             // This not being started from an existing activity, and not part
   1749             // of a new task...  just put it in the top task, though these days
   1750             // this case should never happen.
   1751             targetStack = adjustStackFocus(r);
   1752             moveHomeStack(targetStack.isHomeStack());
   1753             ActivityRecord prev = targetStack.topActivity();
   1754             r.setTask(prev != null ? prev.task
   1755                     : targetStack.createTaskRecord(getNextTaskId(), r.info, intent, true),
   1756                     null, true);
   1757             if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r
   1758                     + " in new guessed " + r.task);
   1759         }
   1760 
   1761         mService.grantUriPermissionFromIntentLocked(callingUid, r.packageName,
   1762                 intent, r.getUriPermissionsLocked());
   1763 
   1764         if (newTask) {
   1765             EventLog.writeEvent(EventLogTags.AM_CREATE_TASK, r.userId, r.task.taskId);
   1766         }
   1767         ActivityStack.logStartActivity(EventLogTags.AM_CREATE_ACTIVITY, r, r.task);
   1768         targetStack.mLastPausedActivity = null;
   1769         targetStack.startActivityLocked(r, newTask, doResume, keepCurTransition, options);
   1770         mService.setFocusedActivityLocked(r);
   1771         return ActivityManager.START_SUCCESS;
   1772     }
   1773 
   1774     void acquireLaunchWakelock() {
   1775         if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) {
   1776             throw new IllegalStateException("Calling must be system uid");
   1777         }
   1778         mLaunchingActivity.acquire();
   1779         if (!mHandler.hasMessages(LAUNCH_TIMEOUT_MSG)) {
   1780             // To be safe, don't allow the wake lock to be held for too long.
   1781             mHandler.sendEmptyMessageDelayed(LAUNCH_TIMEOUT_MSG, LAUNCH_TIMEOUT);
   1782         }
   1783     }
   1784 
   1785     // Checked.
   1786     final ActivityRecord activityIdleInternalLocked(final IBinder token, boolean fromTimeout,
   1787             Configuration config) {
   1788         if (localLOGV) Slog.v(TAG, "Activity idle: " + token);
   1789 
   1790         ArrayList<ActivityRecord> stops = null;
   1791         ArrayList<ActivityRecord> finishes = null;
   1792         ArrayList<UserStartedState> startingUsers = null;
   1793         int NS = 0;
   1794         int NF = 0;
   1795         IApplicationThread sendThumbnail = null;
   1796         boolean booting = false;
   1797         boolean enableScreen = false;
   1798         boolean activityRemoved = false;
   1799 
   1800         ActivityRecord r = ActivityRecord.forToken(token);
   1801         if (r != null) {
   1802             if (DEBUG_IDLE) Slog.d(TAG, "activityIdleInternalLocked: Callers=" +
   1803                     Debug.getCallers(4));
   1804             mHandler.removeMessages(IDLE_TIMEOUT_MSG, r);
   1805             r.finishLaunchTickingLocked();
   1806             if (fromTimeout) {
   1807                 reportActivityLaunchedLocked(fromTimeout, r, -1, -1);
   1808             }
   1809 
   1810             // This is a hack to semi-deal with a race condition
   1811             // in the client where it can be constructed with a
   1812             // newer configuration from when we asked it to launch.
   1813             // We'll update with whatever configuration it now says
   1814             // it used to launch.
   1815             if (config != null) {
   1816                 r.configuration = config;
   1817             }
   1818 
   1819             // We are now idle.  If someone is waiting for a thumbnail from
   1820             // us, we can now deliver.
   1821             r.idle = true;
   1822 
   1823             if (r.thumbnailNeeded && r.app != null && r.app.thread != null) {
   1824                 sendThumbnail = r.app.thread;
   1825                 r.thumbnailNeeded = false;
   1826             }
   1827 
   1828             //Slog.i(TAG, "IDLE: mBooted=" + mBooted + ", fromTimeout=" + fromTimeout);
   1829             if (!mService.mBooted && isFrontStack(r.task.stack)) {
   1830                 mService.mBooted = true;
   1831                 enableScreen = true;
   1832             }
   1833         }
   1834 
   1835         if (allResumedActivitiesIdle()) {
   1836             if (r != null) {
   1837                 mService.scheduleAppGcsLocked();
   1838             }
   1839 
   1840             if (mLaunchingActivity.isHeld()) {
   1841                 mHandler.removeMessages(LAUNCH_TIMEOUT_MSG);
   1842                 if (VALIDATE_WAKE_LOCK_CALLER &&
   1843                         Binder.getCallingUid() != Process.myUid()) {
   1844                     throw new IllegalStateException("Calling must be system uid");
   1845                 }
   1846                 mLaunchingActivity.release();
   1847             }
   1848             ensureActivitiesVisibleLocked(null, 0);
   1849         }
   1850 
   1851         // Atomically retrieve all of the other things to do.
   1852         stops = processStoppingActivitiesLocked(true);
   1853         NS = stops != null ? stops.size() : 0;
   1854         if ((NF=mFinishingActivities.size()) > 0) {
   1855             finishes = new ArrayList<ActivityRecord>(mFinishingActivities);
   1856             mFinishingActivities.clear();
   1857         }
   1858 
   1859         final ArrayList<ActivityRecord> thumbnails;
   1860         final int NT = mCancelledThumbnails.size();
   1861         if (NT > 0) {
   1862             thumbnails = new ArrayList<ActivityRecord>(mCancelledThumbnails);
   1863             mCancelledThumbnails.clear();
   1864         } else {
   1865             thumbnails = null;
   1866         }
   1867 
   1868         if (isFrontStack(mHomeStack)) {
   1869             booting = mService.mBooting;
   1870             mService.mBooting = false;
   1871         }
   1872 
   1873         if (mStartingUsers.size() > 0) {
   1874             startingUsers = new ArrayList<UserStartedState>(mStartingUsers);
   1875             mStartingUsers.clear();
   1876         }
   1877 
   1878         // Perform the following actions from unsynchronized state.
   1879         final IApplicationThread thumbnailThread = sendThumbnail;
   1880         mHandler.post(new Runnable() {
   1881             @Override
   1882             public void run() {
   1883                 if (thumbnailThread != null) {
   1884                     try {
   1885                         thumbnailThread.requestThumbnail(token);
   1886                     } catch (Exception e) {
   1887                         Slog.w(TAG, "Exception thrown when requesting thumbnail", e);
   1888                         mService.sendPendingThumbnail(null, token, null, null, true);
   1889                     }
   1890                 }
   1891 
   1892                 // Report back to any thumbnail receivers.
   1893                 for (int i = 0; i < NT; i++) {
   1894                     ActivityRecord r = thumbnails.get(i);
   1895                     mService.sendPendingThumbnail(r, null, null, null, true);
   1896                 }
   1897             }
   1898         });
   1899 
   1900         // Stop any activities that are scheduled to do so but have been
   1901         // waiting for the next one to start.
   1902         for (int i = 0; i < NS; i++) {
   1903             r = stops.get(i);
   1904             final ActivityStack stack = r.task.stack;
   1905             if (r.finishing) {
   1906                 stack.finishCurrentActivityLocked(r, ActivityStack.FINISH_IMMEDIATELY, false);
   1907             } else {
   1908                 stack.stopActivityLocked(r);
   1909             }
   1910         }
   1911 
   1912         // Finish any activities that are scheduled to do so but have been
   1913         // waiting for the next one to start.
   1914         for (int i = 0; i < NF; i++) {
   1915             r = finishes.get(i);
   1916             activityRemoved |= r.task.stack.destroyActivityLocked(r, true, false, "finish-idle");
   1917         }
   1918 
   1919         if (booting) {
   1920             mService.finishBooting();
   1921         } else if (startingUsers != null) {
   1922             for (int i = 0; i < startingUsers.size(); i++) {
   1923                 mService.finishUserSwitch(startingUsers.get(i));
   1924             }
   1925         }
   1926 
   1927         mService.trimApplications();
   1928         //dump();
   1929         //mWindowManager.dump();
   1930 
   1931         if (enableScreen) {
   1932             mService.enableScreenAfterBoot();
   1933         }
   1934 
   1935         if (activityRemoved) {
   1936             resumeTopActivitiesLocked();
   1937         }
   1938 
   1939         return r;
   1940     }
   1941 
   1942     boolean handleAppDiedLocked(ProcessRecord app) {
   1943         boolean hasVisibleActivities = false;
   1944         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   1945             hasVisibleActivities |= mStacks.get(stackNdx).handleAppDiedLocked(app);
   1946         }
   1947         return hasVisibleActivities;
   1948     }
   1949 
   1950     void closeSystemDialogsLocked() {
   1951         final int numStacks = mStacks.size();
   1952         for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
   1953             final ActivityStack stack = mStacks.get(stackNdx);
   1954             stack.closeSystemDialogsLocked();
   1955         }
   1956     }
   1957 
   1958     void removeUserLocked(int userId) {
   1959         mUserStackInFront.delete(userId);
   1960     }
   1961 
   1962     /**
   1963      * @return true if some activity was finished (or would have finished if doit were true).
   1964      */
   1965     boolean forceStopPackageLocked(String name, boolean doit, boolean evenPersistent, int userId) {
   1966         boolean didSomething = false;
   1967         final int numStacks = mStacks.size();
   1968         for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
   1969             final ActivityStack stack = mStacks.get(stackNdx);
   1970             if (stack.forceStopPackageLocked(name, doit, evenPersistent, userId)) {
   1971                 didSomething = true;
   1972             }
   1973         }
   1974         return didSomething;
   1975     }
   1976 
   1977     void updatePreviousProcessLocked(ActivityRecord r) {
   1978         // Now that this process has stopped, we may want to consider
   1979         // it to be the previous app to try to keep around in case
   1980         // the user wants to return to it.
   1981 
   1982         // First, found out what is currently the foreground app, so that
   1983         // we don't blow away the previous app if this activity is being
   1984         // hosted by the process that is actually still the foreground.
   1985         ProcessRecord fgApp = null;
   1986         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   1987             final ActivityStack stack = mStacks.get(stackNdx);
   1988             if (isFrontStack(stack)) {
   1989                 if (stack.mResumedActivity != null) {
   1990                     fgApp = stack.mResumedActivity.app;
   1991                 } else if (stack.mPausingActivity != null) {
   1992                     fgApp = stack.mPausingActivity.app;
   1993                 }
   1994                 break;
   1995             }
   1996         }
   1997 
   1998         // Now set this one as the previous process, only if that really
   1999         // makes sense to.
   2000         if (r.app != null && fgApp != null && r.app != fgApp
   2001                 && r.lastVisibleTime > mService.mPreviousProcessVisibleTime
   2002                 && r.app != mService.mHomeProcess) {
   2003             mService.mPreviousProcess = r.app;
   2004             mService.mPreviousProcessVisibleTime = r.lastVisibleTime;
   2005         }
   2006     }
   2007 
   2008     boolean resumeTopActivitiesLocked() {
   2009         return resumeTopActivitiesLocked(null, null, null);
   2010     }
   2011 
   2012     boolean resumeTopActivitiesLocked(ActivityStack targetStack, ActivityRecord target,
   2013             Bundle targetOptions) {
   2014         if (targetStack == null) {
   2015             targetStack = getFocusedStack();
   2016         }
   2017         boolean result = false;
   2018         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2019             final ActivityStack stack = mStacks.get(stackNdx);
   2020             if (isFrontStack(stack)) {
   2021                 if (stack == targetStack) {
   2022                     result = stack.resumeTopActivityLocked(target, targetOptions);
   2023                 } else {
   2024                     stack.resumeTopActivityLocked(null);
   2025                 }
   2026             }
   2027         }
   2028         return result;
   2029     }
   2030 
   2031     void finishTopRunningActivityLocked(ProcessRecord app) {
   2032         final int numStacks = mStacks.size();
   2033         for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
   2034             final ActivityStack stack = mStacks.get(stackNdx);
   2035             stack.finishTopRunningActivityLocked(app);
   2036         }
   2037     }
   2038 
   2039     void findTaskToMoveToFrontLocked(int taskId, int flags, Bundle options) {
   2040         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2041             if (mStacks.get(stackNdx).findTaskToMoveToFrontLocked(taskId, flags, options)) {
   2042                 if (DEBUG_STACK) Slog.d(TAG, "findTaskToMoveToFront: moved to front of stack=" +
   2043                         mStacks.get(stackNdx));
   2044                 return;
   2045             }
   2046         }
   2047     }
   2048 
   2049     ActivityStack getStack(int stackId) {
   2050         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2051             final ActivityStack stack = mStacks.get(stackNdx);
   2052             if (stack.getStackId() == stackId) {
   2053                 return stack;
   2054             }
   2055         }
   2056         return null;
   2057     }
   2058 
   2059     ArrayList<ActivityStack> getStacks() {
   2060         return new ArrayList<ActivityStack>(mStacks);
   2061     }
   2062 
   2063     int createStack() {
   2064         while (true) {
   2065             if (++mLastStackId <= HOME_STACK_ID) {
   2066                 mLastStackId = HOME_STACK_ID + 1;
   2067             }
   2068             if (getStack(mLastStackId) == null) {
   2069                 break;
   2070             }
   2071         }
   2072         mStacks.add(new ActivityStack(mService, mContext, mLooper, mLastStackId));
   2073         return mLastStackId;
   2074     }
   2075 
   2076     void moveTaskToStack(int taskId, int stackId, boolean toTop) {
   2077         final TaskRecord task = anyTaskForIdLocked(taskId);
   2078         if (task == null) {
   2079             return;
   2080         }
   2081         final ActivityStack stack = getStack(stackId);
   2082         if (stack == null) {
   2083             Slog.w(TAG, "moveTaskToStack: no stack for id=" + stackId);
   2084             return;
   2085         }
   2086         removeTask(task);
   2087         stack.addTask(task, toTop);
   2088         mWindowManager.addTask(taskId, stackId, toTop);
   2089         resumeTopActivitiesLocked();
   2090     }
   2091 
   2092     ActivityRecord findTaskLocked(ActivityRecord r) {
   2093         if (DEBUG_TASKS) Slog.d(TAG, "Looking for task of " + r);
   2094         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2095             final ActivityStack stack = mStacks.get(stackNdx);
   2096             if (!r.isApplicationActivity() && !stack.isHomeStack()) {
   2097                 if (DEBUG_TASKS) Slog.d(TAG, "Skipping stack: " + stack);
   2098                 continue;
   2099             }
   2100             final ActivityRecord ar = stack.findTaskLocked(r);
   2101             if (ar != null) {
   2102                 return ar;
   2103             }
   2104         }
   2105         if (DEBUG_TASKS) Slog.d(TAG, "No task found");
   2106         return null;
   2107     }
   2108 
   2109     ActivityRecord findActivityLocked(Intent intent, ActivityInfo info) {
   2110         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2111             final ActivityRecord ar = mStacks.get(stackNdx).findActivityLocked(intent, info);
   2112             if (ar != null) {
   2113                 return ar;
   2114             }
   2115         }
   2116         return null;
   2117     }
   2118 
   2119     void goingToSleepLocked() {
   2120         scheduleSleepTimeout();
   2121         if (!mGoingToSleep.isHeld()) {
   2122             mGoingToSleep.acquire();
   2123             if (mLaunchingActivity.isHeld()) {
   2124                 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) {
   2125                     throw new IllegalStateException("Calling must be system uid");
   2126                 }
   2127                 mLaunchingActivity.release();
   2128                 mService.mHandler.removeMessages(LAUNCH_TIMEOUT_MSG);
   2129             }
   2130         }
   2131         checkReadyForSleepLocked();
   2132     }
   2133 
   2134     boolean shutdownLocked(int timeout) {
   2135         boolean timedout = false;
   2136         goingToSleepLocked();
   2137 
   2138         final long endTime = System.currentTimeMillis() + timeout;
   2139         while (true) {
   2140             boolean cantShutdown = false;
   2141             for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2142                 cantShutdown |= mStacks.get(stackNdx).checkReadyForSleepLocked();
   2143             }
   2144             if (cantShutdown) {
   2145                 long timeRemaining = endTime - System.currentTimeMillis();
   2146                 if (timeRemaining > 0) {
   2147                     try {
   2148                         mService.wait(timeRemaining);
   2149                     } catch (InterruptedException e) {
   2150                     }
   2151                 } else {
   2152                     Slog.w(TAG, "Activity manager shutdown timed out");
   2153                     timedout = true;
   2154                     break;
   2155                 }
   2156             } else {
   2157                 break;
   2158             }
   2159         }
   2160 
   2161         // Force checkReadyForSleep to complete.
   2162         mSleepTimeout = true;
   2163         checkReadyForSleepLocked();
   2164 
   2165         return timedout;
   2166     }
   2167 
   2168     void comeOutOfSleepIfNeededLocked() {
   2169         removeSleepTimeouts();
   2170         if (mGoingToSleep.isHeld()) {
   2171             mGoingToSleep.release();
   2172         }
   2173         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2174             final ActivityStack stack = mStacks.get(stackNdx);
   2175             stack.awakeFromSleepingLocked();
   2176             if (isFrontStack(stack)) {
   2177                 resumeTopActivitiesLocked();
   2178             }
   2179         }
   2180         mGoingToSleepActivities.clear();
   2181     }
   2182 
   2183     void activitySleptLocked(ActivityRecord r) {
   2184         mGoingToSleepActivities.remove(r);
   2185         checkReadyForSleepLocked();
   2186     }
   2187 
   2188     void checkReadyForSleepLocked() {
   2189         if (!mService.isSleepingOrShuttingDown()) {
   2190             // Do not care.
   2191             return;
   2192         }
   2193 
   2194         if (!mSleepTimeout) {
   2195             boolean dontSleep = false;
   2196             for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2197                 dontSleep |= mStacks.get(stackNdx).checkReadyForSleepLocked();
   2198             }
   2199 
   2200             if (mStoppingActivities.size() > 0) {
   2201                 // Still need to tell some activities to stop; can't sleep yet.
   2202                 if (DEBUG_PAUSE) Slog.v(TAG, "Sleep still need to stop "
   2203                         + mStoppingActivities.size() + " activities");
   2204                 scheduleIdleLocked();
   2205                 dontSleep = true;
   2206             }
   2207 
   2208             if (mGoingToSleepActivities.size() > 0) {
   2209                 // Still need to tell some activities to sleep; can't sleep yet.
   2210                 if (DEBUG_PAUSE) Slog.v(TAG, "Sleep still need to sleep "
   2211                         + mGoingToSleepActivities.size() + " activities");
   2212                 dontSleep = true;
   2213             }
   2214 
   2215             if (dontSleep) {
   2216                 return;
   2217             }
   2218         }
   2219 
   2220         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2221             mStacks.get(stackNdx).goToSleep();
   2222         }
   2223 
   2224         removeSleepTimeouts();
   2225 
   2226         if (mGoingToSleep.isHeld()) {
   2227             mGoingToSleep.release();
   2228         }
   2229         if (mService.mShuttingDown) {
   2230             mService.notifyAll();
   2231         }
   2232     }
   2233 
   2234     boolean reportResumedActivityLocked(ActivityRecord r) {
   2235         final ActivityStack stack = r.task.stack;
   2236         if (isFrontStack(stack)) {
   2237             mService.updateUsageStats(r, true);
   2238         }
   2239         if (allResumedActivitiesComplete()) {
   2240             ensureActivitiesVisibleLocked(null, 0);
   2241             mWindowManager.executeAppTransition();
   2242             return true;
   2243         }
   2244         return false;
   2245     }
   2246 
   2247     void handleAppCrashLocked(ProcessRecord app) {
   2248         final int numStacks = mStacks.size();
   2249         for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
   2250             final ActivityStack stack = mStacks.get(stackNdx);
   2251             stack.handleAppCrashLocked(app);
   2252         }
   2253     }
   2254 
   2255     void ensureActivitiesVisibleLocked(ActivityRecord starting, int configChanges) {
   2256         // First the front stacks. In case any are not fullscreen and are in front of home.
   2257         boolean showHomeBehindStack = false;
   2258         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2259             final ActivityStack stack = mStacks.get(stackNdx);
   2260             if (isFrontStack(stack)) {
   2261                 showHomeBehindStack =
   2262                         stack.ensureActivitiesVisibleLocked(starting, configChanges);
   2263             }
   2264         }
   2265         // Now do back stacks.
   2266         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2267             final ActivityStack stack = mStacks.get(stackNdx);
   2268             if (!isFrontStack(stack)) {
   2269                 stack.ensureActivitiesVisibleLocked(starting, configChanges, showHomeBehindStack);
   2270             }
   2271         }
   2272     }
   2273 
   2274     void scheduleDestroyAllActivities(ProcessRecord app, String reason) {
   2275         final int numStacks = mStacks.size();
   2276         for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
   2277             final ActivityStack stack = mStacks.get(stackNdx);
   2278             stack.scheduleDestroyActivities(app, false, reason);
   2279         }
   2280     }
   2281 
   2282     boolean switchUserLocked(int userId, UserStartedState uss) {
   2283         mUserStackInFront.put(mCurrentUser, getFocusedStack().getStackId());
   2284         final int restoreStackId = mUserStackInFront.get(userId, HOME_STACK_ID);
   2285         mCurrentUser = userId;
   2286 
   2287         mStartingUsers.add(uss);
   2288         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2289             mStacks.get(stackNdx).switchUserLocked(userId);
   2290         }
   2291 
   2292         ActivityStack stack = getStack(restoreStackId);
   2293         if (stack == null) {
   2294             stack = mHomeStack;
   2295         }
   2296         final boolean homeInFront = stack.isHomeStack();
   2297         moveHomeStack(homeInFront);
   2298         mWindowManager.moveTaskToTop(stack.topTask().taskId);
   2299         return homeInFront;
   2300     }
   2301 
   2302     final ArrayList<ActivityRecord> processStoppingActivitiesLocked(boolean remove) {
   2303         int N = mStoppingActivities.size();
   2304         if (N <= 0) return null;
   2305 
   2306         ArrayList<ActivityRecord> stops = null;
   2307 
   2308         final boolean nowVisible = allResumedActivitiesVisible();
   2309         for (int i=0; i<N; i++) {
   2310             ActivityRecord s = mStoppingActivities.get(i);
   2311             if (localLOGV) Slog.v(TAG, "Stopping " + s + ": nowVisible="
   2312                     + nowVisible + " waitingVisible=" + s.waitingVisible
   2313                     + " finishing=" + s.finishing);
   2314             if (s.waitingVisible && nowVisible) {
   2315                 mWaitingVisibleActivities.remove(s);
   2316                 s.waitingVisible = false;
   2317                 if (s.finishing) {
   2318                     // If this activity is finishing, it is sitting on top of
   2319                     // everyone else but we now know it is no longer needed...
   2320                     // so get rid of it.  Otherwise, we need to go through the
   2321                     // normal flow and hide it once we determine that it is
   2322                     // hidden by the activities in front of it.
   2323                     if (localLOGV) Slog.v(TAG, "Before stopping, can hide: " + s);
   2324                     mWindowManager.setAppVisibility(s.appToken, false);
   2325                 }
   2326             }
   2327             if ((!s.waitingVisible || mService.isSleepingOrShuttingDown()) && remove) {
   2328                 if (localLOGV) Slog.v(TAG, "Ready to stop: " + s);
   2329                 if (stops == null) {
   2330                     stops = new ArrayList<ActivityRecord>();
   2331                 }
   2332                 stops.add(s);
   2333                 mStoppingActivities.remove(i);
   2334                 N--;
   2335                 i--;
   2336             }
   2337         }
   2338 
   2339         return stops;
   2340     }
   2341 
   2342     void validateTopActivitiesLocked() {
   2343         for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) {
   2344             final ActivityStack stack = mStacks.get(stackNdx);
   2345             final ActivityRecord r = stack.topRunningActivityLocked(null);
   2346             final ActivityState state = r == null ? ActivityState.DESTROYED : r.state;
   2347             if (isFrontStack(stack)) {
   2348                 if (r == null) {
   2349                     Slog.e(TAG, "validateTop...: null top activity, stack=" + stack);
   2350                 } else {
   2351                     final ActivityRecord pausing = stack.mPausingActivity;
   2352                     if (pausing != null && pausing == r) {
   2353                         Slog.e(TAG, "validateTop...: top stack has pausing activity r=" + r +
   2354                             " state=" + state);
   2355                     }
   2356                     if (state != ActivityState.INITIALIZING && state != ActivityState.RESUMED) {
   2357                         Slog.e(TAG, "validateTop...: activity in front not resumed r=" + r +
   2358                                 " state=" + state);
   2359                     }
   2360                 }
   2361             } else {
   2362                 final ActivityRecord resumed = stack.mResumedActivity;
   2363                 if (resumed != null && resumed == r) {
   2364                     Slog.e(TAG, "validateTop...: back stack has resumed activity r=" + r +
   2365                         " state=" + state);
   2366                 }
   2367                 if (r != null && (state == ActivityState.INITIALIZING
   2368                         || state == ActivityState.RESUMED)) {
   2369                     Slog.e(TAG, "validateTop...: activity in back resumed r=" + r +
   2370                             " state=" + state);
   2371                 }
   2372             }
   2373         }
   2374     }
   2375 
   2376     private static String stackStateToString(int stackState) {
   2377         switch (stackState) {
   2378             case STACK_STATE_HOME_IN_FRONT: return "STACK_STATE_HOME_IN_FRONT";
   2379             case STACK_STATE_HOME_TO_BACK: return "STACK_STATE_HOME_TO_BACK";
   2380             case STACK_STATE_HOME_IN_BACK: return "STACK_STATE_HOME_IN_BACK";
   2381             case STACK_STATE_HOME_TO_FRONT: return "STACK_STATE_HOME_TO_FRONT";
   2382             default: return "Unknown stackState=" + stackState;
   2383         }
   2384     }
   2385 
   2386     public void dump(PrintWriter pw, String prefix) {
   2387         pw.print(prefix); pw.print("mDismissKeyguardOnNextActivity=");
   2388                 pw.println(mDismissKeyguardOnNextActivity);
   2389         pw.print(prefix); pw.print("mFocusedStack=" + mFocusedStack);
   2390                 pw.print(" mStackState="); pw.println(stackStateToString(mStackState));
   2391         pw.print(prefix); pw.println("mSleepTimeout=" + mSleepTimeout);
   2392         pw.print(prefix); pw.println("mCurTaskId=" + mCurTaskId);
   2393         pw.print(prefix); pw.println("mUserStackInFront=" + mUserStackInFront);
   2394     }
   2395 
   2396     ArrayList<ActivityRecord> getDumpActivitiesLocked(String name) {
   2397         return getFocusedStack().getDumpActivitiesLocked(name);
   2398     }
   2399 
   2400     static boolean printThisActivity(PrintWriter pw, ActivityRecord activity, String dumpPackage,
   2401             boolean needSep, String prefix) {
   2402         if (activity != null) {
   2403             if (dumpPackage == null || dumpPackage.equals(activity.packageName)) {
   2404                 if (needSep) {
   2405                     pw.println();
   2406                 }
   2407                 pw.print(prefix);
   2408                 pw.println(activity);
   2409                 return true;
   2410             }
   2411         }
   2412         return false;
   2413     }
   2414 
   2415     boolean dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, boolean dumpAll,
   2416             boolean dumpClient, String dumpPackage) {
   2417         boolean printed = false;
   2418         boolean needSep = false;
   2419         final int numStacks = mStacks.size();
   2420         for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) {
   2421             final ActivityStack stack = mStacks.get(stackNdx);
   2422             StringBuilder stackHeader = new StringBuilder(128);
   2423             stackHeader.append("  Stack #");
   2424             stackHeader.append(mStacks.indexOf(stack));
   2425             stackHeader.append(":");
   2426             printed |= stack.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, dumpPackage, needSep,
   2427                     stackHeader.toString());
   2428             printed |= dumpHistoryList(fd, pw, stack.mLRUActivities, "    ", "Run", false, !dumpAll,
   2429                     false, dumpPackage, true, "    Running activities (most recent first):", null);
   2430 
   2431             needSep = printed;
   2432             boolean pr = printThisActivity(pw, stack.mPausingActivity, dumpPackage, needSep,
   2433                     "    mPausingActivity: ");
   2434             if (pr) {
   2435                 printed = true;
   2436                 needSep = false;
   2437             }
   2438             pr = printThisActivity(pw, stack.mResumedActivity, dumpPackage, needSep,
   2439                     "    mResumedActivity: ");
   2440             if (pr) {
   2441                 printed = true;
   2442                 needSep = false;
   2443             }
   2444             if (dumpAll) {
   2445                 pr = printThisActivity(pw, stack.mLastPausedActivity, dumpPackage, needSep,
   2446                         "    mLastPausedActivity: ");
   2447                 if (pr) {
   2448                     printed = true;
   2449                     needSep = true;
   2450                 }
   2451                 printed |= printThisActivity(pw, stack.mLastNoHistoryActivity, dumpPackage,
   2452                         needSep, "    mLastNoHistoryActivity: ");
   2453             }
   2454             needSep = printed;
   2455         }
   2456 
   2457         printed |= dumpHistoryList(fd, pw, mFinishingActivities, "  ", "Fin", false, !dumpAll,
   2458                 false, dumpPackage, true, "  Activities waiting to finish:", null);
   2459         printed |= dumpHistoryList(fd, pw, mStoppingActivities, "  ", "Stop", false, !dumpAll,
   2460                 false, dumpPackage, true, "  Activities waiting to stop:", null);
   2461         printed |= dumpHistoryList(fd, pw, mWaitingVisibleActivities, "  ", "Wait", false, !dumpAll,
   2462                 false, dumpPackage, true, "  Activities waiting for another to become visible:",
   2463                 null);
   2464         printed |= dumpHistoryList(fd, pw, mGoingToSleepActivities, "  ", "Sleep", false, !dumpAll,
   2465                 false, dumpPackage, true, "  Activities waiting to sleep:", null);
   2466         printed |= dumpHistoryList(fd, pw, mGoingToSleepActivities, "  ", "Sleep", false, !dumpAll,
   2467                 false, dumpPackage, true, "  Activities waiting to sleep:", null);
   2468 
   2469         return printed;
   2470     }
   2471 
   2472     static boolean dumpHistoryList(FileDescriptor fd, PrintWriter pw, List<ActivityRecord> list,
   2473             String prefix, String label, boolean complete, boolean brief, boolean client,
   2474             String dumpPackage, boolean needNL, String header1, String header2) {
   2475         TaskRecord lastTask = null;
   2476         String innerPrefix = null;
   2477         String[] args = null;
   2478         boolean printed = false;
   2479         for (int i=list.size()-1; i>=0; i--) {
   2480             final ActivityRecord r = list.get(i);
   2481             if (dumpPackage != null && !dumpPackage.equals(r.packageName)) {
   2482                 continue;
   2483             }
   2484             if (innerPrefix == null) {
   2485                 innerPrefix = prefix + "      ";
   2486                 args = new String[0];
   2487             }
   2488             printed = true;
   2489             final boolean full = !brief && (complete || !r.isInHistory());
   2490             if (needNL) {
   2491                 pw.println("");
   2492                 needNL = false;
   2493             }
   2494             if (header1 != null) {
   2495                 pw.println(header1);
   2496                 header1 = null;
   2497             }
   2498             if (header2 != null) {
   2499                 pw.println(header2);
   2500                 header2 = null;
   2501             }
   2502             if (lastTask != r.task) {
   2503                 lastTask = r.task;
   2504                 pw.print(prefix);
   2505                 pw.print(full ? "* " : "  ");
   2506                 pw.println(lastTask);
   2507                 if (full) {
   2508                     lastTask.dump(pw, prefix + "  ");
   2509                 } else if (complete) {
   2510                     // Complete + brief == give a summary.  Isn't that obvious?!?
   2511                     if (lastTask.intent != null) {
   2512                         pw.print(prefix); pw.print("  ");
   2513                                 pw.println(lastTask.intent.toInsecureStringWithClip());
   2514                     }
   2515                 }
   2516             }
   2517             pw.print(prefix); pw.print(full ? "  * " : "    "); pw.print(label);
   2518             pw.print(" #"); pw.print(i); pw.print(": ");
   2519             pw.println(r);
   2520             if (full) {
   2521                 r.dump(pw, innerPrefix);
   2522             } else if (complete) {
   2523                 // Complete + brief == give a summary.  Isn't that obvious?!?
   2524                 pw.print(innerPrefix); pw.println(r.intent.toInsecureString());
   2525                 if (r.app != null) {
   2526                     pw.print(innerPrefix); pw.println(r.app);
   2527                 }
   2528             }
   2529             if (client && r.app != null && r.app.thread != null) {
   2530                 // flush anything that is already in the PrintWriter since the thread is going
   2531                 // to write to the file descriptor directly
   2532                 pw.flush();
   2533                 try {
   2534                     TransferPipe tp = new TransferPipe();
   2535                     try {
   2536                         r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(),
   2537                                 r.appToken, innerPrefix, args);
   2538                         // Short timeout, since blocking here can
   2539                         // deadlock with the application.
   2540                         tp.go(fd, 2000);
   2541                     } finally {
   2542                         tp.kill();
   2543                     }
   2544                 } catch (IOException e) {
   2545                     pw.println(innerPrefix + "Failure while dumping the activity: " + e);
   2546                 } catch (RemoteException e) {
   2547                     pw.println(innerPrefix + "Got a RemoteException while dumping the activity");
   2548                 }
   2549                 needNL = true;
   2550             }
   2551         }
   2552         return printed;
   2553     }
   2554 
   2555     void scheduleIdleTimeoutLocked(ActivityRecord next) {
   2556         if (DEBUG_IDLE) Slog.d(TAG, "scheduleIdleTimeoutLocked: Callers=" + Debug.getCallers(4));
   2557         Message msg = mHandler.obtainMessage(IDLE_TIMEOUT_MSG, next);
   2558         mHandler.sendMessageDelayed(msg, IDLE_TIMEOUT);
   2559     }
   2560 
   2561     final void scheduleIdleLocked() {
   2562         mHandler.sendEmptyMessage(IDLE_NOW_MSG);
   2563     }
   2564 
   2565     void removeTimeoutsForActivityLocked(ActivityRecord r) {
   2566         if (DEBUG_IDLE) Slog.d(TAG, "removeTimeoutsForActivity: Callers=" + Debug.getCallers(4));
   2567         mHandler.removeMessages(IDLE_TIMEOUT_MSG, r);
   2568     }
   2569 
   2570     final void scheduleResumeTopActivities() {
   2571         mHandler.sendEmptyMessage(RESUME_TOP_ACTIVITY_MSG);
   2572     }
   2573 
   2574     void removeSleepTimeouts() {
   2575         mSleepTimeout = false;
   2576         mHandler.removeMessages(SLEEP_TIMEOUT_MSG);
   2577     }
   2578 
   2579     final void scheduleSleepTimeout() {
   2580         removeSleepTimeouts();
   2581         mHandler.sendEmptyMessageDelayed(SLEEP_TIMEOUT_MSG, SLEEP_TIMEOUT);
   2582     }
   2583 
   2584     private final class ActivityStackSupervisorHandler extends Handler {
   2585 
   2586         public ActivityStackSupervisorHandler(Looper looper) {
   2587             super(looper);
   2588         }
   2589 
   2590         void activityIdleInternal(ActivityRecord r) {
   2591             synchronized (mService) {
   2592                 activityIdleInternalLocked(r != null ? r.appToken : null, true, null);
   2593             }
   2594         }
   2595 
   2596         @Override
   2597         public void handleMessage(Message msg) {
   2598             switch (msg.what) {
   2599                 case IDLE_TIMEOUT_MSG: {
   2600                     if (DEBUG_IDLE) Slog.d(TAG, "handleMessage: IDLE_TIMEOUT_MSG: r=" + msg.obj);
   2601                     if (mService.mDidDexOpt) {
   2602                         mService.mDidDexOpt = false;
   2603                         Message nmsg = mHandler.obtainMessage(IDLE_TIMEOUT_MSG);
   2604                         nmsg.obj = msg.obj;
   2605                         mHandler.sendMessageDelayed(nmsg, IDLE_TIMEOUT);
   2606                         return;
   2607                     }
   2608                     // We don't at this point know if the activity is fullscreen,
   2609                     // so we need to be conservative and assume it isn't.
   2610                     activityIdleInternal((ActivityRecord)msg.obj);
   2611                 } break;
   2612                 case IDLE_NOW_MSG: {
   2613                     if (DEBUG_IDLE) Slog.d(TAG, "handleMessage: IDLE_NOW_MSG: r=" + msg.obj);
   2614                     activityIdleInternal((ActivityRecord)msg.obj);
   2615                 } break;
   2616                 case RESUME_TOP_ACTIVITY_MSG: {
   2617                     synchronized (mService) {
   2618                         resumeTopActivitiesLocked();
   2619                     }
   2620                 } break;
   2621                 case SLEEP_TIMEOUT_MSG: {
   2622                     synchronized (mService) {
   2623                         if (mService.isSleepingOrShuttingDown()) {
   2624                             Slog.w(TAG, "Sleep timeout!  Sleeping now.");
   2625                             mSleepTimeout = true;
   2626                             checkReadyForSleepLocked();
   2627                         }
   2628                     }
   2629                 } break;
   2630                 case LAUNCH_TIMEOUT_MSG: {
   2631                     if (mService.mDidDexOpt) {
   2632                         mService.mDidDexOpt = false;
   2633                         mHandler.sendEmptyMessageDelayed(LAUNCH_TIMEOUT_MSG, LAUNCH_TIMEOUT);
   2634                         return;
   2635                     }
   2636                     synchronized (mService) {
   2637                         if (mLaunchingActivity.isHeld()) {
   2638                             Slog.w(TAG, "Launch timeout has expired, giving up wake lock!");
   2639                             if (VALIDATE_WAKE_LOCK_CALLER
   2640                                     && Binder.getCallingUid() != Process.myUid()) {
   2641                                 throw new IllegalStateException("Calling must be system uid");
   2642                             }
   2643                             mLaunchingActivity.release();
   2644                         }
   2645                     }
   2646                 } break;
   2647             }
   2648         }
   2649     }
   2650 }
   2651