Jimmy Chen

A Programmer

基于Android 9之应用冷启动过程分析(二)

Advertisements
Advertisements
Advertisements

  上一篇讲到最后会调用到startActivity,接着分析前想先说一下,其实这篇主要的目的还是想先了解点击应用到调用应用第一个Activity.onCreate方法的整个过程,所以中间有一些方法会先放过不分析,下面继续接着上一篇进行分析,先把上一次调用的代码贴出来:

..............
final ActivityRecord[] outRecord = new ActivityRecord[1];
int res = startActivity(caller, intent, ephemeralIntent, resolvedType, aInfo, rInfo,
        voiceSession, voiceInteractor, resultTo, resultWho, requestCode, callingPid,
        callingUid, callingPackage, realCallingPid, realCallingUid, startFlags, options,
        ignoreTargetSecurity, componentSpecified, outRecord, inTask, reason,
        allowPendingRemoteAnimationRegistryLookup, originatingPendingIntent);

Binder.restoreCallingIdentity(origId);
...............

这里参数非常多,而且startActivity还有重载函数,所以在阅读的时候还是要做好区分

// ActivityStarter.java
private int startActivity(IApplicationThread caller, Intent intent, Intent ephemeralIntent,
        String resolvedType, ActivityInfo aInfo, ResolveInfo rInfo,
        IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
        IBinder resultTo, String resultWho, int requestCode, int callingPid, int callingUid,
        String callingPackage, int realCallingPid, int realCallingUid, int startFlags,
        SafeActivityOptions options, boolean ignoreTargetSecurity, boolean componentSpecified,
        ActivityRecord[] outActivity, TaskRecord inTask, String reason,
        boolean allowPendingRemoteAnimationRegistryLookup,
        PendingIntentRecord originatingPendingIntent) {

    if (TextUtils.isEmpty(reason)) {
        throw new IllegalArgumentException("Need to specify a reason.");
    }
    // 获取启动的原因,这里把启动原因处理了
    mLastStartReason = reason;
    mLastStartActivityTimeMs = System.currentTimeMillis();
    mLastStartActivityRecord[0] = null;

    // 调用同名重载方法,这里比当前流程中的startActivity少了一个reason参数
    mLastStartActivityResult = startActivity(caller, intent, ephemeralIntent, resolvedType,
            aInfo, rInfo, voiceSession, voiceInteractor, resultTo, resultWho, requestCode,
            callingPid, callingUid, callingPackage, realCallingPid, realCallingUid, startFlags,
            options, ignoreTargetSecurity, componentSpecified, mLastStartActivityRecord,
            inTask, allowPendingRemoteAnimationRegistryLookup, originatingPendingIntent);

    if (outActivity != null) {
        // mLastStartActivityRecord[0] is set in the call to startActivity above.
        outActivity[0] = mLastStartActivityRecord[0];
    }

    return getExternalResult(mLastStartActivityResult);
}

// 调用同名重载函数
private int startActivity(IApplicationThread caller, Intent intent, Intent ephemeralIntent,
        String resolvedType, ActivityInfo aInfo, ResolveInfo rInfo,
        IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
        IBinder resultTo, String resultWho, int requestCode, int callingPid, int callingUid,
        String callingPackage, int realCallingPid, int realCallingUid, int startFlags,
        SafeActivityOptions options,
        boolean ignoreTargetSecurity, boolean componentSpecified, ActivityRecord[] outActivity,
        TaskRecord inTask, boolean allowPendingRemoteAnimationRegistryLookup,
        PendingIntentRecord originatingPendingIntent) {
    int err = ActivityManager.START_SUCCESS;
    // Pull the optional Ephemeral Installer-only bundle out of the options early.
    final Bundle verificationBundle
            = options != null ? options.popAppVerificationBundle() : null;

    // 每个进程都会使用一个ProcessRecord来表示,这里记录调用者所在的ProcessRecord
    ProcessRecord callerApp = null;
    if (caller != null) {
        // 这里通过AMS的getRecordForAppLocked方法来获取调用者所在的ProcessRecord
        callerApp = mService.getRecordForAppLocked(caller);
        if (callerApp != null) {
            // 获取调用者的uid和pid
            callingPid = callerApp.pid;
            callingUid = callerApp.info.uid;
        } else {
            Slog.w(TAG, "Unable to find app for caller " + caller
                    + " (pid=" + callingPid + ") when starting: "
                    + intent.toString());
            err = ActivityManager.START_PERMISSION_DENIED;
        }
    }

    ...........................
    // sourceRecord用来记录调用者的Activity信息
    ActivityRecord sourceRecord = null;
    // resultRecord用来记录被调用者(即目标Activity)的Activity信息
    ActivityRecord resultRecord = null;
    // resultTo不为空表明启动Activity需要返回结果
    if (resultTo != null) {
        // 查看接收结果的ActivityRecord是否在堆栈里面
        sourceRecord = mSupervisor.isInAnyStackLocked(resultTo);
        if (DEBUG_RESULTS) Slog.v(TAG_RESULTS,
                "Will send result to " + resultTo + " " + sourceRecord);
        if (sourceRecord != null) {
            // 如果需要返回结果,并且接收结果的Activity不是正在结束的
            // 保存相应的Activity到resutlRecord中
            if (requestCode >= 0 && !sourceRecord.finishing) {
                resultRecord = sourceRecord;
            }
        }
    }

    final int launchFlags = intent.getFlags();

    // 处理设置了FLAG_ACTIVITY_FORWARD_RESULT的情况
    // FLAG_ACTIVITY_FORWARD_RESULT标志位,并且为了避免冲突B在启动C时不需要再设置requestCode,
    // 而此时sourceRecord是B,resultRecord是A,就是下面代码的解释,
    // 设置该标志后,C调用setResult时结果不会传递给B而是传递给A
    if ((launchFlags & Intent.FLAG_ACTIVITY_FORWARD_RESULT) != 0 && sourceRecord != null) {
        // 这里requestCode是B传过来的,如果设置了上面的标签,B就不能再设置requestCode,因此,如果
        // requestCode>=0就会产生冲突,因此B不能再设置requestCode
        if (requestCode >= 0) {
            SafeActivityOptions.abort(options);
            return ActivityManager.START_FORWARD_AND_REQUEST_CONFLICT;
        }
        // 如果设置了上面的标签,最终的接受结果的Activity就是B(sourceRecord)中resultTo指向的Activity而不是B
        resultRecord = sourceRecord.resultTo;
        if (resultRecord != null && !resultRecord.isInStackLocked()) {
            resultRecord = null;
        }
        resultWho = sourceRecord.resultWho;
        requestCode = sourceRecord.requestCode;
        sourceRecord.resultTo = null;
        if (resultRecord != null) {
            resultRecord.removeResultsLocked(sourceRecord, resultWho, requestCode);
        }
        if (sourceRecord.launchedFromUid == callingUid) {
            callingPackage = sourceRecord.launchedFromPackage;
        }
    }

    // 两处错误处理
    // 此处是处理无法找到响应intent的class
    if (err == ActivityManager.START_SUCCESS && intent.getComponent() == null) {
        err = ActivityManager.START_INTENT_NOT_RESOLVED;
    }

    // 此处是无法找到intent中指定的Activity
    if (err == ActivityManager.START_SUCCESS && aInfo == null) {
        // We couldn't find the specific class specified in the Intent.
        // Also the end of the line.
        err = ActivityManager.START_CLASS_NOT_FOUND;
    }

    // voiceSession是和语音接口相关的东西,此处不管
    if (err == ActivityManager.START_SUCCESS && sourceRecord != null
            && sourceRecord.getTask().voiceSession != null) {
        ...............................
    }

    if (err == ActivityManager.START_SUCCESS && voiceSession != null) {
        ...............................
    }

    final ActivityStack resultStack = resultRecord == null ? null : resultRecord.getStack();

    // 上面的步骤都没有问题,发送Activity处理结果
    if (err != START_SUCCESS) {
        if (resultRecord != null) {
            resultStack.sendActivityResultLocked(
                    -1, resultRecord, resultWho, requestCode, RESULT_CANCELED, null);
        }
        SafeActivityOptions.abort(options);
        return err;
    }

    // 检查是否有启动Activity的权限
    boolean abort = !mSupervisor.checkStartAnyActivityPermission(intent, aInfo, resultWho,
            requestCode, callingPid, callingUid, callingPackage, ignoreTargetSecurity,
            inTask != null, callerApp, resultRecord, resultStack);
    abort |= !mService.mIntentFirewall.checkStartActivity(intent, callingUid,
            callingPid, resolvedType, aInfo.applicationInfo);

    // Merge the two options bundles, while realCallerOptions takes precedence.
    ActivityOptions checkedOptions = options != null
            ? options.getOptions(intent, aInfo, callerApp, mSupervisor)
            : null;
    if (allowPendingRemoteAnimationRegistryLookup) {
        checkedOptions = mService.getActivityStartController()
                .getPendingRemoteAnimationRegistry()
                .overrideOptionsIfNeeded(callingPackage, checkedOptions);
    }
    // 如果往service中注册有controler,此处为空
    if (mService.mController != null) {
        try {
            Intent watchIntent = intent.cloneFilter();
            abort |= !mService.mController.activityStarting(watchIntent,
                    aInfo.applicationInfo.packageName);
        } catch (RemoteException e) {
            mService.mController = null;
        }
    }
    // 设置拦截状态并尝试拦截;mInterceptor是ActivityStartInterceptor对象
    mInterceptor.setStates(userId, realCallingPid, realCallingUid, startFlags, callingPackage);
    if (mInterceptor.intercept(intent, rInfo, aInfo, resolvedType, inTask, callingPid,
            callingUid, checkedOptions)) {
        // activity start was intercepted, e.g. because the target user is currently in quiet
        // mode (turn off work) or the target application is suspended
        intent = mInterceptor.mIntent;
        rInfo = mInterceptor.mRInfo;
        aInfo = mInterceptor.mAInfo;
        resolvedType = mInterceptor.mResolvedType;
        inTask = mInterceptor.mInTask;
        callingPid = mInterceptor.mCallingPid;
        callingUid = mInterceptor.mCallingUid;
        checkedOptions = mInterceptor.mActivityOptions;
    }

    if (abort) {
        if (resultRecord != null) {
            resultStack.sendActivityResultLocked(-1, resultRecord, resultWho, requestCode,
                    RESULT_CANCELED, null);
        }
        ActivityOptions.abort(checkedOptions);
        return START_ABORTED;
    }

    // 如果需要对权限再进行一次review
    if (mService.mPermissionReviewRequired && aInfo != null) {
        if (mService.getPackageManagerInternalLocked().isPermissionsReviewRequired(
                aInfo.packageName, userId)) {
            IIntentSender target = mService.getIntentSenderLocked(
                    ActivityManager.INTENT_SENDER_ACTIVITY, callingPackage,
                    callingUid, userId, null, null, 0, new Intent[]{intent},
                    new String[]{resolvedType}, PendingIntent.FLAG_CANCEL_CURRENT
                            | PendingIntent.FLAG_ONE_SHOT, null);

            final int flags = intent.getFlags();
            Intent newIntent = new Intent(Intent.ACTION_REVIEW_PERMISSIONS);
            newIntent.setFlags(flags
                    | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
            newIntent.putExtra(Intent.EXTRA_PACKAGE_NAME, aInfo.packageName);
            newIntent.putExtra(Intent.EXTRA_INTENT, new IntentSender(target));
            if (resultRecord != null) {
                newIntent.putExtra(Intent.EXTRA_RESULT_NEEDED, true);
            }
            intent = newIntent;

            resolvedType = null;
            callingUid = realCallingUid;
            callingPid = realCallingPid;

            rInfo = mSupervisor.resolveIntent(intent, resolvedType, userId, 0,
                    computeResolveFilterUid(
                            callingUid, realCallingUid, mRequest.filterCallingUid));
            aInfo = mSupervisor.resolveActivity(intent, rInfo, startFlags,
                    null /*profilerInfo*/);

            if (DEBUG_PERMISSIONS_REVIEW) {
                Slog.i(TAG, "START u" + userId + " {" + intent.toShortString(true, true,
                        true, false) + "} from uid " + callingUid + " on display "
                        + (mSupervisor.mFocusedStack == null
                        ? DEFAULT_DISPLAY : mSupervisor.mFocusedStack.mDisplayId));
            }
        }
    }

    // 如果有对应的快应用,这里会启动快应用安装,并启动对应的快应用
    if (rInfo != null && rInfo.auxiliaryInfo != null) {
        intent = createLaunchIntent(rInfo.auxiliaryInfo, ephemeralIntent,
                callingPackage, verificationBundle, resolvedType, userId);
        resolvedType = null;
        callingUid = realCallingUid;
        callingPid = realCallingPid;

        aInfo = mSupervisor.resolveActivity(intent, rInfo, startFlags, null /*profilerInfo*/);
    }

    // 创建要启动Activity的ActivityRecord对象
    ActivityRecord r = new ActivityRecord(mService, callerApp, callingPid, callingUid,
            callingPackage, intent, resolvedType, aInfo, mService.getGlobalConfiguration(),
            resultRecord, resultWho, requestCode, componentSpecified, voiceSession != null,
            mSupervisor, checkedOptions, sourceRecord);
    if (outActivity != null) {
        outActivity[0] = r;
    }

    if (r.appTimeTracker == null && sourceRecord != null) {
        r.appTimeTracker = sourceRecord.appTimeTracker;
    }

    final ActivityStack stack = mSupervisor.mFocusedStack;

    // 如果准备启动的Activity和准备resumed的Activity不是来自相同的uid的,这里需要检查是否允许切换
    if (voiceSession == null && (stack.getResumedActivity() == null
            || stack.getResumedActivity().info.applicationInfo.uid != realCallingUid)) {
        if (!mService.checkAppSwitchAllowedLocked(callingPid, callingUid,
                realCallingPid, realCallingUid, "Activity start")) {
            mController.addPendingActivityLaunch(new PendingActivityLaunch(r,
                    sourceRecord, startFlags, stack, callerApp));
            ActivityOptions.abort(checkedOptions);
            return ActivityManager.START_SWITCHES_CANCELED;
        }
    }

    if (mService.mDidAppSwitch) {
        mService.mAppSwitchesAllowedTime = 0;
    } else {
        mService.mDidAppSwitch = true;
    }

    mController.doPendingActivityLaunches(false);

    maybeLogActivityStart(callingUid, callingPackage, realCallingUid, intent, callerApp, r,
            originatingPendingIntent);

    // 调用参数更少的startActivity方法
    return startActivity(r, sourceRecord, voiceSession, voiceInteractor, startFlags,
            true /* doResume */, checkedOptions, inTask, outActivity);
}

上面的代码已经写得很详细了(就是博主能理解的部分都写上去了),值得注意的是FLAG_ACTIVITY_FORWARD_RESULT这个标签,以前只是知道有这个标签,现在看代码可以知道FLAG_ACTIVITY_FORWARD_RESULT是怎么处理的。接下来继续看看startActivity

private int startActivity(final ActivityRecord r, ActivityRecord sourceRecord,
            IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
            int startFlags, boolean doResume, ActivityOptions options, TaskRecord inTask,
            ActivityRecord[] outActivity) {
    int result = START_CANCELED;
    try {
        mService.mWindowManager.deferSurfaceLayout();
        // 调用startActivityUnchecked方法,下面进行分析
        result = startActivityUnchecked(r, sourceRecord, voiceSession, voiceInteractor,
                startFlags, doResume, options, inTask, outActivity);
    } finally {
        final ActivityStack stack = mStartActivity.getStack();
        if (!ActivityManager.isStartResultSuccessful(result) && stack != null) {
            stack.finishActivityLocked(mStartActivity, RESULT_CANCELED,
                    null /* intentResultData */, "startActivity", true /* oomAdj */);
        }
        mService.mWindowManager.continueSurfaceLayout();
    }

    postStartActivityProcessing(r, result, mTargetStack);

    return result;
}

private int startActivityUnchecked(final ActivityRecord r, ActivityRecord sourceRecord,
        IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
        int startFlags, boolean doResume, ActivityOptions options, TaskRecord inTask,
        ActivityRecord[] outActivity) {

    // 设置初始状态
    setInitialState(r, options, inTask, doResume, startFlags, sourceRecord, voiceSession,
            voiceInteractor);

    computeLaunchingTaskFlags();
    computeSourceStack();
    mIntent.setFlags(mLaunchFlags);

    // 查找可复用的Activity
    ActivityRecord reusedActivity = getReusableIntentActivity();

    ..........................

    // 如果可复用的Activity不为空
    if (reusedActivity != null) {
        ..........................
        // mStartActivity是在setInitialState方法中赋值的,指向的是被启动Activity对象封装,
        // 如果是第一次启动那么它的任务栈就不存在,此时先默认设置成启动Activity的任务栈。
        if (mStartActivity.getTask() == null && !clearTopAndResetStandardLaunchMode) {
            mStartActivity.setTask(reusedActivity.getTask());
        }

         .......................
           
        // 如果设置了FLAG_ACTIVITY_CLEAR_TOP
        // 或者Activity设置了SingleInstance或者SingleTask模式走这里
        if ((mLaunchFlags & FLAG_ACTIVITY_CLEAR_TOP) != 0
                || isDocumentLaunchesIntoExisting(mLaunchFlags)
                || isLaunchModeOneOf(LAUNCH_SINGLE_INSTANCE, LAUNCH_SINGLE_TASK)) {
            final TaskRecord task = reusedActivity.getTask();

            // 清理栈,获取所需要的Activity
            final ActivityRecord top = task.performClearTaskForReuseLocked(mStartActivity,
                    mLaunchFlags);

            if (reusedActivity.getTask() == null) {
                reusedActivity.setTask(task);
            }

            if (top != null) {
                if (top.frontOfTask) {
                    top.getTask().setIntent(mStartActivity);
                }
                deliverNewIntent(top);
            }
        }

        mSupervisor.sendPowerHintForLaunchStartIfNeeded(false /* forceSend */, reusedActivity);

        // 将可复用的Activity移到栈顶,下面接着分析这个方法
        reusedActivity = setTargetStackAndMoveToFrontIfNeeded(reusedActivity);

        final ActivityRecord outResult =
                outActivity != null && outActivity.length > 0 ? outActivity[0] : null;

        if (outResult != null && (outResult.finishing || outResult.noDisplay)) {
            outActivity[0] = reusedActivity;
        }

        if ((mStartFlags & START_FLAG_ONLY_IF_NEEDED) != 0) {
            resumeTargetStackIfNeeded();
            return START_RETURN_INTENT_TO_CALLER;
        }

        if (reusedActivity != null) {
            setTaskFromIntentActivity(reusedActivity);


            // 如果不需要添加到任务栈,并且复用TaskRecord为空,说明没有启动一个新的Activity
            // mAddingToTask为false表示要为目标Activity组件创建一个专属任务,事实上函数会检查这个专属
            // 任务是否存在,如果已存在,那么就会将变量mAddingToTask的值设置为true
            if (!mAddingToTask && mReuseTask == null) {
                resumeTargetStackIfNeeded();
                if (outActivity != null && outActivity.length > 0) {
                    outActivity[0] = reusedActivity;
                }

                return mMovedToFront ? START_TASK_TO_FRONT : START_DELIVERED_TO_TOP;
            }
        }
    }

    // 这里处理找不到对应的类的情况
    if (mStartActivity.packageName == null) {
        final ActivityStack sourceStack = mStartActivity.resultTo != null
                ? mStartActivity.resultTo.getStack() : null;
        if (sourceStack != null) {
            sourceStack.sendActivityResultLocked(-1 /* callingUid */, mStartActivity.resultTo,
                    mStartActivity.resultWho, mStartActivity.requestCode, RESULT_CANCELED,
                    null /* data */);
        }
        ActivityOptions.abort(mOptions);
        return START_CLASS_NOT_FOUND;
    }

    final ActivityStack topStack = mSupervisor.mFocusedStack;
    final ActivityRecord topFocused = topStack.getTopActivity();
    final ActivityRecord top = topStack.topRunningNonDelayedActivityLocked(mNotTop);
    // 判断是否启动
    final boolean dontStart = top != null && mStartActivity.resultTo == null
            && top.realActivity.equals(mStartActivity.realActivity)
            && top.userId == mStartActivity.userId
            && top.app != null && top.app.thread != null
            && ((mLaunchFlags & FLAG_ACTIVITY_SINGLE_TOP) != 0
            || isLaunchModeOneOf(LAUNCH_SINGLE_TOP, LAUNCH_SINGLE_TASK));
    // 如果不启动
    if (dontStart) {
        topStack.mLastPausedActivity = null;
        if (mDoResume) {
            // 恢复原来最顶端的Activity
            mSupervisor.resumeFocusedStackTopActivityLocked();
        }
        ActivityOptions.abort(mOptions);
        if ((mStartFlags & START_FLAG_ONLY_IF_NEEDED) != 0) {
            return START_RETURN_INTENT_TO_CALLER;
        }

        deliverNewIntent(top);

        mSupervisor.handleNonResizableTaskIfNeeded(top.getTask(), preferredWindowingMode,
                preferredLaunchDisplayId, topStack);

        // 需要启动的Activity在栈顶
        return START_DELIVERED_TO_TOP;
    }

    boolean newTask = false;
    // Activity组件中有一个android:taskAffinity属性,用来描述它的一个专属任务,当AMS决定要将目标
    // Activity运行在一个不同的任务中时,AMS就会检查目标Activity组件的专属任务是否已经存在,如果存
    // 在,那么AMS就会直接将目标Activity组件添加到它里面运行,否则,就会先创建这个专属任务,然后将目
    // 标Activity组件添加到它里面去运行
    final TaskRecord taskToAffiliate = (mLaunchTaskBehind && mSourceRecord != null)
            ? mSourceRecord.getTask() : null;

    int result = START_SUCCESS;
    // 判断是否需要新创建一个Task
    if (mStartActivity.resultTo == null && mInTask == null && !mAddingToTask
            && (mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0) {
        newTask = true;
        result = setTaskFromReuseOrCreateNewTask(taskToAffiliate, topStack);
    } else if (mSourceRecord != null) {
        result = setTaskFromSourceRecord();
    } else if (mInTask != null) {
        result = setTaskFromInTask();
    } else {

        setTaskToCurrentTopOrCreateNewTask();
    }
    if (result != START_SUCCESS) {
        return result;
    }

    mService.grantUriPermissionFromIntentLocked(mCallingUid, mStartActivity.packageName,
            mIntent, mStartActivity.getUriPermissionsLocked(), mStartActivity.userId);
    mService.grantEphemeralAccessLocked(mStartActivity.userId, mIntent,
            mStartActivity.appInfo.uid, UserHandle.getAppId(mCallingUid));
    if (newTask) {
        EventLog.writeEvent(EventLogTags.AM_CREATE_TASK, mStartActivity.userId,
                mStartActivity.getTask().taskId);
    }
    ActivityStack.logStartActivity(
            EventLogTags.AM_CREATE_ACTIVITY, mStartActivity, mStartActivity.getTask());
    mTargetStack.mLastPausedActivity = null;

    mSupervisor.sendPowerHintForLaunchStartIfNeeded(false /* forceSend */, mStartActivity);

    // 调用startActivityLocked,这个方法貌似主要就是准备界面描绘的容器
    // 并通知WindowManager进行界面切换
    mTargetStack.startActivityLocked(mStartActivity, topFocused, newTask, mKeepCurTransition,
            mOptions);
    if (mDoResume) {
        final ActivityRecord topTaskActivity =
                mStartActivity.getTask().topRunningActivityLocked();
        if (!mTargetStack.isFocusable()
                || (topTaskActivity != null && topTaskActivity.mTaskOverlay
                && mStartActivity != topTaskActivity)) {

            mTargetStack.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);

            mService.mWindowManager.executeAppTransition();
        } else {

            if (mTargetStack.isFocusable() && !mSupervisor.isFocusedStack(mTargetStack)) {
                mTargetStack.moveToFront("startActivityUnchecked");
            }
            mSupervisor.resumeFocusedStackTopActivityLocked(mTargetStack, mStartActivity,
                    mOptions);
        }
    } else if (mStartActivity != null) {
        mSupervisor.mRecentTasks.add(mStartActivity.getTask());
    }
    mSupervisor.updateUserStackLocked(mStartActivity.userId, mTargetStack);

    mSupervisor.handleNonResizableTaskIfNeeded(mStartActivity.getTask(), preferredWindowingMode,
            preferredLaunchDisplayId, mTargetStack);

    return START_SUCCESS;
}

上面的代码中间会调用到setTargetStackAndMoveToFrontIfNeeded方法对栈进行调整,我们接着分析这个方法

private ActivityRecord setTargetStackAndMoveToFrontIfNeeded(ActivityRecord intentActivity) {
    mTargetStack = intentActivity.getStack();
    mTargetStack.mLastPausedActivity = null;
    
    final ActivityStack focusStack = mSupervisor.getFocusedStack();
    // 获取焦点栈中最上面的非延迟Activity
    ActivityRecord curTop = (focusStack == null)
            ? null : focusStack.topRunningNonDelayedActivityLocked(mNotTop);

    // 获取上述Activity所在的Task
    final TaskRecord topTask = curTop != null ? curTop.getTask() : null;
    // 三个条件:1. 存在上面说的Activity;2. 而且该Activity和要启动的Activity不在同一个Task中,
    // 或者该Activity不在焦点栈的栈顶;3. 目标Activity需要移动到栈顶
    if (topTask != null
            && (topTask != intentActivity.getTask() || topTask != focusStack.topTask())
            && !mAvoidMoveToFront) {
        mStartActivity.intent.addFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT);
        // 源Activity不存在,或者
        // 源Activity所在栈存在顶部Activity,并且该顶部Activity和源Activity不在同一个任务中
        if (mSourceRecord == null || (mSourceStack.getTopActivity() != null &&
                mSourceStack.getTopActivity().getTask() == mSourceRecord.getTask())) {
            if (mLaunchTaskBehind && mSourceRecord != null) {
                intentActivity.setTaskToAffiliateWith(mSourceRecord.getTask());
            }

            // 判断是否需要清理任务栈
            final boolean willClearTask =
                    (mLaunchFlags & (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK))
                        == (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK);
            // 如果不需要清理
            if (!willClearTask) {
                // 获取启动的Activity栈
                final ActivityStack launchStack = getLaunchStack(
                        mStartActivity, mLaunchFlags, mStartActivity.getTask(), mOptions);
                // 获取启动Activity所在的TaskRecord
                final TaskRecord intentTask = intentActivity.getTask();
                if (launchStack == null || launchStack == mTargetStack) {
                    // 讲启动的Activity移动到最顶端显示
                    mTargetStack.moveTaskToFrontLocked(intentTask, mNoAnimation, mOptions,
                            mStartActivity.appTimeTracker, "bringingFoundTaskToFront");
                    mMovedToFront = true;
                // 如果是分屏模式,这里略过
                } else if (launchStack.inSplitScreenWindowingMode()) {
                    .....................................
                // 这里判断启动的Activity显示在外接的显示设备上,这里略过
                } else if (launchStack.mDisplayId != mTargetStack.mDisplayId) {
                    .....................................
                } else if (launchStack.isActivityTypeHome()
                        && !mTargetStack.isActivityTypeHome()) {
                    ....................................
                }
                mOptions = null;

                // 显示启动窗口
                intentActivity.showStartingWindow(null /* prev */, false /* newTask */,
                        true /* taskSwitch */);
            }
        }
    }
    // 更新启动Activity的任务栈
    mTargetStack = intentActivity.getStack();
    if (!mMovedToFront && mDoResume) {
        if (DEBUG_TASKS) Slog.d(TAG_TASKS, "Bring to front target: " + mTargetStack
                + " from " + intentActivity);
        mTargetStack.moveToFront("intentActivityFound");
    }

    // 处理需要resize的情况
    mSupervisor.handleNonResizableTaskIfNeeded(intentActivity.getTask(),
            WINDOWING_MODE_UNDEFINED, DEFAULT_DISPLAY, mTargetStack);

    // If the caller has requested that the target task be reset, then do so.
    if ((mLaunchFlags & FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) != 0) {
        return mTargetStack.resetTaskIfNeededLocked(intentActivity, mStartActivity);
    }
    return intentActivity;
}

  这上面和我们的目的(startActivity启动Activity到调用Activity的onCreate)相关联的应该就是moveTaskToFrontLocked方法了。moveTaskToFrontLocked方法可以讲Activity所在的任务调到前台,在任务调用前台后Activity才有机会调用起onCreate方法进行显示,下面接着贴代码分析:

final void moveTaskToFrontLocked(TaskRecord tr, boolean noAnimation, ActivityOptions options,
        AppTimeTracker timeTracker, String reason) {
    if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "moveTaskToFront: " + tr);

    // 获取顶部Activity的相关信息
    final ActivityStack topStack = getDisplay().getTopStack();
    final ActivityRecord topActivity = topStack != null ? topStack.getTopActivity() : null;
    final int numTasks = mTaskHistory.size();
    final int index = mTaskHistory.indexOf(tr);
    
    .......................

    try {
        getDisplay().deferUpdateImeTarget();

        // 讲任务插入到顶部
        insertTaskAtTop(tr, null);

        // Don't refocus if invisible to current user
        final ActivityRecord top = tr.getTopActivity();
        if (top == null || !top.okToShowLocked()) {
            if (top != null) {
                mStackSupervisor.mRecentTasks.add(top.getTask());
            }
            ActivityOptions.abort(options);
            return;
        }

        // 讲焦点设置为当前栈中顶部正在运行的Activity
        final ActivityRecord r = topRunningActivityLocked();
        mStackSupervisor.moveFocusableActivityStackToFrontLocked(r, reason);

        .................
        // 下面我们接着分析这个方法
        mStackSupervisor.resumeFocusedStackTopActivityLocked();
        EventLog.writeEvent(EventLogTags.AM_TASK_TO_FRONT, tr.userId, tr.taskId);

        mService.mTaskChangeNotificationController.notifyTaskMovedToFront(tr.taskId);
    } finally {
        getDisplay().continueUpdateImeTarget();
    }
}

上面没什么好说的,主要是调整Activity栈中Activity的位置,接着分析resumeFocusedStackTopActivityLocked方法

// 无参方法
boolean resumeFocusedStackTopActivityLocked() {
    return resumeFocusedStackTopActivityLocked(null, null, null);
}

// 传递三个参数都为null
boolean resumeFocusedStackTopActivityLocked(
        ActivityStack targetStack, ActivityRecord target, ActivityOptions targetOptions) {

    if (!readyToResume()) {
        return false;
    }

    // tgargetStack为null,忽略
    if (targetStack != null && isFocusedStack(targetStack)) {
        return targetStack.resumeTopActivityUncheckedLocked(target, targetOptions);
    }

    final ActivityRecord r = mFocusedStack.topRunningActivityLocked();
    // 如果目标栈不存在或者没有在聚焦状态,则从聚焦栈中取出栈顶的Activity
    // resumeTopActivityUncheckedLocked下面接着分析
    if (r == null || !r.isState(RESUMED)) {
        mFocusedStack.resumeTopActivityUncheckedLocked(null, null);
    } else if (r.isState(RESUMED)) {
        // Kick off any lingering app transitions form the MoveTaskToFront operation.
        mFocusedStack.executeAppTransition(targetOptions);
    }

    return false;
}

// 上面可以知道传递的两个参数都为null
boolean resumeTopActivityUncheckedLocked(ActivityRecord prev, ActivityOptions options) {
    if (mStackSupervisor.inResumeTopActivity) {
        // Don't even start recursing.
        return false;
    }

    boolean result = false;
    try {
        // 设置顶部Activity的状态
        mStackSupervisor.inResumeTopActivity = true;
        // 调用resumeTopActivityInnerLocked进行resume
        result = resumeTopActivityInnerLocked(prev, options);

        final ActivityRecord next = topRunningActivityLocked(true /* focusableOnly */);
        if (next == null || !next.canTurnScreenOn()) {
            checkReadyForSleep();
        }
    } finally {
        mStackSupervisor.inResumeTopActivity = false;
    }

    return result;
}

resumeTopActivityInnerLocked的内容比较多,需要集中精神慢慢分析:

private boolean resumeTopActivityInnerLocked(ActivityRecord prev, ActivityOptions options) {
    if (!mService.mBooting && !mService.mBooted) {
        // Not ready yet!
        return false;
    }

    // 前面我们把要启动的Activity放置在当前Activity组件堆栈的顶端,并且它是正在等待启动的,即它不是
    // 处于结束状态的,因此next就指向了我们将要启动的Activity组件
    final ActivityRecord next = topRunningActivityLocked(true /* focusableOnly */);

    final boolean hasRunningActivity = next != null;

    // 有需要启动的组件,但是没有Attach到进程中
    if (hasRunningActivity && !isAttached()) {
        return false;
    }

    mStackSupervisor.cancelInitializingActivities();

    boolean userLeaving = mStackSupervisor.mUserLeaving;
    mStackSupervisor.mUserLeaving = false;

    // 不存在要启动的Activity
    if (!hasRunningActivity) {
        return resumeTopActivityInNextFocusableStack(prev, options, "noMoreActivities");
    }

    next.delayedResume = false;

    // 如果正在Resume的Activity就是我们要启动的Activity
    // 而且要启动的Activity已经resume完成
    if (mResumedActivity == next && next.isState(RESUMED)
            && mStackSupervisor.allResumedActivitiesComplete()) {
        executeAppTransition(options);
        if (DEBUG_STATES) Slog.d(TAG_STATES,
                "resumeTopActivityLocked: Top activity resumed " + next);
        if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
        return false;
    }

    if (shouldSleepOrShutDownActivities()
            && mLastPausedActivity == next
            && mStackSupervisor.allPausedActivitiesComplete()) {
        executeAppTransition(options);
        if (DEBUG_STATES) Slog.d(TAG_STATES,
                "resumeTopActivityLocked: Going to sleep and all paused");
        if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
        return false;
    }

    // 这里需要确保启动拥有该Activity的用户已经启动
    if (!mService.mUserController.hasStartedUserState(next.userId)) {
        Slog.w(TAG, "Skipping resume of top activity " + next
                + ": user " + next.userId + " is stopped");
        if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
        return false;
    }

    // 如果要启动的Activity可能正在等到stop,但是如果代码走到这里
    // 代表其已经不能再stop了
    mStackSupervisor.mStoppingActivities.remove(next);
    mStackSupervisor.mGoingToSleepActivities.remove(next);
    next.sleeping = false;
    mStackSupervisor.mActivitiesWaitingForVisibleActivity.remove(next);

    if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Resuming " + next);

    // 如果正在暂停一个Activity,我们需要等待其完成
    if (!mStackSupervisor.allPausedActivitiesComplete()) {
        if (DEBUG_SWITCH || DEBUG_PAUSE || DEBUG_STATES) Slog.v(TAG_PAUSE,
                "resumeTopActivityLocked: Skip resume: some activity pausing.");
        if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
        return false;
    }

    // 设置Activity加载相关资源  
    mStackSupervisor.setLaunchSource(next.info.applicationInfo.uid);

    // 这部分代码不涉及,暂不考虑
    boolean lastResumedCanPip = false;
    ActivityRecord lastResumed = null;
    final ActivityStack lastFocusedStack = mStackSupervisor.getLastStack();
    if (lastFocusedStack != null && lastFocusedStack != this) {
        ......................
    }

    // 如果设置了RESUME_WHILE_PAUSING标志位,在resume正在resume的Activity的同时需要将
    // 前一个Activity暂停
    final boolean resumeWhilePausing = (next.info.flags & FLAG_RESUME_WHILE_PAUSING) != 0
            && !lastResumedCanPip;

    // 处理需要暂停运行的Activity
    boolean pausing = mStackSupervisor.pauseBackStacks(userLeaving, next, false);
    if (mResumedActivity != null) {
        if (DEBUG_STATES) Slog.d(TAG_STATES,
                "resumeTopActivityLocked: Pausing " + mResumedActivity);
        pausing |= startPausingLocked(userLeaving, false, next, false);
    }
    .............................................

    // 如果最近的Activity设置了不加入到历史记录中
    // 而且设备准备进入休眠状态,需要讲该Activity停止并finish
    if (shouldSleepActivities() && mLastNoHistoryActivity != null &&
            !mLastNoHistoryActivity.finishing) {
        if (DEBUG_STATES) Slog.d(TAG_STATES,
                "no-history finish of " + mLastNoHistoryActivity + " on new resume");
        requestFinishActivityLocked(mLastNoHistoryActivity.appToken, Activity.RESULT_CANCELED,
                null, "resume-no-history", false);
        mLastNoHistoryActivity = null;
    }

    if (prev != null && prev != next) {
        if (!mStackSupervisor.mActivitiesWaitingForVisibleActivity.contains(prev)
                && next != null && !next.nowVisible) {
            // 等待Activity可见
            mStackSupervisor.mActivitiesWaitingForVisibleActivity.add(prev);
            if (DEBUG_SWITCH) Slog.v(TAG_SWITCH,
                    "Resuming top, waiting visible to hide: " + prev);
        } else {
            // 下一个Activity已经准备好可见了,并且前一个Activity已经已经结束
            // 需要讲上一个Activity设置为不可见
            if (prev.finishing) {
                prev.setVisibility(false);
                if (DEBUG_SWITCH) Slog.v(TAG_SWITCH,
                        "Not waiting for visible to hide: " + prev + ", waitingVisible="
                        + mStackSupervisor.mActivitiesWaitingForVisibleActivity.contains(prev)
                        + ", nowVisible=" + next.nowVisible);
            } else {
                if (DEBUG_SWITCH) Slog.v(TAG_SWITCH,
                        "Previous already visible but still waiting to hide: " + prev
                        + ", waitingVisible="
                        + mStackSupervisor.mActivitiesWaitingForVisibleActivity.contains(prev)
                        + ", nowVisible=" + next.nowVisible);
            }
        }
    }

    // 加载应用的Activity
    try {
        AppGlobals.getPackageManager().setPackageStoppedState(
                next.packageName, false, next.userId); /* TODO: Verify if correct userid */
    } catch (RemoteException e1) {
    } catch (IllegalArgumentException e) {
        Slog.w(TAG, "Failed trying to unstop package "
                + next.packageName + ": " + e);
    }

    // 告诉WindowManager前一个Activity可以设置为不可见
    boolean anim = true;
    if (prev != null) {
        if (prev.finishing) {
            if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION,
                    "Prepare close transition: prev=" + prev);
            if (mStackSupervisor.mNoAnimActivities.contains(prev)) {
                anim = false;
                mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
            } else {
                mWindowManager.prepareAppTransition(prev.getTask() == next.getTask()
                        ? TRANSIT_ACTIVITY_CLOSE
                        : TRANSIT_TASK_CLOSE, false);
            }
            prev.setVisibility(false);
        } else {
            if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION,
                    "Prepare open transition: prev=" + prev);
            if (mStackSupervisor.mNoAnimActivities.contains(next)) {
                anim = false;
                mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
            } else {
                mWindowManager.prepareAppTransition(prev.getTask() == next.getTask()
                        ? TRANSIT_ACTIVITY_OPEN
                        : next.mLaunchTaskBehind
                                ? TRANSIT_TASK_OPEN_BEHIND
                                : TRANSIT_TASK_OPEN, false);
            }
        }
    } else {
        if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION, "Prepare open transition: no previous");
        if (mStackSupervisor.mNoAnimActivities.contains(next)) {
            anim = false;
            mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
        } else {
            mWindowManager.prepareAppTransition(TRANSIT_ACTIVITY_OPEN, false);
        }
    }

    // 过渡动画
    if (anim) {
        next.applyOptionsLocked();
    } else {
        next.clearOptionsLocked();
    }

    mStackSupervisor.mNoAnimActivities.clear();

    ActivityStack lastStack = mStackSupervisor.getLastStack();
    // 如果Activity所在进程已经启动,我们这里应用是冷启动,所以不走这里
    if (next.app != null && next.app.thread != null) {
        ...............
    } else {
        if (!next.hasBeenLaunched) {
            next.hasBeenLaunched = true;
        } else {
            if (SHOW_APP_STARTING_PREVIEW) {
                next.showStartingWindow(null /* prev */, false /* newTask */,
                        false /* taskSwich */);
            }
            if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Restarting: " + next);
        }
        if (DEBUG_STATES) Slog.d(TAG_STATES, "resumeTopActivityLocked: Restarting " + next);
        // 应用冷启动,需要创建对应的进程
        mStackSupervisor.startSpecificActivityLocked(next, true, true);
    }

    if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
    return true;
}

  上面开始分析到需要通过startSpecificActivityLocked来进行进程的冷启动,下一篇我们会继续分析进程创建过程。

Advertisements
Advertisements
Advertisements

发表评论

电子邮件地址不会被公开。 必填项已用*标注

此站点使用Akismet来减少垃圾评论。了解我们如何处理您的评论数据

%d 博主赞过: