Do not try to restore a task id if it does not exist.

Previously, we were trying to restore the recent task regardless of
if it was found in recents or a stack. This would lead to
referencing a null object later.

Change-Id: I014a751d3254ad267c32ac0b54783b31b8d17e93
Test: bit FrameworksServicesTests:com.android.server.am.ActivityStackSupervisorTests
Fixes: 36688598
This commit is contained in:
Bryce Lee
2017-04-03 08:33:11 -07:00
parent d2778f32e2
commit 92b7b65939
2 changed files with 65 additions and 5 deletions

View File

@@ -745,7 +745,7 @@ public class ActivityStackSupervisor extends ConfigurationContainer implements D
}
/**
* Returns a {@link TaskRecord} for the input id if available. Null otherwise.
* Returns a {@link TaskRecord} for the input id if available. {@code null} otherwise.
* @param id Id of the task we would like returned.
* @param matchMode The mode to match the given task id in.
* @param stackId The stack to restore the task to (default launch stack will be used if
@@ -765,7 +765,7 @@ public class ActivityStackSupervisor extends ConfigurationContainer implements D
ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks;
for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) {
ActivityStack stack = stacks.get(stackNdx);
TaskRecord task = stack.taskForIdLocked(id);
final TaskRecord task = stack.taskForIdLocked(id);
if (task != null) {
return task;
}
@@ -780,11 +780,17 @@ public class ActivityStackSupervisor extends ConfigurationContainer implements D
// Otherwise, check the recent tasks and return if we find it there and we are not restoring
// the task from recents
if (DEBUG_RECENTS) Slog.v(TAG_RECENTS, "Looking for task id=" + id + " in recents");
TaskRecord task = mRecentTasks.taskForIdLocked(id);
if (matchMode == MATCH_TASK_IN_STACKS_OR_RECENT_TASKS) {
if (DEBUG_RECENTS && task == null) {
final TaskRecord task = mRecentTasks.taskForIdLocked(id);
if (task == null) {
if (DEBUG_RECENTS) {
Slog.d(TAG_RECENTS, "\tDidn't find task id=" + id + " in recents");
}
return null;
}
if (matchMode == MATCH_TASK_IN_STACKS_OR_RECENT_TASKS) {
return task;
}

View File

@@ -0,0 +1,54 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License
*/
package com.android.server.am;
import static org.junit.Assert.assertNull;
import android.os.Debug;
import android.platform.test.annotations.Presubmit;
import android.support.test.filters.MediumTest;
import android.support.test.runner.AndroidJUnit4;
import org.junit.runner.RunWith;
import org.junit.Test;
import static com.android.server.am.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_OR_RECENT_TASKS_AND_RESTORE;
/**
* Tests for the {@link ActivityStackSupervisor} class.
*
* Build/Install/Run:
* bit FrameworksServicesTests:com.android.server.am.ActivityStackSupervisorTests
*/
@MediumTest
@Presubmit
@RunWith(AndroidJUnit4.class)
public class ActivityStackSupervisorTests extends ActivityTestsBase {
/**
* This test ensures that we do not try to restore a task based off an invalid task id. The
* stack supervisor is a test version so there will be no tasks present. We should expect
* {@code null} to be returned in this case.
*/
@Test
public void testRestoringInvalidTask() throws Exception {
Debug.waitForDebugger();
final ActivityManagerService service = createActivityManagerService();
TaskRecord task = service.mStackSupervisor.anyTaskForIdLocked(0 /*taskId*/,
MATCH_TASK_IN_STACKS_OR_RECENT_TASKS_AND_RESTORE, 0 /*stackId*/);
assertNull(task);
}
}