Merge "Allow starting activity for result on another TaskFragment" into tm-qpr-dev am: c1108902cd
Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/20554413 Change-Id: I9b3162c692096659c9489c5b3bff1f4e2c0133c0 Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
This commit is contained in:
@@ -3327,9 +3327,17 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
|
||||
mAtmService.mUgmInternal.grantUriPermissionUncheckedFromIntent(resultGrants,
|
||||
resultTo.getUriPermissionsLocked());
|
||||
}
|
||||
if (mForceSendResultForMediaProjection) {
|
||||
resultTo.sendResult(this.getUid(), resultWho, requestCode, resultCode,
|
||||
resultData, resultGrants, true /* forceSendForMediaProjection */);
|
||||
if (mForceSendResultForMediaProjection || resultTo.isState(RESUMED)) {
|
||||
// Sending the result to the resultTo activity asynchronously to prevent the
|
||||
// resultTo activity getting results before this Activity paused.
|
||||
final ActivityRecord resultToActivity = resultTo;
|
||||
mAtmService.mH.post(() -> {
|
||||
synchronized (mAtmService.mGlobalLock) {
|
||||
resultToActivity.sendResult(this.getUid(), resultWho, requestCode,
|
||||
resultCode, resultData, resultGrants,
|
||||
mForceSendResultForMediaProjection);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
resultTo.addResultLocked(this, resultWho, requestCode, resultCode, resultData);
|
||||
}
|
||||
@@ -4640,7 +4648,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
|
||||
false /* forceSendForMediaProjection */);
|
||||
}
|
||||
|
||||
private void sendResult(int callingUid, String resultWho, int requestCode, int resultCode,
|
||||
void sendResult(int callingUid, String resultWho, int requestCode, int resultCode,
|
||||
Intent data, NeededUriGrants dataGrants, boolean forceSendForMediaProjection) {
|
||||
if (callingUid > 0) {
|
||||
mAtmService.mUgmInternal.grantUriPermissionUncheckedFromIntent(dataGrants,
|
||||
|
||||
@@ -80,7 +80,6 @@ import static com.android.server.wm.Task.REPARENT_MOVE_ROOT_TASK_TO_FRONT;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_ALLOWED;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_MIN_DIMENSION_VIOLATION;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_NEW_TASK;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_UNTRUSTED_HOST;
|
||||
import static com.android.server.wm.WindowContainer.POSITION_TOP;
|
||||
|
||||
@@ -2799,11 +2798,6 @@ class ActivityStarter {
|
||||
errMsg = "The app:" + mCallingUid + "is not trusted to " + mStartActivity;
|
||||
break;
|
||||
}
|
||||
case EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT: {
|
||||
errMsg = "Cannot embed activity across TaskFragments for result, resultTo: "
|
||||
+ mStartActivity.resultTo;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
errMsg = "Unhandled embed result:" + result;
|
||||
}
|
||||
|
||||
@@ -170,13 +170,6 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
* indicate that an Activity can't be embedded because the Activity is started on a new task.
|
||||
*/
|
||||
static final int EMBEDDING_DISALLOWED_NEW_TASK = 3;
|
||||
/**
|
||||
* An embedding check result of
|
||||
* {@link ActivityStarter#canEmbedActivity(TaskFragment, ActivityRecord, Task)}:
|
||||
* indicate that an Activity can't be embedded because the Activity is started on a new
|
||||
* TaskFragment, e.g. start an Activity on a new TaskFragment for result.
|
||||
*/
|
||||
static final int EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT = 4;
|
||||
|
||||
/**
|
||||
* Embedding check results of {@link #isAllowedToEmbedActivity(ActivityRecord)} or
|
||||
@@ -187,7 +180,6 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
EMBEDDING_DISALLOWED_UNTRUSTED_HOST,
|
||||
EMBEDDING_DISALLOWED_MIN_DIMENSION_VIOLATION,
|
||||
EMBEDDING_DISALLOWED_NEW_TASK,
|
||||
EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT,
|
||||
})
|
||||
@interface EmbeddingCheckResult {}
|
||||
|
||||
@@ -614,14 +606,6 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
return EMBEDDING_DISALLOWED_MIN_DIMENSION_VIOLATION;
|
||||
}
|
||||
|
||||
// Cannot embed activity across TaskFragments for activity result.
|
||||
// If the activity that started for result is finishing, it's likely that this start mode
|
||||
// is used to place an activity in the same task. Since the finishing activity won't be
|
||||
// able to get the results, so it's OK to embed in a different TaskFragment.
|
||||
if (a.resultTo != null && !a.resultTo.finishing && a.resultTo.getTaskFragment() != this) {
|
||||
return EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT;
|
||||
}
|
||||
|
||||
return EMBEDDING_ALLOWED;
|
||||
}
|
||||
|
||||
|
||||
@@ -1206,6 +1206,25 @@ public class ActivityRecordTests extends WindowTestsBase {
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFinishActivityIfPossible_sendResultImmediatelyIfResumed() {
|
||||
final Task task = new TaskBuilder(mSupervisor).build();
|
||||
final TaskFragment taskFragment1 = createTaskFragmentWithParentTask(task);
|
||||
final TaskFragment taskFragment2 = createTaskFragmentWithParentTask(task);
|
||||
final ActivityRecord resultToActivity = taskFragment1.getTopMostActivity();
|
||||
final ActivityRecord targetActivity = taskFragment2.getTopMostActivity();
|
||||
resultToActivity.setState(RESUMED, "test");
|
||||
targetActivity.setState(RESUMED, "test");
|
||||
targetActivity.resultTo = resultToActivity;
|
||||
|
||||
clearInvocations(mAtm.getLifecycleManager());
|
||||
targetActivity.finishIfPossible(0, new Intent(), null, "test", false /* oomAdj */);
|
||||
waitUntilHandlersIdle();
|
||||
|
||||
verify(resultToActivity).sendResult(anyInt(), eq(null), anyInt(), anyInt(), any(), eq(null),
|
||||
anyBoolean());
|
||||
}
|
||||
|
||||
/**
|
||||
* Verify that complete finish request for non-finishing activity is invalid.
|
||||
*/
|
||||
|
||||
@@ -24,7 +24,6 @@ import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
|
||||
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
|
||||
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSET;
|
||||
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
|
||||
import static android.os.Process.FIRST_APPLICATION_UID;
|
||||
|
||||
import static com.android.dx.mockito.inline.extended.ExtendedMockito.any;
|
||||
import static com.android.dx.mockito.inline.extended.ExtendedMockito.doNothing;
|
||||
@@ -33,9 +32,7 @@ import static com.android.dx.mockito.inline.extended.ExtendedMockito.never;
|
||||
import static com.android.dx.mockito.inline.extended.ExtendedMockito.spyOn;
|
||||
import static com.android.dx.mockito.inline.extended.ExtendedMockito.verify;
|
||||
import static com.android.server.wm.ActivityRecord.State.RESUMED;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_ALLOWED;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_MIN_DIMENSION_VIOLATION;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT;
|
||||
import static com.android.server.wm.TaskFragment.EMBEDDING_DISALLOWED_UNTRUSTED_HOST;
|
||||
import static com.android.server.wm.WindowContainer.POSITION_TOP;
|
||||
|
||||
@@ -477,23 +474,6 @@ public class TaskFragmentTest extends WindowTestsBase {
|
||||
doReturn(true).when(taskFragment).smallerThanMinDimension(any());
|
||||
assertEquals(EMBEDDING_DISALLOWED_MIN_DIMENSION_VIOLATION,
|
||||
taskFragment.isAllowedToEmbedActivity(activity));
|
||||
|
||||
// Not allow to start activity across TaskFragments for result.
|
||||
final TaskFragment newTaskFragment = new TaskFragmentBuilder(mAtm)
|
||||
.setParentTask(taskFragment.getTask())
|
||||
.build();
|
||||
final ActivityRecord newActivity = new ActivityBuilder(mAtm)
|
||||
.setUid(FIRST_APPLICATION_UID)
|
||||
.build();
|
||||
doReturn(true).when(newTaskFragment).isAllowedToEmbedActivityInTrustedMode(any(), anyInt());
|
||||
doReturn(false).when(newTaskFragment).smallerThanMinDimension(any());
|
||||
newActivity.resultTo = activity;
|
||||
assertEquals(EMBEDDING_DISALLOWED_NEW_TASK_FRAGMENT,
|
||||
newTaskFragment.isAllowedToEmbedActivity(newActivity));
|
||||
|
||||
// Allow embedding if the resultTo activity is finishing.
|
||||
activity.finishing = true;
|
||||
assertEquals(EMBEDDING_ALLOWED, newTaskFragment.isAllowedToEmbedActivity(newActivity));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
Reference in New Issue
Block a user