blob: faf9531f8f2afa76bbacfcf97c4c1d554c4b4d30 [file] [log] [blame]
Wale Ogunwale65ebd952018-04-25 15:41:44 -07001/*
2 * Copyright (C) 2018 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
Wale Ogunwale59507092018-10-29 09:00:30 -070017package com.android.server.wm;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070018
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070019import static android.Manifest.permission.BIND_VOICE_INTERACTION;
20import static android.Manifest.permission.CHANGE_CONFIGURATION;
21import static android.Manifest.permission.CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS;
22import static android.Manifest.permission.INTERNAL_SYSTEM_WINDOW;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070023import static android.Manifest.permission.MANAGE_ACTIVITY_STACKS;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070024import static android.Manifest.permission.READ_FRAME_BUFFER;
25import static android.Manifest.permission.REMOVE_TASKS;
26import static android.Manifest.permission.START_TASKS_FROM_RECENTS;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070027import static android.Manifest.permission.STOP_APP_SWITCHES;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070028import static android.app.ActivityManager.LOCK_TASK_MODE_NONE;
Wale Ogunwalebff2df42018-10-18 17:09:19 -070029import static android.app.ActivityManager.PROCESS_STATE_NONEXISTENT;
Evan Rosky4505b352018-09-06 11:20:40 -070030import static android.app.ActivityManagerInternal.ALLOW_FULL_ONLY;
Yunfan Chen79b96062018-10-17 12:45:23 -070031import static android.app.ActivityTaskManager.INVALID_TASK_ID;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070032import static android.app.ActivityTaskManager.RESIZE_MODE_PRESERVE_WINDOW;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070033import static android.app.ActivityTaskManager.SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT;
34import static android.app.WindowConfiguration.ACTIVITY_TYPE_UNDEFINED;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070035import static android.app.WindowConfiguration.WINDOWING_MODE_FREEFORM;
36import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070037import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED;
38import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070039import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070040import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED;
Wale Ogunwale31913b52018-10-13 08:29:31 -070041import static android.content.Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070042import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
Wale Ogunwale31913b52018-10-13 08:29:31 -070043import static android.content.Intent.FLAG_ACTIVITY_TASK_ON_HOME;
Wale Ogunwale214f3482018-10-04 11:00:47 -070044import static android.content.pm.ApplicationInfo.FLAG_FACTORY_TEST;
Wale Ogunwale342fbe92018-10-09 08:44:10 -070045import static android.content.pm.ConfigurationInfo.GL_ES_VERSION_UNDEFINED;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070046import static android.content.pm.PackageManager.FEATURE_ACTIVITIES_ON_SECONDARY_DISPLAYS;
47import static android.content.pm.PackageManager.FEATURE_FREEFORM_WINDOW_MANAGEMENT;
Evan Rosky4505b352018-09-06 11:20:40 -070048import static android.content.pm.PackageManager.FEATURE_PC;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070049import static android.content.pm.PackageManager.FEATURE_PICTURE_IN_PICTURE;
Wale Ogunwaled0412b32018-05-08 09:25:50 -070050import static android.content.pm.PackageManager.PERMISSION_GRANTED;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070051import static android.content.res.Configuration.UI_MODE_TYPE_TELEVISION;
52import static android.os.Build.VERSION_CODES.N;
Wale Ogunwale214f3482018-10-04 11:00:47 -070053import static android.os.FactoryTest.FACTORY_TEST_HIGH_LEVEL;
54import static android.os.FactoryTest.FACTORY_TEST_LOW_LEVEL;
55import static android.os.FactoryTest.FACTORY_TEST_OFF;
Wale Ogunwale31913b52018-10-13 08:29:31 -070056import static android.os.Process.FIRST_APPLICATION_UID;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070057import static android.os.Process.SYSTEM_UID;
Evan Rosky4505b352018-09-06 11:20:40 -070058import static android.os.Trace.TRACE_TAG_ACTIVITY_MANAGER;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070059import static android.provider.Settings.Global.ALWAYS_FINISH_ACTIVITIES;
60import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT;
61import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES;
62import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RTL;
Evan Rosky4505b352018-09-06 11:20:40 -070063import static android.provider.Settings.Global.HIDE_ERROR_DIALOGS;
64import static android.provider.Settings.System.FONT_SCALE;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070065import static android.service.voice.VoiceInteractionSession.SHOW_SOURCE_APPLICATION;
66import static android.view.Display.DEFAULT_DISPLAY;
67import static android.view.Display.INVALID_DISPLAY;
Wale Ogunwale6767eae2018-05-03 15:52:51 -070068import static android.view.WindowManager.TRANSIT_NONE;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070069import static android.view.WindowManager.TRANSIT_TASK_IN_PLACE;
Evan Rosky4505b352018-09-06 11:20:40 -070070
Yunfan Chen79b96062018-10-17 12:45:23 -070071import static com.android.server.am.ActivityManagerService.ANR_TRACE_DIR;
72import static com.android.server.am.ActivityManagerService.MY_PID;
73import static com.android.server.am.ActivityManagerService.STOCK_PM_FLAGS;
74import static com.android.server.am.ActivityManagerService.dumpStackTraces;
Wale Ogunwale31913b52018-10-13 08:29:31 -070075import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.CONFIG_WILL_CHANGE;
76import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.CONTROLLER;
77import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.CURRENT_TRACKER;
78import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.Controller.IS_A_MONKEY;
79import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.GLOBAL_CONFIGURATION;
80import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.GOING_TO_SLEEP;
81import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.HEAVY_WEIGHT_PROC;
82import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.HOME_PROC;
83import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.LAUNCHING_ACTIVITY;
84import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.PREVIOUS_PROC;
Wale Ogunwale59507092018-10-29 09:00:30 -070085import static com.android.server.am.ActivityManagerServiceDumpProcessesProto
86 .PREVIOUS_PROC_VISIBLE_TIME_MS;
Wale Ogunwale31913b52018-10-13 08:29:31 -070087import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.SCREEN_COMPAT_PACKAGES;
Wale Ogunwale59507092018-10-29 09:00:30 -070088import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.ScreenCompatPackage
89 .MODE;
90import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.ScreenCompatPackage
91 .PACKAGE;
92import static com.android.server.wm.ActivityStack.REMOVE_TASK_MODE_DESTROYING;
93import static com.android.server.wm.ActivityStackSupervisor.DEFER_RESUME;
94import static com.android.server.wm.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_ONLY;
95import static com.android.server.wm.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_OR_RECENT_TASKS;
96import static com.android.server.wm.ActivityStackSupervisor.ON_TOP;
97import static com.android.server.wm.ActivityStackSupervisor.PRESERVE_WINDOWS;
98import static com.android.server.wm.ActivityStackSupervisor.REMOVE_FROM_RECENTS;
99import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_ALL;
100import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_CONFIGURATION;
101import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_FOCUS;
102import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_IMMERSIVE;
103import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_LOCKTASK;
104import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_STACK;
105import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_SWITCH;
106import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_TASKS;
107import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_VISIBILITY;
108import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_CONFIGURATION;
109import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_FOCUS;
110import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_IMMERSIVE;
111import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_LOCKTASK;
112import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_STACK;
113import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_SWITCH;
114import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_VISIBILITY;
115import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_ATM;
116import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_WITH_CLASS_NAME;
Evan Rosky4505b352018-09-06 11:20:40 -0700117import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_CONTENT;
118import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_DATA;
119import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_RECEIVER_EXTRAS;
120import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_STRUCTURE;
wilsonshihe7903ea2018-09-26 16:17:59 +0800121import static com.android.server.wm.ActivityTaskManagerService.H.REPORT_TIME_TRACKER_MSG;
122import static com.android.server.wm.ActivityTaskManagerService.UiHandler.DISMISS_DIALOG_UI_MSG;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700123import static com.android.server.wm.RecentsAnimationController.REORDER_KEEP_IN_PLACE;
124import static com.android.server.wm.RecentsAnimationController.REORDER_MOVE_TO_ORIGINAL_POSITION;
wilsonshihe7903ea2018-09-26 16:17:59 +0800125import static com.android.server.wm.TaskRecord.LOCK_TASK_AUTH_DONT_LOCK;
126import static com.android.server.wm.TaskRecord.REPARENT_KEEP_STACK_AT_FRONT;
127import static com.android.server.wm.TaskRecord.REPARENT_LEAVE_STACK_IN_PLACE;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700128
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700129import android.Manifest;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700130import android.annotation.NonNull;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700131import android.annotation.Nullable;
132import android.annotation.UserIdInt;
133import android.app.Activity;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700134import android.app.ActivityManager;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700135import android.app.ActivityManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700136import android.app.ActivityOptions;
137import android.app.ActivityTaskManager;
Wale Ogunwalef6733932018-06-27 05:14:34 -0700138import android.app.ActivityThread;
139import android.app.AlertDialog;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700140import android.app.AppGlobals;
Evan Rosky4505b352018-09-06 11:20:40 -0700141import android.app.Dialog;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700142import android.app.IActivityController;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700143import android.app.IActivityTaskManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700144import android.app.IApplicationThread;
145import android.app.IAssistDataReceiver;
Wale Ogunwale53783742018-09-16 10:21:51 -0700146import android.app.INotificationManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700147import android.app.ITaskStackListener;
Wale Ogunwale53783742018-09-16 10:21:51 -0700148import android.app.Notification;
149import android.app.NotificationManager;
150import android.app.PendingIntent;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700151import android.app.PictureInPictureParams;
152import android.app.ProfilerInfo;
153import android.app.RemoteAction;
154import android.app.WaitResult;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700155import android.app.WindowConfiguration;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700156import android.app.admin.DevicePolicyCache;
157import android.app.assist.AssistContent;
158import android.app.assist.AssistStructure;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700159import android.app.usage.UsageStatsManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700160import android.content.ActivityNotFoundException;
161import android.content.ComponentName;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700162import android.content.ContentResolver;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700163import android.content.Context;
Evan Rosky4505b352018-09-06 11:20:40 -0700164import android.content.DialogInterface;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700165import android.content.IIntentSender;
166import android.content.Intent;
167import android.content.pm.ActivityInfo;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700168import android.content.pm.ApplicationInfo;
Yunfan Chen75157d72018-07-27 14:47:21 +0900169import android.content.pm.ConfigurationInfo;
Evan Rosky4505b352018-09-06 11:20:40 -0700170import android.content.pm.IPackageManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700171import android.content.pm.PackageManager;
Evan Rosky4505b352018-09-06 11:20:40 -0700172import android.content.pm.PackageManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700173import android.content.pm.ParceledListSlice;
174import android.content.pm.ResolveInfo;
Wale Ogunwale53783742018-09-16 10:21:51 -0700175import android.content.res.CompatibilityInfo;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700176import android.content.res.Configuration;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700177import android.content.res.Resources;
Evan Rosky4505b352018-09-06 11:20:40 -0700178import android.database.ContentObserver;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700179import android.graphics.Bitmap;
180import android.graphics.Point;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700181import android.graphics.Rect;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700182import android.metrics.LogMaker;
183import android.net.Uri;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700184import android.os.Binder;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700185import android.os.Build;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700186import android.os.Bundle;
Wale Ogunwale214f3482018-10-04 11:00:47 -0700187import android.os.FactoryTest;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700188import android.os.FileUtils;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700189import android.os.Handler;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700190import android.os.IBinder;
Evan Rosky4505b352018-09-06 11:20:40 -0700191import android.os.IUserManager;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700192import android.os.LocaleList;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700193import android.os.Message;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700194import android.os.PersistableBundle;
Evan Rosky4505b352018-09-06 11:20:40 -0700195import android.os.PowerManager;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700196import android.os.PowerManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700197import android.os.RemoteException;
Evan Rosky4505b352018-09-06 11:20:40 -0700198import android.os.ServiceManager;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700199import android.os.StrictMode;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700200import android.os.SystemClock;
201import android.os.SystemProperties;
Evan Rosky4505b352018-09-06 11:20:40 -0700202import android.os.Trace;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700203import android.os.UpdateLock;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700204import android.os.UserHandle;
Evan Rosky4505b352018-09-06 11:20:40 -0700205import android.os.UserManager;
206import android.os.WorkSource;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700207import android.os.storage.IStorageManager;
208import android.os.storage.StorageManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700209import android.provider.Settings;
210import android.service.voice.IVoiceInteractionSession;
211import android.service.voice.VoiceInteractionManagerInternal;
212import android.telecom.TelecomManager;
213import android.text.TextUtils;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700214import android.text.format.Time;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700215import android.util.ArrayMap;
216import android.util.EventLog;
217import android.util.Log;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700218import android.util.Slog;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700219import android.util.SparseArray;
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700220import android.util.SparseIntArray;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700221import android.util.StatsLog;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700222import android.util.TimeUtils;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700223import android.util.proto.ProtoOutputStream;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700224import android.view.IRecentsAnimationRunner;
225import android.view.RemoteAnimationAdapter;
226import android.view.RemoteAnimationDefinition;
Evan Rosky4505b352018-09-06 11:20:40 -0700227import android.view.WindowManager;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700228
Evan Rosky4505b352018-09-06 11:20:40 -0700229import com.android.internal.R;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700230import com.android.internal.annotations.VisibleForTesting;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700231import com.android.internal.app.AssistUtils;
Evan Rosky4505b352018-09-06 11:20:40 -0700232import com.android.internal.app.IAppOpsService;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700233import com.android.internal.app.IVoiceInteractor;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700234import com.android.internal.app.ProcessMap;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700235import com.android.internal.logging.MetricsLogger;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700236import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
Wale Ogunwale53783742018-09-16 10:21:51 -0700237import com.android.internal.messages.nano.SystemMessageProto.SystemMessage;
238import com.android.internal.notification.SystemNotificationChannels;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700239import com.android.internal.os.TransferPipe;
Evan Rosky4505b352018-09-06 11:20:40 -0700240import com.android.internal.os.logging.MetricsLoggerWrapper;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700241import com.android.internal.policy.IKeyguardDismissCallback;
242import com.android.internal.policy.KeyguardDismissCallback;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700243import com.android.internal.util.ArrayUtils;
244import com.android.internal.util.FastPrintWriter;
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700245import com.android.internal.util.Preconditions;
Wale Ogunwale53783742018-09-16 10:21:51 -0700246import com.android.internal.util.function.pooled.PooledLambda;
Evan Rosky4505b352018-09-06 11:20:40 -0700247import com.android.server.AppOpsService;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700248import com.android.server.AttributeCache;
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -0800249import com.android.server.DisplayThread;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700250import com.android.server.LocalServices;
251import com.android.server.SystemService;
Evan Rosky4505b352018-09-06 11:20:40 -0700252import com.android.server.SystemServiceManager;
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -0800253import com.android.server.UiThread;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700254import com.android.server.Watchdog;
Wale Ogunwale59507092018-10-29 09:00:30 -0700255import com.android.server.am.ActivityManagerService;
256import com.android.server.am.ActivityManagerServiceDumpActivitiesProto;
257import com.android.server.am.ActivityManagerServiceDumpProcessesProto;
258import com.android.server.am.AppTimeTracker;
259import com.android.server.am.BaseErrorDialog;
260import com.android.server.am.EventLogTags;
261import com.android.server.am.PendingIntentController;
262import com.android.server.am.PendingIntentRecord;
263import com.android.server.am.UserState;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700264import com.android.server.firewall.IntentFirewall;
Evan Rosky4505b352018-09-06 11:20:40 -0700265import com.android.server.pm.UserManagerService;
266import com.android.server.uri.UriGrantsManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700267import com.android.server.vr.VrManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700268
Wale Ogunwale31913b52018-10-13 08:29:31 -0700269import java.io.BufferedReader;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700270import java.io.File;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700271import java.io.FileDescriptor;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700272import java.io.FileOutputStream;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700273import java.io.FileReader;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700274import java.io.IOException;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700275import java.io.PrintWriter;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700276import java.io.StringWriter;
Wale Ogunwaleee6eca12018-09-19 20:37:53 -0700277import java.lang.ref.WeakReference;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700278import java.text.DateFormat;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700279import java.util.ArrayList;
Wale Ogunwale27c48ae2018-10-25 19:01:01 -0700280import java.util.Arrays;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700281import java.util.Date;
Wale Ogunwaleee6eca12018-09-19 20:37:53 -0700282import java.util.HashSet;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700283import java.util.List;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700284import java.util.Locale;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700285import java.util.Map;
286import java.util.Set;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700287
288/**
289 * System service for managing activities and their containers (task, stacks, displays,... ).
290 *
291 * {@hide}
292 */
293public class ActivityTaskManagerService extends IActivityTaskManager.Stub {
Wale Ogunwale98875612018-10-12 07:53:02 -0700294 private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityTaskManagerService" : TAG_ATM;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700295 private static final String TAG_STACK = TAG + POSTFIX_STACK;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700296 private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH;
297 private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE;
298 private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS;
299 private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY;
300 private static final String TAG_LOCKTASK = TAG + POSTFIX_LOCKTASK;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700301 private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700302
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700303 // How long we wait until we timeout on key dispatching.
Wale Ogunwale51cc98a2018-10-15 10:41:05 -0700304 public static final int KEY_DISPATCHING_TIMEOUT_MS = 5 * 1000;
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700305 // How long we wait until we timeout on key dispatching during instrumentation.
Wale Ogunwale51cc98a2018-10-15 10:41:05 -0700306 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT_MS = 60 * 1000;
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700307
Wale Ogunwale98875612018-10-12 07:53:02 -0700308 /** Used to indicate that an app transition should be animated. */
309 static final boolean ANIMATE = true;
310
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700311 /** Hardware-reported OpenGLES version. */
312 final int GL_ES_VERSION;
313
Wale Ogunwale31913b52018-10-13 08:29:31 -0700314 public static final String DUMP_ACTIVITIES_CMD = "activities" ;
315 public static final String DUMP_ACTIVITIES_SHORT_CMD = "a" ;
316 public static final String DUMP_LASTANR_CMD = "lastanr" ;
317 public static final String DUMP_LASTANR_TRACES_CMD = "lastanr-traces" ;
318 public static final String DUMP_STARTER_CMD = "starter" ;
319 public static final String DUMP_CONTAINERS_CMD = "containers" ;
320 public static final String DUMP_RECENTS_CMD = "recents" ;
321 public static final String DUMP_RECENTS_SHORT_CMD = "r" ;
322
Wale Ogunwale64258362018-10-16 15:13:37 -0700323 /** This activity is not being relaunched, or being relaunched for a non-resize reason. */
324 public static final int RELAUNCH_REASON_NONE = 0;
325 /** This activity is being relaunched due to windowing mode change. */
326 public static final int RELAUNCH_REASON_WINDOWING_MODE_RESIZE = 1;
327 /** This activity is being relaunched due to a free-resize operation. */
328 public static final int RELAUNCH_REASON_FREE_RESIZE = 2;
329
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700330 Context mContext;
Wale Ogunwale64258362018-10-16 15:13:37 -0700331
Wale Ogunwalef6733932018-06-27 05:14:34 -0700332 /**
333 * This Context is themable and meant for UI display (AlertDialogs, etc.). The theme can
334 * change at runtime. Use mContext for non-UI purposes.
335 */
336 final Context mUiContext;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700337 final ActivityThread mSystemThread;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700338 H mH;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700339 UiHandler mUiHandler;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700340 ActivityManagerInternal mAmInternal;
Wale Ogunwale6d50dcc2018-07-21 23:00:40 -0700341 UriGrantsManagerInternal mUgmInternal;
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700342 private PackageManagerInternal mPmInternal;
Wale Ogunwale53783742018-09-16 10:21:51 -0700343 private ActivityTaskManagerInternal mInternal;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700344 PowerManagerInternal mPowerManagerInternal;
345 private UsageStatsManagerInternal mUsageStatsInternal;
346
Wale Ogunwaleee6eca12018-09-19 20:37:53 -0700347 PendingIntentController mPendingIntentController;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700348 IntentFirewall mIntentFirewall;
349
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700350 /* Global service lock used by the package the owns this service. */
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -0800351 final WindowManagerGlobalLock mGlobalLock = new WindowManagerGlobalLock();
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700352 ActivityStackSupervisor mStackSupervisor;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700353 WindowManagerService mWindowManager;
Wale Ogunwalef6733932018-06-27 05:14:34 -0700354 private UserManagerService mUserManager;
355 private AppOpsService mAppOpsService;
Wale Ogunwalebff2df42018-10-18 17:09:19 -0700356 /** All active uids in the system. */
Wale Ogunwale9de19442018-10-18 19:05:03 -0700357 private final SparseArray<Integer> mActiveUids = new SparseArray<>();
358 private final SparseArray<String> mPendingTempWhitelist = new SparseArray<>();
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700359 /** All processes currently running that might have a window organized by name. */
360 final ProcessMap<WindowProcessController> mProcessNames = new ProcessMap<>();
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700361 /** All processes we currently have running mapped by pid */
362 final SparseArray<WindowProcessController> mPidMap = new SparseArray<>();
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700363 /** This is the process holding what we currently consider to be the "home" activity. */
364 WindowProcessController mHomeProcess;
Wale Ogunwale53783742018-09-16 10:21:51 -0700365 /** The currently running heavy-weight process, if any. */
366 WindowProcessController mHeavyWeightProcess = null;
Wale Ogunwale214f3482018-10-04 11:00:47 -0700367 boolean mHasHeavyWeightFeature;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700368 /**
369 * This is the process holding the activity the user last visited that is in a different process
370 * from the one they are currently in.
371 */
372 WindowProcessController mPreviousProcess;
373 /** The time at which the previous process was last visible. */
374 long mPreviousProcessVisibleTime;
375
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700376 /** List of intents that were used to start the most recent tasks. */
377 private RecentTasks mRecentTasks;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700378 /** State of external calls telling us if the device is awake or asleep. */
379 private boolean mKeyguardShown = false;
380
381 // Wrapper around VoiceInteractionServiceManager
382 private AssistUtils mAssistUtils;
383
384 // VoiceInteraction session ID that changes for each new request except when
385 // being called for multi-window assist in a single session.
386 private int mViSessionId = 1000;
387
388 // How long to wait in getAssistContextExtras for the activity and foreground services
389 // to respond with the result.
390 private static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500;
391
392 // How long top wait when going through the modern assist (which doesn't need to block
393 // on getting this result before starting to launch its UI).
394 private static final int PENDING_ASSIST_EXTRAS_LONG_TIMEOUT = 2000;
395
396 // How long to wait in getAutofillAssistStructure() for the activity to respond with the result.
397 private static final int PENDING_AUTOFILL_ASSIST_STRUCTURE_TIMEOUT = 2000;
398
399 private final ArrayList<PendingAssistExtras> mPendingAssistExtras = new ArrayList<>();
400
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700401 // Keeps track of the active voice interaction service component, notified from
402 // VoiceInteractionManagerService
403 ComponentName mActiveVoiceInteractionServiceComponent;
404
Wale Ogunwalee2172292018-10-25 10:11:10 -0700405 VrController mVrController;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700406 KeyguardController mKeyguardController;
407 private final ClientLifecycleManager mLifecycleManager;
408 private TaskChangeNotificationController mTaskChangeNotificationController;
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700409 /** The controller for all operations related to locktask. */
410 private LockTaskController mLockTaskController;
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700411 private ActivityStartController mActivityStartController;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700412
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700413 boolean mSuppressResizeConfigChanges;
414
415 private final UpdateConfigurationResult mTmpUpdateConfigurationResult =
416 new UpdateConfigurationResult();
417
418 static final class UpdateConfigurationResult {
419 // Configuration changes that were updated.
420 int changes;
421 // If the activity was relaunched to match the new configuration.
422 boolean activityRelaunched;
423
424 void reset() {
425 changes = 0;
426 activityRelaunched = false;
427 }
428 }
429
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700430 /** Current sequencing integer of the configuration, for skipping old configurations. */
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700431 private int mConfigurationSeq;
432 // To cache the list of supported system locales
433 private String[] mSupportedSystemLocales = null;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700434
435 /**
436 * Temp object used when global and/or display override configuration is updated. It is also
437 * sent to outer world instead of {@link #getGlobalConfiguration} because we don't trust
438 * anyone...
439 */
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700440 private Configuration mTempConfig = new Configuration();
441
Wale Ogunwalef6733932018-06-27 05:14:34 -0700442 /** Temporary to avoid allocations. */
443 final StringBuilder mStringBuilder = new StringBuilder(256);
444
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700445 // Amount of time after a call to stopAppSwitches() during which we will
446 // prevent further untrusted switches from happening.
447 private static final long APP_SWITCH_DELAY_TIME = 5 * 1000;
448
449 /**
450 * The time at which we will allow normal application switches again,
451 * after a call to {@link #stopAppSwitches()}.
452 */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700453 private long mAppSwitchesAllowedTime;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700454 /**
455 * This is set to true after the first switch after mAppSwitchesAllowedTime
456 * is set; any switches after that will clear the time.
457 */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700458 private boolean mDidAppSwitch;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700459
460 IActivityController mController = null;
461 boolean mControllerIsAMonkey = false;
462
Wale Ogunwale214f3482018-10-04 11:00:47 -0700463 final int mFactoryTest;
464
465 /** Used to control how we initialize the service. */
466 ComponentName mTopComponent;
467 String mTopAction = Intent.ACTION_MAIN;
468 String mTopData;
469
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -0800470 /** Profiling app information. */
471 String mProfileApp = null;
472 WindowProcessController mProfileProc = null;
473 ProfilerInfo mProfilerInfo = null;
474
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700475 /**
Wale Ogunwale31913b52018-10-13 08:29:31 -0700476 * Dump of the activity state at the time of the last ANR. Cleared after
477 * {@link WindowManagerService#LAST_ANR_LIFETIME_DURATION_MSECS}
478 */
479 String mLastANRState;
480
481 /**
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700482 * Used to retain an update lock when the foreground activity is in
483 * immersive mode.
484 */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700485 private final UpdateLock mUpdateLock = new UpdateLock("immersive");
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700486
487 /**
488 * Packages that are being allowed to perform unrestricted app switches. Mapping is
489 * User -> Type -> uid.
490 */
491 final SparseArray<ArrayMap<String, Integer>> mAllowAppSwitchUids = new SparseArray<>();
492
493 /** The dimensions of the thumbnails in the Recents UI. */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700494 private int mThumbnailWidth;
495 private int mThumbnailHeight;
496 private float mFullscreenThumbnailScale;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700497
498 /**
499 * Flag that indicates if multi-window is enabled.
500 *
501 * For any particular form of multi-window to be enabled, generic multi-window must be enabled
502 * in {@link com.android.internal.R.bool#config_supportsMultiWindow} config or
503 * {@link Settings.Global#DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES} development option set.
504 * At least one of the forms of multi-window must be enabled in order for this flag to be
505 * initialized to 'true'.
506 *
507 * @see #mSupportsSplitScreenMultiWindow
508 * @see #mSupportsFreeformWindowManagement
509 * @see #mSupportsPictureInPicture
510 * @see #mSupportsMultiDisplay
511 */
512 boolean mSupportsMultiWindow;
513 boolean mSupportsSplitScreenMultiWindow;
514 boolean mSupportsFreeformWindowManagement;
515 boolean mSupportsPictureInPicture;
516 boolean mSupportsMultiDisplay;
517 boolean mForceResizableActivities;
518
519 final List<ActivityTaskManagerInternal.ScreenObserver> mScreenObservers = new ArrayList<>();
520
521 // VR Vr2d Display Id.
522 int mVr2dDisplayId = INVALID_DISPLAY;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700523
Wale Ogunwalef6733932018-06-27 05:14:34 -0700524 /**
525 * Set while we are wanting to sleep, to prevent any
526 * activities from being started/resumed.
527 *
528 * TODO(b/33594039): Clarify the actual state transitions represented by mSleeping.
529 *
530 * Currently mSleeping is set to true when transitioning into the sleep state, and remains true
531 * while in the sleep state until there is a pending transition out of sleep, in which case
532 * mSleeping is set to false, and remains false while awake.
533 *
534 * Whether mSleeping can quickly toggled between true/false without the device actually
535 * display changing states is undefined.
536 */
537 private boolean mSleeping = false;
538
539 /**
540 * The process state used for processes that are running the top activities.
541 * This changes between TOP and TOP_SLEEPING to following mSleeping.
542 */
543 int mTopProcessState = ActivityManager.PROCESS_STATE_TOP;
544
545 // Whether we should show our dialogs (ANR, crash, etc) or just perform their default action
546 // automatically. Important for devices without direct input devices.
547 private boolean mShowDialogs = true;
548
549 /** Set if we are shutting down the system, similar to sleeping. */
550 boolean mShuttingDown = false;
551
552 /**
553 * We want to hold a wake lock while running a voice interaction session, since
554 * this may happen with the screen off and we need to keep the CPU running to
555 * be able to continue to interact with the user.
556 */
557 PowerManager.WakeLock mVoiceWakeLock;
558
559 /**
560 * Set while we are running a voice interaction. This overrides sleeping while it is active.
561 */
562 IVoiceInteractionSession mRunningVoice;
563
564 /**
565 * The last resumed activity. This is identical to the current resumed activity most
566 * of the time but could be different when we're pausing one activity before we resume
567 * another activity.
568 */
569 ActivityRecord mLastResumedActivity;
570
571 /**
572 * The activity that is currently being traced as the active resumed activity.
573 *
574 * @see #updateResumedAppTrace
575 */
576 private @Nullable ActivityRecord mTracedResumedActivity;
577
578 /** If non-null, we are tracking the time the user spends in the currently focused app. */
579 AppTimeTracker mCurAppTimeTracker;
580
Wale Ogunwale008163e2018-07-23 23:11:08 -0700581 private AppWarnings mAppWarnings;
582
Wale Ogunwale53783742018-09-16 10:21:51 -0700583 /**
584 * Packages that the user has asked to have run in screen size
585 * compatibility mode instead of filling the screen.
586 */
587 CompatModePackages mCompatModePackages;
588
Wale Ogunwalef6733932018-06-27 05:14:34 -0700589 private FontScaleSettingObserver mFontScaleSettingObserver;
590
591 private final class FontScaleSettingObserver extends ContentObserver {
592 private final Uri mFontScaleUri = Settings.System.getUriFor(FONT_SCALE);
593 private final Uri mHideErrorDialogsUri = Settings.Global.getUriFor(HIDE_ERROR_DIALOGS);
594
595 public FontScaleSettingObserver() {
596 super(mH);
597 final ContentResolver resolver = mContext.getContentResolver();
598 resolver.registerContentObserver(mFontScaleUri, false, this, UserHandle.USER_ALL);
599 resolver.registerContentObserver(mHideErrorDialogsUri, false, this,
600 UserHandle.USER_ALL);
601 }
602
603 @Override
604 public void onChange(boolean selfChange, Uri uri, @UserIdInt int userId) {
605 if (mFontScaleUri.equals(uri)) {
606 updateFontScaleIfNeeded(userId);
607 } else if (mHideErrorDialogsUri.equals(uri)) {
608 synchronized (mGlobalLock) {
609 updateShouldShowDialogsLocked(getGlobalConfiguration());
610 }
611 }
612 }
613 }
614
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700615 ActivityTaskManagerService(Context context) {
616 mContext = context;
Wale Ogunwale214f3482018-10-04 11:00:47 -0700617 mFactoryTest = FactoryTest.getMode();
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700618 mSystemThread = ActivityThread.currentActivityThread();
619 mUiContext = mSystemThread.getSystemUiContext();
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700620 mLifecycleManager = new ClientLifecycleManager();
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700621 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", GL_ES_VERSION_UNDEFINED);
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700622 }
623
Wale Ogunwale387b34c2018-10-25 19:59:40 -0700624 public void onSystemReady() {
625 synchronized (mGlobalLock) {
626 mHasHeavyWeightFeature = mContext.getPackageManager().hasSystemFeature(
627 PackageManager.FEATURE_CANT_SAVE_STATE);
628 mAssistUtils = new AssistUtils(mContext);
629 mVrController.onSystemReady();
630 mRecentTasks.onSystemReadyLocked();
631 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700632 }
633
Wale Ogunwale387b34c2018-10-25 19:59:40 -0700634 public void onInitPowerManagement() {
635 synchronized (mGlobalLock) {
636 mStackSupervisor.initPowerManagement();
637 final PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
638 mPowerManagerInternal = LocalServices.getService(PowerManagerInternal.class);
639 mVoiceWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "*voice*");
640 mVoiceWakeLock.setReferenceCounted(false);
641 }
Wale Ogunwalef6733932018-06-27 05:14:34 -0700642 }
643
Wale Ogunwale387b34c2018-10-25 19:59:40 -0700644 public void installSystemProviders() {
Wale Ogunwalef6733932018-06-27 05:14:34 -0700645 mFontScaleSettingObserver = new FontScaleSettingObserver();
646 }
647
Wale Ogunwale59507092018-10-29 09:00:30 -0700648 public void retrieveSettings(ContentResolver resolver) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700649 final boolean freeformWindowManagement =
650 mContext.getPackageManager().hasSystemFeature(FEATURE_FREEFORM_WINDOW_MANAGEMENT)
651 || Settings.Global.getInt(
652 resolver, DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT, 0) != 0;
653
654 final boolean supportsMultiWindow = ActivityTaskManager.supportsMultiWindow(mContext);
655 final boolean supportsPictureInPicture = supportsMultiWindow &&
656 mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE);
657 final boolean supportsSplitScreenMultiWindow =
658 ActivityTaskManager.supportsSplitScreenMultiWindow(mContext);
659 final boolean supportsMultiDisplay = mContext.getPackageManager()
660 .hasSystemFeature(FEATURE_ACTIVITIES_ON_SECONDARY_DISPLAYS);
661 final boolean alwaysFinishActivities =
662 Settings.Global.getInt(resolver, ALWAYS_FINISH_ACTIVITIES, 0) != 0;
663 final boolean forceRtl = Settings.Global.getInt(resolver, DEVELOPMENT_FORCE_RTL, 0) != 0;
664 final boolean forceResizable = Settings.Global.getInt(
665 resolver, DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES, 0) != 0;
Garfield Tane0846042018-07-26 13:42:04 -0700666 final boolean isPc = mContext.getPackageManager().hasSystemFeature(FEATURE_PC);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700667
668 // Transfer any global setting for forcing RTL layout, into a System Property
669 SystemProperties.set(DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0");
670
671 final Configuration configuration = new Configuration();
672 Settings.System.getConfiguration(resolver, configuration);
673 if (forceRtl) {
674 // This will take care of setting the correct layout direction flags
675 configuration.setLayoutDirection(configuration.locale);
676 }
677
678 synchronized (mGlobalLock) {
679 mForceResizableActivities = forceResizable;
680 final boolean multiWindowFormEnabled = freeformWindowManagement
681 || supportsSplitScreenMultiWindow
682 || supportsPictureInPicture
683 || supportsMultiDisplay;
684 if ((supportsMultiWindow || forceResizable) && multiWindowFormEnabled) {
685 mSupportsMultiWindow = true;
686 mSupportsFreeformWindowManagement = freeformWindowManagement;
687 mSupportsSplitScreenMultiWindow = supportsSplitScreenMultiWindow;
688 mSupportsPictureInPicture = supportsPictureInPicture;
689 mSupportsMultiDisplay = supportsMultiDisplay;
690 } else {
691 mSupportsMultiWindow = false;
692 mSupportsFreeformWindowManagement = false;
693 mSupportsSplitScreenMultiWindow = false;
694 mSupportsPictureInPicture = false;
695 mSupportsMultiDisplay = false;
696 }
697 mWindowManager.setForceResizableTasks(mForceResizableActivities);
698 mWindowManager.setSupportsPictureInPicture(mSupportsPictureInPicture);
Garfield Tane0846042018-07-26 13:42:04 -0700699 mWindowManager.setSupportsFreeformWindowManagement(mSupportsFreeformWindowManagement);
700 mWindowManager.setIsPc(isPc);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700701 // This happens before any activities are started, so we can change global configuration
702 // in-place.
703 updateConfigurationLocked(configuration, null, true);
704 final Configuration globalConfig = getGlobalConfiguration();
705 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Initial config: " + globalConfig);
706
707 // Load resources only after the current configuration has been set.
708 final Resources res = mContext.getResources();
709 mThumbnailWidth = res.getDimensionPixelSize(
710 com.android.internal.R.dimen.thumbnail_width);
711 mThumbnailHeight = res.getDimensionPixelSize(
712 com.android.internal.R.dimen.thumbnail_height);
713
714 if ((globalConfig.uiMode & UI_MODE_TYPE_TELEVISION) == UI_MODE_TYPE_TELEVISION) {
715 mFullscreenThumbnailScale = (float) res
716 .getInteger(com.android.internal.R.integer.thumbnail_width_tv) /
717 (float) globalConfig.screenWidthDp;
718 } else {
719 mFullscreenThumbnailScale = res.getFraction(
720 com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1);
721 }
722 }
723 }
724
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -0800725 public WindowManagerGlobalLock getGlobalLock() {
726 return mGlobalLock;
727 }
728
729 public void setActivityManagerService(IntentFirewall intentFirewall,
730 PendingIntentController intentController) {
731 mH = new H();
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700732 mUiHandler = new UiHandler();
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700733 mIntentFirewall = intentFirewall;
Wale Ogunwale53783742018-09-16 10:21:51 -0700734 final File systemDir = SystemServiceManager.ensureSystemDir();
735 mAppWarnings = new AppWarnings(this, mUiContext, mH, mUiHandler, systemDir);
736 mCompatModePackages = new CompatModePackages(this, systemDir, mH);
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700737 mPendingIntentController = intentController;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700738
739 mTempConfig.setToDefaults();
740 mTempConfig.setLocales(LocaleList.getDefault());
741 mConfigurationSeq = mTempConfig.seq = 1;
742 mStackSupervisor = createStackSupervisor();
743 mStackSupervisor.onConfigurationChanged(mTempConfig);
744
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700745 mTaskChangeNotificationController =
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700746 new TaskChangeNotificationController(mGlobalLock, mStackSupervisor, mH);
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700747 mLockTaskController = new LockTaskController(mContext, mStackSupervisor, mH);
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700748 mActivityStartController = new ActivityStartController(this);
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700749 mRecentTasks = createRecentTasks();
750 mStackSupervisor.setRecentTasks(mRecentTasks);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700751 mVrController = new VrController(mGlobalLock);
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700752 mKeyguardController = mStackSupervisor.getKeyguardController();
753 }
754
Wale Ogunwale387b34c2018-10-25 19:59:40 -0700755 public void onActivityManagerInternalAdded() {
756 synchronized (mGlobalLock) {
757 mAmInternal = LocalServices.getService(ActivityManagerInternal.class);
758 mUgmInternal = LocalServices.getService(UriGrantsManagerInternal.class);
759 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700760 }
761
Yunfan Chen75157d72018-07-27 14:47:21 +0900762 int increaseConfigurationSeqLocked() {
763 mConfigurationSeq = Math.max(++mConfigurationSeq, 1);
764 return mConfigurationSeq;
765 }
766
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700767 protected ActivityStackSupervisor createStackSupervisor() {
768 final ActivityStackSupervisor supervisor = new ActivityStackSupervisor(this, mH.getLooper());
769 supervisor.initialize();
770 return supervisor;
771 }
772
Wale Ogunwale387b34c2018-10-25 19:59:40 -0700773 public void setWindowManager(WindowManagerService wm) {
774 synchronized (mGlobalLock) {
775 mWindowManager = wm;
776 mLockTaskController.setWindowManager(wm);
777 mStackSupervisor.setWindowManager(wm);
778 }
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700779 }
780
Wale Ogunwale387b34c2018-10-25 19:59:40 -0700781 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) {
782 synchronized (mGlobalLock) {
783 mUsageStatsInternal = usageStatsManager;
784 }
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700785 }
786
Wale Ogunwalef6733932018-06-27 05:14:34 -0700787 UserManagerService getUserManager() {
788 if (mUserManager == null) {
789 IBinder b = ServiceManager.getService(Context.USER_SERVICE);
790 mUserManager = (UserManagerService) IUserManager.Stub.asInterface(b);
791 }
792 return mUserManager;
793 }
794
795 AppOpsService getAppOpsService() {
796 if (mAppOpsService == null) {
797 IBinder b = ServiceManager.getService(Context.APP_OPS_SERVICE);
798 mAppOpsService = (AppOpsService) IAppOpsService.Stub.asInterface(b);
799 }
800 return mAppOpsService;
801 }
802
803 boolean hasUserRestriction(String restriction, int userId) {
804 return getUserManager().hasUserRestriction(restriction, userId);
805 }
806
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700807 protected RecentTasks createRecentTasks() {
808 return new RecentTasks(this, mStackSupervisor);
809 }
810
811 RecentTasks getRecentTasks() {
812 return mRecentTasks;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700813 }
814
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700815 ClientLifecycleManager getLifecycleManager() {
816 return mLifecycleManager;
817 }
818
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700819 ActivityStartController getActivityStartController() {
820 return mActivityStartController;
821 }
822
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700823 TaskChangeNotificationController getTaskChangeNotificationController() {
824 return mTaskChangeNotificationController;
825 }
826
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700827 LockTaskController getLockTaskController() {
828 return mLockTaskController;
829 }
830
Yunfan Chen75157d72018-07-27 14:47:21 +0900831 /**
832 * Return the global configuration used by the process corresponding to the input pid. This is
833 * usually the global configuration with some overrides specific to that process.
834 */
835 Configuration getGlobalConfigurationForCallingPid() {
836 final int pid = Binder.getCallingPid();
837 if (pid == MY_PID || pid < 0) {
838 return getGlobalConfiguration();
839 }
840 synchronized (mGlobalLock) {
841 final WindowProcessController app = mPidMap.get(pid);
842 return app != null ? app.getConfiguration() : getGlobalConfiguration();
843 }
844 }
845
846 /**
847 * Return the device configuration info used by the process corresponding to the input pid.
848 * The value is consistent with the global configuration for the process.
849 */
850 @Override
851 public ConfigurationInfo getDeviceConfigurationInfo() {
852 ConfigurationInfo config = new ConfigurationInfo();
853 synchronized (mGlobalLock) {
854 final Configuration globalConfig = getGlobalConfigurationForCallingPid();
855 config.reqTouchScreen = globalConfig.touchscreen;
856 config.reqKeyboardType = globalConfig.keyboard;
857 config.reqNavigation = globalConfig.navigation;
858 if (globalConfig.navigation == Configuration.NAVIGATION_DPAD
859 || globalConfig.navigation == Configuration.NAVIGATION_TRACKBALL) {
860 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV;
861 }
862 if (globalConfig.keyboard != Configuration.KEYBOARD_UNDEFINED
863 && globalConfig.keyboard != Configuration.KEYBOARD_NOKEYS) {
864 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD;
865 }
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700866 config.reqGlEsVersion = GL_ES_VERSION;
Yunfan Chen75157d72018-07-27 14:47:21 +0900867 }
868 return config;
869 }
870
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700871 private void start() {
Wale Ogunwale53783742018-09-16 10:21:51 -0700872 mInternal = new LocalService();
873 LocalServices.addService(ActivityTaskManagerInternal.class, mInternal);
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700874 }
875
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700876 public static final class Lifecycle extends SystemService {
877 private final ActivityTaskManagerService mService;
878
879 public Lifecycle(Context context) {
880 super(context);
881 mService = new ActivityTaskManagerService(context);
882 }
883
884 @Override
885 public void onStart() {
886 publishBinderService(Context.ACTIVITY_TASK_SERVICE, mService);
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700887 mService.start();
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700888 }
889
890 public ActivityTaskManagerService getService() {
891 return mService;
892 }
893 }
894
895 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700896 public final int startActivity(IApplicationThread caller, String callingPackage,
897 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
898 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) {
899 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
900 resultWho, requestCode, startFlags, profilerInfo, bOptions,
901 UserHandle.getCallingUserId());
902 }
903
904 @Override
905 public final int startActivities(IApplicationThread caller, String callingPackage,
906 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle bOptions,
907 int userId) {
908 final String reason = "startActivities";
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700909 enforceNotIsolatedCaller(reason);
910 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, reason);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700911 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700912 return getActivityStartController().startActivities(caller, -1, callingPackage, intents,
Michal Karpinski201bc0c2018-07-20 15:32:00 +0100913 resolvedTypes, resultTo, SafeActivityOptions.fromBundle(bOptions), userId, reason,
914 null /* originatingPendingIntent */);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700915 }
916
917 @Override
918 public int startActivityAsUser(IApplicationThread caller, String callingPackage,
919 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
920 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) {
921 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
922 resultWho, requestCode, startFlags, profilerInfo, bOptions, userId,
923 true /*validateIncomingUser*/);
924 }
925
926 int startActivityAsUser(IApplicationThread caller, String callingPackage,
927 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
928 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId,
929 boolean validateIncomingUser) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700930 enforceNotIsolatedCaller("startActivityAsUser");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700931
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700932 userId = getActivityStartController().checkTargetUser(userId, validateIncomingUser,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700933 Binder.getCallingPid(), Binder.getCallingUid(), "startActivityAsUser");
934
935 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700936 return getActivityStartController().obtainStarter(intent, "startActivityAsUser")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700937 .setCaller(caller)
938 .setCallingPackage(callingPackage)
939 .setResolvedType(resolvedType)
940 .setResultTo(resultTo)
941 .setResultWho(resultWho)
942 .setRequestCode(requestCode)
943 .setStartFlags(startFlags)
944 .setProfilerInfo(profilerInfo)
945 .setActivityOptions(bOptions)
946 .setMayWait(userId)
947 .execute();
948
949 }
950
951 @Override
952 public int startActivityIntentSender(IApplicationThread caller, IIntentSender target,
953 IBinder whitelistToken, Intent fillInIntent, String resolvedType, IBinder resultTo,
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700954 String resultWho, int requestCode, int flagsMask, int flagsValues, Bundle bOptions) {
955 enforceNotIsolatedCaller("startActivityIntentSender");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700956 // Refuse possible leaked file descriptors
957 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) {
958 throw new IllegalArgumentException("File descriptors passed in Intent");
959 }
960
961 if (!(target instanceof PendingIntentRecord)) {
962 throw new IllegalArgumentException("Bad PendingIntent object");
963 }
964
965 PendingIntentRecord pir = (PendingIntentRecord)target;
966
967 synchronized (mGlobalLock) {
968 // If this is coming from the currently resumed activity, it is
969 // effectively saying that app switches are allowed at this point.
Andrii Kulian5f750bc2018-07-17 08:57:23 -0700970 final ActivityStack stack = getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700971 if (stack.mResumedActivity != null &&
972 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700973 mAppSwitchesAllowedTime = 0;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700974 }
975 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700976 return pir.sendInner(0, fillInIntent, resolvedType, whitelistToken, null, null,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700977 resultTo, resultWho, requestCode, flagsMask, flagsValues, bOptions);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700978 }
979
980 @Override
981 public boolean startNextMatchingActivity(IBinder callingActivity, Intent intent,
982 Bundle bOptions) {
983 // Refuse possible leaked file descriptors
984 if (intent != null && intent.hasFileDescriptors()) {
985 throw new IllegalArgumentException("File descriptors passed in Intent");
986 }
987 SafeActivityOptions options = SafeActivityOptions.fromBundle(bOptions);
988
989 synchronized (mGlobalLock) {
990 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity);
991 if (r == null) {
992 SafeActivityOptions.abort(options);
993 return false;
994 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700995 if (!r.attachedToProcess()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700996 // The caller is not running... d'oh!
997 SafeActivityOptions.abort(options);
998 return false;
999 }
1000 intent = new Intent(intent);
1001 // The caller is not allowed to change the data.
1002 intent.setDataAndType(r.intent.getData(), r.intent.getType());
1003 // And we are resetting to find the next component...
1004 intent.setComponent(null);
1005
1006 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0);
1007
1008 ActivityInfo aInfo = null;
1009 try {
1010 List<ResolveInfo> resolves =
1011 AppGlobals.getPackageManager().queryIntentActivities(
1012 intent, r.resolvedType,
1013 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS,
1014 UserHandle.getCallingUserId()).getList();
1015
1016 // Look for the original activity in the list...
1017 final int N = resolves != null ? resolves.size() : 0;
1018 for (int i=0; i<N; i++) {
1019 ResolveInfo rInfo = resolves.get(i);
1020 if (rInfo.activityInfo.packageName.equals(r.packageName)
1021 && rInfo.activityInfo.name.equals(r.info.name)) {
1022 // We found the current one... the next matching is
1023 // after it.
1024 i++;
1025 if (i<N) {
1026 aInfo = resolves.get(i).activityInfo;
1027 }
1028 if (debug) {
1029 Slog.v(TAG, "Next matching activity: found current " + r.packageName
1030 + "/" + r.info.name);
1031 Slog.v(TAG, "Next matching activity: next is " + ((aInfo == null)
1032 ? "null" : aInfo.packageName + "/" + aInfo.name));
1033 }
1034 break;
1035 }
1036 }
1037 } catch (RemoteException e) {
1038 }
1039
1040 if (aInfo == null) {
1041 // Nobody who is next!
1042 SafeActivityOptions.abort(options);
1043 if (debug) Slog.d(TAG, "Next matching activity: nothing found");
1044 return false;
1045 }
1046
1047 intent.setComponent(new ComponentName(
1048 aInfo.applicationInfo.packageName, aInfo.name));
1049 intent.setFlags(intent.getFlags()&~(
1050 Intent.FLAG_ACTIVITY_FORWARD_RESULT|
1051 Intent.FLAG_ACTIVITY_CLEAR_TOP|
1052 Intent.FLAG_ACTIVITY_MULTIPLE_TASK|
1053 FLAG_ACTIVITY_NEW_TASK));
1054
1055 // Okay now we need to start the new activity, replacing the currently running activity.
1056 // This is a little tricky because we want to start the new one as if the current one is
1057 // finished, but not finish the current one first so that there is no flicker.
1058 // And thus...
1059 final boolean wasFinishing = r.finishing;
1060 r.finishing = true;
1061
1062 // Propagate reply information over to the new activity.
1063 final ActivityRecord resultTo = r.resultTo;
1064 final String resultWho = r.resultWho;
1065 final int requestCode = r.requestCode;
1066 r.resultTo = null;
1067 if (resultTo != null) {
1068 resultTo.removeResultsLocked(r, resultWho, requestCode);
1069 }
1070
1071 final long origId = Binder.clearCallingIdentity();
1072 // TODO(b/64750076): Check if calling pid should really be -1.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001073 final int res = getActivityStartController()
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001074 .obtainStarter(intent, "startNextMatchingActivity")
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001075 .setCaller(r.app.getThread())
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001076 .setResolvedType(r.resolvedType)
1077 .setActivityInfo(aInfo)
1078 .setResultTo(resultTo != null ? resultTo.appToken : null)
1079 .setResultWho(resultWho)
1080 .setRequestCode(requestCode)
1081 .setCallingPid(-1)
1082 .setCallingUid(r.launchedFromUid)
1083 .setCallingPackage(r.launchedFromPackage)
1084 .setRealCallingPid(-1)
1085 .setRealCallingUid(r.launchedFromUid)
1086 .setActivityOptions(options)
1087 .execute();
1088 Binder.restoreCallingIdentity(origId);
1089
1090 r.finishing = wasFinishing;
1091 if (res != ActivityManager.START_SUCCESS) {
1092 return false;
1093 }
1094 return true;
1095 }
1096 }
1097
1098 @Override
1099 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage,
1100 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
1101 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) {
1102 final WaitResult res = new WaitResult();
1103 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001104 enforceNotIsolatedCaller("startActivityAndWait");
1105 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
1106 userId, "startActivityAndWait");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001107 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001108 getActivityStartController().obtainStarter(intent, "startActivityAndWait")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001109 .setCaller(caller)
1110 .setCallingPackage(callingPackage)
1111 .setResolvedType(resolvedType)
1112 .setResultTo(resultTo)
1113 .setResultWho(resultWho)
1114 .setRequestCode(requestCode)
1115 .setStartFlags(startFlags)
1116 .setActivityOptions(bOptions)
1117 .setMayWait(userId)
1118 .setProfilerInfo(profilerInfo)
1119 .setWaitResult(res)
1120 .execute();
1121 }
1122 return res;
1123 }
1124
1125 @Override
1126 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage,
1127 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
1128 int startFlags, Configuration config, Bundle bOptions, int userId) {
1129 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001130 enforceNotIsolatedCaller("startActivityWithConfig");
1131 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId,
1132 "startActivityWithConfig");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001133 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001134 return getActivityStartController().obtainStarter(intent, "startActivityWithConfig")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001135 .setCaller(caller)
1136 .setCallingPackage(callingPackage)
1137 .setResolvedType(resolvedType)
1138 .setResultTo(resultTo)
1139 .setResultWho(resultWho)
1140 .setRequestCode(requestCode)
1141 .setStartFlags(startFlags)
1142 .setGlobalConfiguration(config)
1143 .setActivityOptions(bOptions)
1144 .setMayWait(userId)
1145 .execute();
1146 }
1147 }
1148
1149 @Override
1150 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage,
1151 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
1152 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, boolean ignoreTargetSecurity,
1153 int userId) {
1154
1155 // This is very dangerous -- it allows you to perform a start activity (including
1156 // permission grants) as any app that may launch one of your own activities. So
1157 // we will only allow this to be done from activities that are part of the core framework,
1158 // and then only when they are running as the system.
1159 final ActivityRecord sourceRecord;
1160 final int targetUid;
1161 final String targetPackage;
1162 final boolean isResolver;
1163 synchronized (mGlobalLock) {
1164 if (resultTo == null) {
1165 throw new SecurityException("Must be called from an activity");
1166 }
1167 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo);
1168 if (sourceRecord == null) {
1169 throw new SecurityException("Called with bad activity token: " + resultTo);
1170 }
1171 if (!sourceRecord.info.packageName.equals("android")) {
1172 throw new SecurityException(
1173 "Must be called from an activity that is declared in the android package");
1174 }
1175 if (sourceRecord.app == null) {
1176 throw new SecurityException("Called without a process attached to activity");
1177 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001178 if (UserHandle.getAppId(sourceRecord.app.mUid) != SYSTEM_UID) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001179 // This is still okay, as long as this activity is running under the
1180 // uid of the original calling activity.
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001181 if (sourceRecord.app.mUid != sourceRecord.launchedFromUid) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001182 throw new SecurityException(
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001183 "Calling activity in uid " + sourceRecord.app.mUid
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001184 + " must be system uid or original calling uid "
1185 + sourceRecord.launchedFromUid);
1186 }
1187 }
1188 if (ignoreTargetSecurity) {
1189 if (intent.getComponent() == null) {
1190 throw new SecurityException(
1191 "Component must be specified with ignoreTargetSecurity");
1192 }
1193 if (intent.getSelector() != null) {
1194 throw new SecurityException(
1195 "Selector not allowed with ignoreTargetSecurity");
1196 }
1197 }
1198 targetUid = sourceRecord.launchedFromUid;
1199 targetPackage = sourceRecord.launchedFromPackage;
1200 isResolver = sourceRecord.isResolverOrChildActivity();
1201 }
1202
1203 if (userId == UserHandle.USER_NULL) {
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001204 userId = UserHandle.getUserId(sourceRecord.app.mUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001205 }
1206
1207 // TODO: Switch to user app stacks here.
1208 try {
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001209 return getActivityStartController().obtainStarter(intent, "startActivityAsCaller")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001210 .setCallingUid(targetUid)
1211 .setCallingPackage(targetPackage)
1212 .setResolvedType(resolvedType)
1213 .setResultTo(resultTo)
1214 .setResultWho(resultWho)
1215 .setRequestCode(requestCode)
1216 .setStartFlags(startFlags)
1217 .setActivityOptions(bOptions)
1218 .setMayWait(userId)
1219 .setIgnoreTargetSecurity(ignoreTargetSecurity)
1220 .setFilterCallingUid(isResolver ? 0 /* system */ : targetUid)
1221 .execute();
1222 } catch (SecurityException e) {
1223 // XXX need to figure out how to propagate to original app.
1224 // A SecurityException here is generally actually a fault of the original
1225 // calling activity (such as a fairly granting permissions), so propagate it
1226 // back to them.
1227 /*
1228 StringBuilder msg = new StringBuilder();
1229 msg.append("While launching");
1230 msg.append(intent.toString());
1231 msg.append(": ");
1232 msg.append(e.getMessage());
1233 */
1234 throw e;
1235 }
1236 }
1237
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001238 int handleIncomingUser(int callingPid, int callingUid, int userId, String name) {
1239 return mAmInternal.handleIncomingUser(callingPid, callingUid, userId, false /* allowAll */,
1240 ALLOW_FULL_ONLY, name, null /* callerPackage */);
1241 }
1242
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001243 @Override
1244 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid,
1245 Intent intent, String resolvedType, IVoiceInteractionSession session,
1246 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo,
1247 Bundle bOptions, int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001248 mAmInternal.enforceCallingPermission(BIND_VOICE_INTERACTION, "startVoiceActivity()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001249 if (session == null || interactor == null) {
1250 throw new NullPointerException("null session or interactor");
1251 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001252 userId = handleIncomingUser(callingPid, callingUid, userId, "startVoiceActivity");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001253 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001254 return getActivityStartController().obtainStarter(intent, "startVoiceActivity")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001255 .setCallingUid(callingUid)
1256 .setCallingPackage(callingPackage)
1257 .setResolvedType(resolvedType)
1258 .setVoiceSession(session)
1259 .setVoiceInteractor(interactor)
1260 .setStartFlags(startFlags)
1261 .setProfilerInfo(profilerInfo)
1262 .setActivityOptions(bOptions)
1263 .setMayWait(userId)
1264 .execute();
1265 }
1266
1267 @Override
1268 public int startAssistantActivity(String callingPackage, int callingPid, int callingUid,
1269 Intent intent, String resolvedType, Bundle bOptions, int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001270 mAmInternal.enforceCallingPermission(BIND_VOICE_INTERACTION, "startAssistantActivity()");
1271 userId = handleIncomingUser(callingPid, callingUid, userId, "startAssistantActivity");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001272
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001273 return getActivityStartController().obtainStarter(intent, "startAssistantActivity")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001274 .setCallingUid(callingUid)
1275 .setCallingPackage(callingPackage)
1276 .setResolvedType(resolvedType)
1277 .setActivityOptions(bOptions)
1278 .setMayWait(userId)
1279 .execute();
1280 }
1281
1282 @Override
1283 public void startRecentsActivity(Intent intent, IAssistDataReceiver assistDataReceiver,
1284 IRecentsAnimationRunner recentsAnimationRunner) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001285 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "startRecentsActivity()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001286 final int callingPid = Binder.getCallingPid();
1287 final long origId = Binder.clearCallingIdentity();
1288 try {
1289 synchronized (mGlobalLock) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07001290 final ComponentName recentsComponent = mRecentTasks.getRecentsComponent();
1291 final int recentsUid = mRecentTasks.getRecentsComponentUid();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001292
1293 // Start a new recents animation
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001294 final RecentsAnimation anim = new RecentsAnimation(this, mStackSupervisor,
1295 getActivityStartController(), mWindowManager, callingPid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001296 anim.startRecentsActivity(intent, recentsAnimationRunner, recentsComponent,
1297 recentsUid, assistDataReceiver);
1298 }
1299 } finally {
1300 Binder.restoreCallingIdentity(origId);
1301 }
1302 }
1303
1304 @Override
1305 public final int startActivityFromRecents(int taskId, Bundle bOptions) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001306 enforceCallerIsRecentsOrHasPermission(START_TASKS_FROM_RECENTS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001307 "startActivityFromRecents()");
1308
1309 final int callingPid = Binder.getCallingPid();
1310 final int callingUid = Binder.getCallingUid();
1311 final SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(bOptions);
1312 final long origId = Binder.clearCallingIdentity();
1313 try {
1314 synchronized (mGlobalLock) {
1315 return mStackSupervisor.startActivityFromRecents(callingPid, callingUid, taskId,
1316 safeOptions);
1317 }
1318 } finally {
1319 Binder.restoreCallingIdentity(origId);
1320 }
1321 }
1322
1323 /**
1324 * This is the internal entry point for handling Activity.finish().
1325 *
1326 * @param token The Binder token referencing the Activity we want to finish.
1327 * @param resultCode Result code, if any, from this Activity.
1328 * @param resultData Result data (Intent), if any, from this Activity.
1329 * @param finishTask Whether to finish the task associated with this Activity.
1330 *
1331 * @return Returns true if the activity successfully finished, or false if it is still running.
1332 */
1333 @Override
1334 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData,
1335 int finishTask) {
1336 // Refuse possible leaked file descriptors
1337 if (resultData != null && resultData.hasFileDescriptors()) {
1338 throw new IllegalArgumentException("File descriptors passed in Intent");
1339 }
1340
1341 synchronized (mGlobalLock) {
1342 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1343 if (r == null) {
1344 return true;
1345 }
1346 // Keep track of the root activity of the task before we finish it
1347 TaskRecord tr = r.getTask();
1348 ActivityRecord rootR = tr.getRootActivity();
1349 if (rootR == null) {
1350 Slog.w(TAG, "Finishing task with all activities already finished");
1351 }
1352 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps can
1353 // finish.
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07001354 if (getLockTaskController().activityBlockedFromFinish(r)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001355 return false;
1356 }
1357
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001358 // TODO: There is a dup. of this block of code in ActivityStack.navigateUpToLocked
1359 // We should consolidate.
1360 if (mController != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001361 // Find the first activity that is not finishing.
1362 ActivityRecord next = r.getStack().topRunningActivityLocked(token, 0);
1363 if (next != null) {
1364 // ask watcher if this is allowed
1365 boolean resumeOK = true;
1366 try {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001367 resumeOK = mController.activityResuming(next.packageName);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001368 } catch (RemoteException e) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001369 mController = null;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001370 Watchdog.getInstance().setActivityController(null);
1371 }
1372
1373 if (!resumeOK) {
1374 Slog.i(TAG, "Not finishing activity because controller resumed");
1375 return false;
1376 }
1377 }
1378 }
1379 final long origId = Binder.clearCallingIdentity();
1380 try {
1381 boolean res;
1382 final boolean finishWithRootActivity =
1383 finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY;
1384 if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY
1385 || (finishWithRootActivity && r == rootR)) {
1386 // If requested, remove the task that is associated to this activity only if it
1387 // was the root activity in the task. The result code and data is ignored
1388 // because we don't support returning them across task boundaries. Also, to
1389 // keep backwards compatibility we remove the task from recents when finishing
1390 // task with root activity.
1391 res = mStackSupervisor.removeTaskByIdLocked(tr.taskId, false,
1392 finishWithRootActivity, "finish-activity");
1393 if (!res) {
1394 Slog.i(TAG, "Removing task failed to finish activity");
1395 }
Garfield Tan2746ab52018-07-25 12:33:01 -07001396 // Explicitly dismissing the activity so reset its relaunch flag.
Wale Ogunwale64258362018-10-16 15:13:37 -07001397 r.mRelaunchReason = RELAUNCH_REASON_NONE;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001398 } else {
1399 res = tr.getStack().requestFinishActivityLocked(token, resultCode,
1400 resultData, "app-request", true);
1401 if (!res) {
1402 Slog.i(TAG, "Failed to finish by app-request");
1403 }
1404 }
1405 return res;
1406 } finally {
1407 Binder.restoreCallingIdentity(origId);
1408 }
1409 }
1410 }
1411
1412 @Override
1413 public boolean finishActivityAffinity(IBinder token) {
1414 synchronized (mGlobalLock) {
1415 final long origId = Binder.clearCallingIdentity();
1416 try {
1417 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1418 if (r == null) {
1419 return false;
1420 }
1421
1422 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps
1423 // can finish.
1424 final TaskRecord task = r.getTask();
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07001425 if (getLockTaskController().activityBlockedFromFinish(r)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001426 return false;
1427 }
1428 return task.getStack().finishActivityAffinityLocked(r);
1429 } finally {
1430 Binder.restoreCallingIdentity(origId);
1431 }
1432 }
1433 }
1434
1435 @Override
1436 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) {
1437 final long origId = Binder.clearCallingIdentity();
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001438 try {
1439 WindowProcessController proc = null;
1440 synchronized (mGlobalLock) {
1441 ActivityStack stack = ActivityRecord.getStackLocked(token);
1442 if (stack == null) {
1443 return;
1444 }
1445 final ActivityRecord r = mStackSupervisor.activityIdleInternalLocked(token,
1446 false /* fromTimeout */, false /* processPausingActivities */, config);
1447 if (r != null) {
1448 proc = r.app;
1449 }
1450 if (stopProfiling && proc != null) {
1451 proc.clearProfilerIfNeeded();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001452 }
1453 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001454 } finally {
1455 Binder.restoreCallingIdentity(origId);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001456 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001457 }
1458
1459 @Override
1460 public final void activityResumed(IBinder token) {
1461 final long origId = Binder.clearCallingIdentity();
1462 synchronized (mGlobalLock) {
1463 ActivityRecord.activityResumedLocked(token);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001464 mWindowManager.notifyAppResumedFinished(token);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001465 }
1466 Binder.restoreCallingIdentity(origId);
1467 }
1468
1469 @Override
1470 public final void activityPaused(IBinder token) {
1471 final long origId = Binder.clearCallingIdentity();
1472 synchronized (mGlobalLock) {
1473 ActivityStack stack = ActivityRecord.getStackLocked(token);
1474 if (stack != null) {
1475 stack.activityPausedLocked(token, false);
1476 }
1477 }
1478 Binder.restoreCallingIdentity(origId);
1479 }
1480
1481 @Override
1482 public final void activityStopped(IBinder token, Bundle icicle,
1483 PersistableBundle persistentState, CharSequence description) {
1484 if (DEBUG_ALL) Slog.v(TAG, "Activity stopped: token=" + token);
1485
1486 // Refuse possible leaked file descriptors
1487 if (icicle != null && icicle.hasFileDescriptors()) {
1488 throw new IllegalArgumentException("File descriptors passed in Bundle");
1489 }
1490
1491 final long origId = Binder.clearCallingIdentity();
1492
1493 synchronized (mGlobalLock) {
1494 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1495 if (r != null) {
1496 r.activityStoppedLocked(icicle, persistentState, description);
1497 }
1498 }
1499
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001500 mAmInternal.trimApplications();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001501
1502 Binder.restoreCallingIdentity(origId);
1503 }
1504
1505 @Override
1506 public final void activityDestroyed(IBinder token) {
1507 if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "ACTIVITY DESTROYED: " + token);
1508 synchronized (mGlobalLock) {
1509 ActivityStack stack = ActivityRecord.getStackLocked(token);
1510 if (stack != null) {
1511 stack.activityDestroyedLocked(token, "activityDestroyed");
1512 }
1513 }
1514 }
1515
1516 @Override
1517 public final void activityRelaunched(IBinder token) {
1518 final long origId = Binder.clearCallingIdentity();
1519 synchronized (mGlobalLock) {
1520 mStackSupervisor.activityRelaunchedLocked(token);
1521 }
1522 Binder.restoreCallingIdentity(origId);
1523 }
1524
1525 public final void activitySlept(IBinder token) {
1526 if (DEBUG_ALL) Slog.v(TAG, "Activity slept: token=" + token);
1527
1528 final long origId = Binder.clearCallingIdentity();
1529
1530 synchronized (mGlobalLock) {
1531 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1532 if (r != null) {
1533 mStackSupervisor.activitySleptLocked(r);
1534 }
1535 }
1536
1537 Binder.restoreCallingIdentity(origId);
1538 }
1539
1540 @Override
1541 public void setRequestedOrientation(IBinder token, int requestedOrientation) {
1542 synchronized (mGlobalLock) {
1543 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1544 if (r == null) {
1545 return;
1546 }
1547 final long origId = Binder.clearCallingIdentity();
1548 try {
1549 r.setRequestedOrientation(requestedOrientation);
1550 } finally {
1551 Binder.restoreCallingIdentity(origId);
1552 }
1553 }
1554 }
1555
1556 @Override
1557 public int getRequestedOrientation(IBinder token) {
1558 synchronized (mGlobalLock) {
1559 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1560 if (r == null) {
1561 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
1562 }
1563 return r.getRequestedOrientation();
1564 }
1565 }
1566
1567 @Override
1568 public void setImmersive(IBinder token, boolean immersive) {
1569 synchronized (mGlobalLock) {
1570 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1571 if (r == null) {
1572 throw new IllegalArgumentException();
1573 }
1574 r.immersive = immersive;
1575
1576 // update associated state if we're frontmost
Andrii Kulian52d255c2018-07-13 11:32:19 -07001577 if (r.isResumedActivityOnDisplay()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001578 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, "Frontmost changed immersion: "+ r);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001579 applyUpdateLockStateLocked(r);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001580 }
1581 }
1582 }
1583
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001584 void applyUpdateLockStateLocked(ActivityRecord r) {
1585 // Modifications to the UpdateLock state are done on our handler, outside
1586 // the activity manager's locks. The new state is determined based on the
1587 // state *now* of the relevant activity record. The object is passed to
1588 // the handler solely for logging detail, not to be consulted/modified.
1589 final boolean nextState = r != null && r.immersive;
1590 mH.post(() -> {
1591 if (mUpdateLock.isHeld() != nextState) {
1592 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE,
1593 "Applying new update lock state '" + nextState + "' for " + r);
1594 if (nextState) {
1595 mUpdateLock.acquire();
1596 } else {
1597 mUpdateLock.release();
1598 }
1599 }
1600 });
1601 }
1602
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001603 @Override
1604 public boolean isImmersive(IBinder token) {
1605 synchronized (mGlobalLock) {
1606 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1607 if (r == null) {
1608 throw new IllegalArgumentException();
1609 }
1610 return r.immersive;
1611 }
1612 }
1613
1614 @Override
1615 public boolean isTopActivityImmersive() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001616 enforceNotIsolatedCaller("isTopActivityImmersive");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001617 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001618 final ActivityRecord r = getTopDisplayFocusedStack().topRunningActivityLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001619 return (r != null) ? r.immersive : false;
1620 }
1621 }
1622
1623 @Override
1624 public void overridePendingTransition(IBinder token, String packageName,
1625 int enterAnim, int exitAnim) {
1626 synchronized (mGlobalLock) {
1627 ActivityRecord self = ActivityRecord.isInStackLocked(token);
1628 if (self == null) {
1629 return;
1630 }
1631
1632 final long origId = Binder.clearCallingIdentity();
1633
1634 if (self.isState(
1635 ActivityStack.ActivityState.RESUMED, ActivityStack.ActivityState.PAUSING)) {
lumark588a3e82018-07-20 18:53:54 +08001636 self.getDisplay().getWindowContainerController().overridePendingAppTransition(
1637 packageName, enterAnim, exitAnim, null);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001638 }
1639
1640 Binder.restoreCallingIdentity(origId);
1641 }
1642 }
1643
1644 @Override
1645 public int getFrontActivityScreenCompatMode() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001646 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001647 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001648 final ActivityRecord r = getTopDisplayFocusedStack().topRunningActivityLocked();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001649 if (r == null) {
1650 return ActivityManager.COMPAT_MODE_UNKNOWN;
1651 }
Wale Ogunwale53783742018-09-16 10:21:51 -07001652 return mCompatModePackages.computeCompatModeLocked(r.info.applicationInfo);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001653 }
1654 }
1655
1656 @Override
1657 public void setFrontActivityScreenCompatMode(int mode) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001658 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001659 "setFrontActivityScreenCompatMode");
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001660 ApplicationInfo ai;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001661 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001662 final ActivityRecord r = getTopDisplayFocusedStack().topRunningActivityLocked();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001663 if (r == null) {
1664 Slog.w(TAG, "setFrontActivityScreenCompatMode failed: no top activity");
1665 return;
1666 }
1667 ai = r.info.applicationInfo;
Wale Ogunwale53783742018-09-16 10:21:51 -07001668 mCompatModePackages.setPackageScreenCompatModeLocked(ai, mode);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001669 }
1670 }
1671
1672 @Override
1673 public int getLaunchedFromUid(IBinder activityToken) {
1674 ActivityRecord srec;
1675 synchronized (mGlobalLock) {
1676 srec = ActivityRecord.forTokenLocked(activityToken);
1677 }
1678 if (srec == null) {
1679 return -1;
1680 }
1681 return srec.launchedFromUid;
1682 }
1683
1684 @Override
1685 public String getLaunchedFromPackage(IBinder activityToken) {
1686 ActivityRecord srec;
1687 synchronized (mGlobalLock) {
1688 srec = ActivityRecord.forTokenLocked(activityToken);
1689 }
1690 if (srec == null) {
1691 return null;
1692 }
1693 return srec.launchedFromPackage;
1694 }
1695
1696 @Override
1697 public boolean convertFromTranslucent(IBinder token) {
1698 final long origId = Binder.clearCallingIdentity();
1699 try {
1700 synchronized (mGlobalLock) {
1701 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1702 if (r == null) {
1703 return false;
1704 }
1705 final boolean translucentChanged = r.changeWindowTranslucency(true);
1706 if (translucentChanged) {
1707 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
1708 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001709 mWindowManager.setAppFullscreen(token, true);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001710 return translucentChanged;
1711 }
1712 } finally {
1713 Binder.restoreCallingIdentity(origId);
1714 }
1715 }
1716
1717 @Override
1718 public boolean convertToTranslucent(IBinder token, Bundle options) {
1719 SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(options);
1720 final long origId = Binder.clearCallingIdentity();
1721 try {
1722 synchronized (mGlobalLock) {
1723 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1724 if (r == null) {
1725 return false;
1726 }
1727 final TaskRecord task = r.getTask();
1728 int index = task.mActivities.lastIndexOf(r);
1729 if (index > 0) {
1730 ActivityRecord under = task.mActivities.get(index - 1);
1731 under.returningOptions = safeOptions != null ? safeOptions.getOptions(r) : null;
1732 }
1733 final boolean translucentChanged = r.changeWindowTranslucency(false);
1734 if (translucentChanged) {
1735 r.getStack().convertActivityToTranslucent(r);
1736 }
1737 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001738 mWindowManager.setAppFullscreen(token, false);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001739 return translucentChanged;
1740 }
1741 } finally {
1742 Binder.restoreCallingIdentity(origId);
1743 }
1744 }
1745
1746 @Override
1747 public void notifyActivityDrawn(IBinder token) {
1748 if (DEBUG_VISIBILITY) Slog.d(TAG_VISIBILITY, "notifyActivityDrawn: token=" + token);
1749 synchronized (mGlobalLock) {
1750 ActivityRecord r = mStackSupervisor.isInAnyStackLocked(token);
1751 if (r != null) {
1752 r.getStack().notifyActivityDrawnLocked(r);
1753 }
1754 }
1755 }
1756
1757 @Override
1758 public void reportActivityFullyDrawn(IBinder token, boolean restoredFromBundle) {
1759 synchronized (mGlobalLock) {
1760 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1761 if (r == null) {
1762 return;
1763 }
1764 r.reportFullyDrawnLocked(restoredFromBundle);
1765 }
1766 }
1767
1768 @Override
1769 public int getActivityDisplayId(IBinder activityToken) throws RemoteException {
1770 synchronized (mGlobalLock) {
1771 final ActivityStack stack = ActivityRecord.getStackLocked(activityToken);
1772 if (stack != null && stack.mDisplayId != INVALID_DISPLAY) {
1773 return stack.mDisplayId;
1774 }
1775 return DEFAULT_DISPLAY;
1776 }
1777 }
1778
1779 @Override
1780 public ActivityManager.StackInfo getFocusedStackInfo() throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001781 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001782 long ident = Binder.clearCallingIdentity();
1783 try {
1784 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001785 ActivityStack focusedStack = getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001786 if (focusedStack != null) {
1787 return mStackSupervisor.getStackInfo(focusedStack.mStackId);
1788 }
1789 return null;
1790 }
1791 } finally {
1792 Binder.restoreCallingIdentity(ident);
1793 }
1794 }
1795
1796 @Override
1797 public void setFocusedStack(int stackId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001798 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001799 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedStack: stackId=" + stackId);
1800 final long callingId = Binder.clearCallingIdentity();
1801 try {
1802 synchronized (mGlobalLock) {
1803 final ActivityStack stack = mStackSupervisor.getStack(stackId);
1804 if (stack == null) {
1805 Slog.w(TAG, "setFocusedStack: No stack with id=" + stackId);
1806 return;
1807 }
1808 final ActivityRecord r = stack.topRunningActivityLocked();
Louis Chang19443452018-10-09 12:10:21 +08001809 if (r != null && r.moveFocusableActivityToTop("setFocusedStack")) {
Andrii Kulianab132ee2018-07-24 22:10:21 +08001810 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001811 }
1812 }
1813 } finally {
1814 Binder.restoreCallingIdentity(callingId);
1815 }
1816 }
1817
1818 @Override
1819 public void setFocusedTask(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001820 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedTask()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001821 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedTask: taskId=" + taskId);
1822 final long callingId = Binder.clearCallingIdentity();
1823 try {
1824 synchronized (mGlobalLock) {
Riddle Hsu090ac6f2018-10-31 12:55:29 +08001825 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
1826 MATCH_TASK_IN_STACKS_ONLY);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001827 if (task == null) {
1828 return;
1829 }
1830 final ActivityRecord r = task.topRunningActivityLocked();
Louis Chang19443452018-10-09 12:10:21 +08001831 if (r != null && r.moveFocusableActivityToTop("setFocusedTask")) {
Andrii Kulianab132ee2018-07-24 22:10:21 +08001832 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001833 }
1834 }
1835 } finally {
1836 Binder.restoreCallingIdentity(callingId);
1837 }
1838 }
1839
1840 @Override
1841 public boolean removeTask(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001842 enforceCallerIsRecentsOrHasPermission(REMOVE_TASKS, "removeTask()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001843 synchronized (mGlobalLock) {
1844 final long ident = Binder.clearCallingIdentity();
1845 try {
1846 return mStackSupervisor.removeTaskByIdLocked(taskId, true, REMOVE_FROM_RECENTS,
1847 "remove-task");
1848 } finally {
1849 Binder.restoreCallingIdentity(ident);
1850 }
1851 }
1852 }
1853
1854 @Override
Winson Chunge6439102018-07-30 15:48:01 -07001855 public void removeAllVisibleRecentTasks() {
1856 enforceCallerIsRecentsOrHasPermission(REMOVE_TASKS, "removeAllVisibleRecentTasks()");
1857 synchronized (mGlobalLock) {
1858 final long ident = Binder.clearCallingIdentity();
1859 try {
1860 getRecentTasks().removeAllVisibleTasks();
1861 } finally {
1862 Binder.restoreCallingIdentity(ident);
1863 }
1864 }
1865 }
1866
1867 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001868 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) {
1869 synchronized (mGlobalLock) {
1870 final ActivityRecord srec = ActivityRecord.forTokenLocked(token);
1871 if (srec != null) {
1872 return srec.getStack().shouldUpRecreateTaskLocked(srec, destAffinity);
1873 }
1874 }
1875 return false;
1876 }
1877
1878 @Override
1879 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode,
1880 Intent resultData) {
1881
1882 synchronized (mGlobalLock) {
1883 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
1884 if (r != null) {
1885 return r.getStack().navigateUpToLocked(r, destIntent, resultCode, resultData);
1886 }
1887 return false;
1888 }
1889 }
1890
1891 /**
1892 * Attempts to move a task backwards in z-order (the order of activities within the task is
1893 * unchanged).
1894 *
1895 * There are several possible results of this call:
1896 * - if the task is locked, then we will show the lock toast
1897 * - if there is a task behind the provided task, then that task is made visible and resumed as
1898 * this task is moved to the back
1899 * - otherwise, if there are no other tasks in the stack:
1900 * - if this task is in the pinned stack, then we remove the stack completely, which will
1901 * have the effect of moving the task to the top or bottom of the fullscreen stack
1902 * (depending on whether it is visible)
1903 * - otherwise, we simply return home and hide this task
1904 *
1905 * @param token A reference to the activity we wish to move
1906 * @param nonRoot If false then this only works if the activity is the root
1907 * of a task; if true it will work for any activity in a task.
1908 * @return Returns true if the move completed, false if not.
1909 */
1910 @Override
1911 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001912 enforceNotIsolatedCaller("moveActivityTaskToBack");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001913 synchronized (mGlobalLock) {
1914 final long origId = Binder.clearCallingIdentity();
1915 try {
1916 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot);
1917 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
1918 if (task != null) {
1919 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId);
1920 }
1921 } finally {
1922 Binder.restoreCallingIdentity(origId);
1923 }
1924 }
1925 return false;
1926 }
1927
1928 @Override
1929 public Rect getTaskBounds(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001930 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getTaskBounds()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001931 long ident = Binder.clearCallingIdentity();
1932 Rect rect = new Rect();
1933 try {
1934 synchronized (mGlobalLock) {
1935 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
1936 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
1937 if (task == null) {
1938 Slog.w(TAG, "getTaskBounds: taskId=" + taskId + " not found");
1939 return rect;
1940 }
1941 if (task.getStack() != null) {
1942 // Return the bounds from window manager since it will be adjusted for various
1943 // things like the presense of a docked stack for tasks that aren't resizeable.
1944 task.getWindowContainerBounds(rect);
1945 } else {
1946 // Task isn't in window manager yet since it isn't associated with a stack.
1947 // Return the persist value from activity manager
1948 if (!task.matchParentBounds()) {
1949 rect.set(task.getBounds());
1950 } else if (task.mLastNonFullscreenBounds != null) {
1951 rect.set(task.mLastNonFullscreenBounds);
1952 }
1953 }
1954 }
1955 } finally {
1956 Binder.restoreCallingIdentity(ident);
1957 }
1958 return rect;
1959 }
1960
1961 @Override
1962 public ActivityManager.TaskDescription getTaskDescription(int id) {
1963 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001964 enforceCallerIsRecentsOrHasPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001965 MANAGE_ACTIVITY_STACKS, "getTaskDescription()");
1966 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(id,
1967 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
1968 if (tr != null) {
1969 return tr.lastTaskDescription;
1970 }
1971 }
1972 return null;
1973 }
1974
1975 @Override
Wale Ogunwale65ebd952018-04-25 15:41:44 -07001976 public void setTaskWindowingMode(int taskId, int windowingMode, boolean toTop) {
1977 if (windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) {
1978 setTaskWindowingModeSplitScreenPrimary(taskId, SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT,
1979 toTop, ANIMATE, null /* initialBounds */, true /* showRecents */);
1980 return;
1981 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001982 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "setTaskWindowingMode()");
Wale Ogunwale65ebd952018-04-25 15:41:44 -07001983 synchronized (mGlobalLock) {
1984 final long ident = Binder.clearCallingIdentity();
1985 try {
Riddle Hsu090ac6f2018-10-31 12:55:29 +08001986 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
1987 MATCH_TASK_IN_STACKS_ONLY);
Wale Ogunwale65ebd952018-04-25 15:41:44 -07001988 if (task == null) {
1989 Slog.w(TAG, "setTaskWindowingMode: No task for id=" + taskId);
1990 return;
1991 }
1992
1993 if (DEBUG_STACK) Slog.d(TAG_STACK, "setTaskWindowingMode: moving task=" + taskId
1994 + " to windowingMode=" + windowingMode + " toTop=" + toTop);
1995
1996 if (!task.isActivityTypeStandardOrUndefined()) {
1997 throw new IllegalArgumentException("setTaskWindowingMode: Attempt to move"
1998 + " non-standard task " + taskId + " to windowing mode="
1999 + windowingMode);
2000 }
2001
2002 final ActivityStack stack = task.getStack();
2003 if (toTop) {
2004 stack.moveToFront("setTaskWindowingMode", task);
2005 }
2006 stack.setWindowingMode(windowingMode);
2007 } finally {
2008 Binder.restoreCallingIdentity(ident);
2009 }
2010 }
2011 }
2012
2013 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002014 public String getCallingPackage(IBinder token) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002015 synchronized (mGlobalLock) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002016 ActivityRecord r = getCallingRecordLocked(token);
2017 return r != null ? r.info.packageName : null;
2018 }
2019 }
2020
2021 @Override
2022 public ComponentName getCallingActivity(IBinder token) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002023 synchronized (mGlobalLock) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002024 ActivityRecord r = getCallingRecordLocked(token);
2025 return r != null ? r.intent.getComponent() : null;
2026 }
2027 }
2028
2029 private ActivityRecord getCallingRecordLocked(IBinder token) {
2030 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2031 if (r == null) {
2032 return null;
2033 }
2034 return r.resultTo;
2035 }
2036
2037 @Override
2038 public void unhandledBack() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002039 mAmInternal.enforceCallingPermission(android.Manifest.permission.FORCE_BACK, "unhandledBack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002040
2041 synchronized (mGlobalLock) {
2042 final long origId = Binder.clearCallingIdentity();
2043 try {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07002044 getTopDisplayFocusedStack().unhandledBackLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002045 } finally {
2046 Binder.restoreCallingIdentity(origId);
2047 }
2048 }
2049 }
2050
2051 /**
2052 * TODO: Add mController hook
2053 */
2054 @Override
2055 public void moveTaskToFront(int taskId, int flags, Bundle bOptions) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002056 mAmInternal.enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, "moveTaskToFront()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002057
2058 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToFront: moving taskId=" + taskId);
2059 synchronized (mGlobalLock) {
2060 moveTaskToFrontLocked(taskId, flags, SafeActivityOptions.fromBundle(bOptions),
2061 false /* fromRecents */);
2062 }
2063 }
2064
2065 void moveTaskToFrontLocked(int taskId, int flags, SafeActivityOptions options,
2066 boolean fromRecents) {
2067
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002068 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(),
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002069 Binder.getCallingUid(), -1, -1, "Task to front")) {
2070 SafeActivityOptions.abort(options);
2071 return;
2072 }
2073 final long origId = Binder.clearCallingIdentity();
2074 try {
2075 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2076 if (task == null) {
2077 Slog.d(TAG, "Could not find task for id: "+ taskId);
Winson Chungd0243682018-09-25 18:11:54 -07002078 SafeActivityOptions.abort(options);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002079 return;
2080 }
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002081 if (getLockTaskController().isLockTaskModeViolation(task)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002082 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode");
Winson Chungd0243682018-09-25 18:11:54 -07002083 SafeActivityOptions.abort(options);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002084 return;
2085 }
2086 ActivityOptions realOptions = options != null
2087 ? options.getOptions(mStackSupervisor)
2088 : null;
2089 mStackSupervisor.findTaskToMoveToFront(task, flags, realOptions, "moveTaskToFront",
2090 false /* forceNonResizable */);
2091
2092 final ActivityRecord topActivity = task.getTopActivity();
2093 if (topActivity != null) {
2094
2095 // We are reshowing a task, use a starting window to hide the initial draw delay
2096 // so the transition can start earlier.
2097 topActivity.showStartingWindow(null /* prev */, false /* newTask */,
2098 true /* taskSwitch */, fromRecents);
2099 }
2100 } finally {
2101 Binder.restoreCallingIdentity(origId);
2102 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002103 }
2104
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002105 boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid,
2106 int callingPid, int callingUid, String name) {
2107 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) {
2108 return true;
2109 }
2110
2111 if (getRecentTasks().isCallerRecents(sourceUid)) {
2112 return true;
2113 }
2114
2115 int perm = checkComponentPermission(STOP_APP_SWITCHES, sourcePid, sourceUid, -1, true);
2116 if (perm == PackageManager.PERMISSION_GRANTED) {
2117 return true;
2118 }
2119 if (checkAllowAppSwitchUid(sourceUid)) {
2120 return true;
2121 }
2122
2123 // If the actual IPC caller is different from the logical source, then
2124 // also see if they are allowed to control app switches.
2125 if (callingUid != -1 && callingUid != sourceUid) {
2126 perm = checkComponentPermission(STOP_APP_SWITCHES, callingPid, callingUid, -1, true);
2127 if (perm == PackageManager.PERMISSION_GRANTED) {
2128 return true;
2129 }
2130 if (checkAllowAppSwitchUid(callingUid)) {
2131 return true;
2132 }
2133 }
2134
2135 Slog.w(TAG, name + " request from " + sourceUid + " stopped");
2136 return false;
2137 }
2138
2139 private boolean checkAllowAppSwitchUid(int uid) {
2140 ArrayMap<String, Integer> types = mAllowAppSwitchUids.get(UserHandle.getUserId(uid));
2141 if (types != null) {
2142 for (int i = types.size() - 1; i >= 0; i--) {
2143 if (types.valueAt(i).intValue() == uid) {
2144 return true;
2145 }
2146 }
2147 }
2148 return false;
2149 }
2150
2151 @Override
2152 public void setActivityController(IActivityController controller, boolean imAMonkey) {
2153 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER,
2154 "setActivityController()");
2155 synchronized (mGlobalLock) {
2156 mController = controller;
2157 mControllerIsAMonkey = imAMonkey;
2158 Watchdog.getInstance().setActivityController(controller);
2159 }
2160 }
2161
Wale Ogunwale387b34c2018-10-25 19:59:40 -07002162 public boolean isControllerAMonkey() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002163 synchronized (mGlobalLock) {
2164 return mController != null && mControllerIsAMonkey;
2165 }
2166 }
2167
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002168 @Override
2169 public int getTaskForActivity(IBinder token, boolean onlyRoot) {
2170 synchronized (mGlobalLock) {
2171 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot);
2172 }
2173 }
2174
2175 @Override
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002176 public List<ActivityManager.RunningTaskInfo> getTasks(int maxNum) {
2177 return getFilteredTasks(maxNum, ACTIVITY_TYPE_UNDEFINED, WINDOWING_MODE_UNDEFINED);
2178 }
2179
2180 @Override
2181 public List<ActivityManager.RunningTaskInfo> getFilteredTasks(int maxNum,
2182 @WindowConfiguration.ActivityType int ignoreActivityType,
2183 @WindowConfiguration.WindowingMode int ignoreWindowingMode) {
2184 final int callingUid = Binder.getCallingUid();
2185 ArrayList<ActivityManager.RunningTaskInfo> list = new ArrayList<>();
2186
2187 synchronized (mGlobalLock) {
2188 if (DEBUG_ALL) Slog.v(TAG, "getTasks: max=" + maxNum);
2189
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002190 final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(),
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002191 callingUid);
2192 mStackSupervisor.getRunningTasks(maxNum, list, ignoreActivityType,
2193 ignoreWindowingMode, callingUid, allowed);
2194 }
2195
2196 return list;
2197 }
2198
2199 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002200 public final void finishSubActivity(IBinder token, String resultWho, int requestCode) {
2201 synchronized (mGlobalLock) {
2202 final long origId = Binder.clearCallingIdentity();
2203 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2204 if (r != null) {
2205 r.getStack().finishSubActivityLocked(r, resultWho, requestCode);
2206 }
2207 Binder.restoreCallingIdentity(origId);
2208 }
2209 }
2210
2211 @Override
2212 public boolean willActivityBeVisible(IBinder token) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002213 synchronized (mGlobalLock) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002214 ActivityStack stack = ActivityRecord.getStackLocked(token);
2215 if (stack != null) {
2216 return stack.willActivityBeVisibleLocked(token);
2217 }
2218 return false;
2219 }
2220 }
2221
2222 @Override
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002223 public void moveTaskToStack(int taskId, int stackId, boolean toTop) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002224 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToStack()");
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002225 synchronized (mGlobalLock) {
2226 final long ident = Binder.clearCallingIdentity();
2227 try {
2228 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2229 if (task == null) {
2230 Slog.w(TAG, "moveTaskToStack: No task for id=" + taskId);
2231 return;
2232 }
2233
2234 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToStack: moving task=" + taskId
2235 + " to stackId=" + stackId + " toTop=" + toTop);
2236
2237 final ActivityStack stack = mStackSupervisor.getStack(stackId);
2238 if (stack == null) {
2239 throw new IllegalStateException(
2240 "moveTaskToStack: No stack for stackId=" + stackId);
2241 }
2242 if (!stack.isActivityTypeStandardOrUndefined()) {
2243 throw new IllegalArgumentException("moveTaskToStack: Attempt to move task "
2244 + taskId + " to stack " + stackId);
2245 }
2246 if (stack.inSplitScreenPrimaryWindowingMode()) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002247 mWindowManager.setDockedStackCreateState(
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002248 SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT, null /* initialBounds */);
2249 }
2250 task.reparent(stack, toTop, REPARENT_KEEP_STACK_AT_FRONT, ANIMATE, !DEFER_RESUME,
2251 "moveTaskToStack");
2252 } finally {
2253 Binder.restoreCallingIdentity(ident);
2254 }
2255 }
2256 }
2257
2258 @Override
2259 public void resizeStack(int stackId, Rect destBounds, boolean allowResizeInDockedMode,
2260 boolean preserveWindows, boolean animate, int animationDuration) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002261 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()");
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002262
2263 final long ident = Binder.clearCallingIdentity();
2264 try {
2265 synchronized (mGlobalLock) {
2266 if (animate) {
2267 final PinnedActivityStack stack = mStackSupervisor.getStack(stackId);
2268 if (stack == null) {
2269 Slog.w(TAG, "resizeStack: stackId " + stackId + " not found.");
2270 return;
2271 }
2272 if (stack.getWindowingMode() != WINDOWING_MODE_PINNED) {
2273 throw new IllegalArgumentException("Stack: " + stackId
2274 + " doesn't support animated resize.");
2275 }
2276 stack.animateResizePinnedStack(null /* sourceHintBounds */, destBounds,
2277 animationDuration, false /* fromFullscreen */);
2278 } else {
2279 final ActivityStack stack = mStackSupervisor.getStack(stackId);
2280 if (stack == null) {
2281 Slog.w(TAG, "resizeStack: stackId " + stackId + " not found.");
2282 return;
2283 }
2284 mStackSupervisor.resizeStackLocked(stack, destBounds,
2285 null /* tempTaskBounds */, null /* tempTaskInsetBounds */,
2286 preserveWindows, allowResizeInDockedMode, !DEFER_RESUME);
2287 }
2288 }
2289 } finally {
2290 Binder.restoreCallingIdentity(ident);
2291 }
2292 }
2293
2294 /**
2295 * Moves the specified task to the primary-split-screen stack.
2296 *
2297 * @param taskId Id of task to move.
2298 * @param createMode The mode the primary split screen stack should be created in if it doesn't
2299 * exist already. See
2300 * {@link android.app.ActivityTaskManager#SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT}
2301 * and
2302 * {@link android.app.ActivityTaskManager#SPLIT_SCREEN_CREATE_MODE_BOTTOM_OR_RIGHT}
2303 * @param toTop If the task and stack should be moved to the top.
2304 * @param animate Whether we should play an animation for the moving the task.
2305 * @param initialBounds If the primary stack gets created, it will use these bounds for the
2306 * stack. Pass {@code null} to use default bounds.
2307 * @param showRecents If the recents activity should be shown on the other side of the task
2308 * going into split-screen mode.
2309 */
2310 @Override
2311 public boolean setTaskWindowingModeSplitScreenPrimary(int taskId, int createMode,
2312 boolean toTop, boolean animate, Rect initialBounds, boolean showRecents) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002313 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002314 "setTaskWindowingModeSplitScreenPrimary()");
2315 synchronized (mGlobalLock) {
2316 final long ident = Binder.clearCallingIdentity();
2317 try {
Riddle Hsu090ac6f2018-10-31 12:55:29 +08002318 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
2319 MATCH_TASK_IN_STACKS_ONLY);
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002320 if (task == null) {
2321 Slog.w(TAG, "setTaskWindowingModeSplitScreenPrimary: No task for id=" + taskId);
2322 return false;
2323 }
2324 if (DEBUG_STACK) Slog.d(TAG_STACK,
2325 "setTaskWindowingModeSplitScreenPrimary: moving task=" + taskId
2326 + " to createMode=" + createMode + " toTop=" + toTop);
2327 if (!task.isActivityTypeStandardOrUndefined()) {
2328 throw new IllegalArgumentException("setTaskWindowingMode: Attempt to move"
2329 + " non-standard task " + taskId + " to split-screen windowing mode");
2330 }
2331
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002332 mWindowManager.setDockedStackCreateState(createMode, initialBounds);
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002333 final int windowingMode = task.getWindowingMode();
2334 final ActivityStack stack = task.getStack();
2335 if (toTop) {
2336 stack.moveToFront("setTaskWindowingModeSplitScreenPrimary", task);
2337 }
2338 stack.setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, animate, showRecents,
2339 false /* enteringSplitScreenMode */, false /* deferEnsuringVisibility */);
2340 return windowingMode != task.getWindowingMode();
2341 } finally {
2342 Binder.restoreCallingIdentity(ident);
2343 }
2344 }
2345 }
2346
2347 /**
2348 * Removes stacks in the input windowing modes from the system if they are of activity type
2349 * ACTIVITY_TYPE_STANDARD or ACTIVITY_TYPE_UNDEFINED
2350 */
2351 @Override
2352 public void removeStacksInWindowingModes(int[] windowingModes) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002353 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002354 "removeStacksInWindowingModes()");
2355
2356 synchronized (mGlobalLock) {
2357 final long ident = Binder.clearCallingIdentity();
2358 try {
2359 mStackSupervisor.removeStacksInWindowingModes(windowingModes);
2360 } finally {
2361 Binder.restoreCallingIdentity(ident);
2362 }
2363 }
2364 }
2365
2366 @Override
2367 public void removeStacksWithActivityTypes(int[] activityTypes) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002368 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002369 "removeStacksWithActivityTypes()");
2370
2371 synchronized (mGlobalLock) {
2372 final long ident = Binder.clearCallingIdentity();
2373 try {
2374 mStackSupervisor.removeStacksWithActivityTypes(activityTypes);
2375 } finally {
2376 Binder.restoreCallingIdentity(ident);
2377 }
2378 }
2379 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002380
2381 @Override
2382 public ParceledListSlice<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags,
2383 int userId) {
2384 final int callingUid = Binder.getCallingUid();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002385 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, "getRecentTasks");
2386 final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(),
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002387 callingUid);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002388 final boolean detailed = checkGetTasksPermission(
2389 android.Manifest.permission.GET_DETAILED_TASKS, Binder.getCallingPid(),
2390 UserHandle.getAppId(callingUid))
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002391 == PackageManager.PERMISSION_GRANTED;
2392
2393 synchronized (mGlobalLock) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002394 return mRecentTasks.getRecentTasks(maxNum, flags, allowed, detailed, userId,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002395 callingUid);
2396 }
2397 }
2398
2399 @Override
2400 public List<ActivityManager.StackInfo> getAllStackInfos() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002401 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getAllStackInfos()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002402 long ident = Binder.clearCallingIdentity();
2403 try {
2404 synchronized (mGlobalLock) {
2405 return mStackSupervisor.getAllStackInfosLocked();
2406 }
2407 } finally {
2408 Binder.restoreCallingIdentity(ident);
2409 }
2410 }
2411
2412 @Override
2413 public ActivityManager.StackInfo getStackInfo(int windowingMode, int activityType) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002414 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002415 long ident = Binder.clearCallingIdentity();
2416 try {
2417 synchronized (mGlobalLock) {
2418 return mStackSupervisor.getStackInfo(windowingMode, activityType);
2419 }
2420 } finally {
2421 Binder.restoreCallingIdentity(ident);
2422 }
2423 }
2424
2425 @Override
2426 public void cancelRecentsAnimation(boolean restoreHomeStackPosition) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002427 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "cancelRecentsAnimation()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002428 final long callingUid = Binder.getCallingUid();
2429 final long origId = Binder.clearCallingIdentity();
2430 try {
2431 synchronized (mGlobalLock) {
2432 // Cancel the recents animation synchronously (do not hold the WM lock)
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002433 mWindowManager.cancelRecentsAnimationSynchronously(restoreHomeStackPosition
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002434 ? REORDER_MOVE_TO_ORIGINAL_POSITION
2435 : REORDER_KEEP_IN_PLACE, "cancelRecentsAnimation/uid=" + callingUid);
2436 }
2437 } finally {
2438 Binder.restoreCallingIdentity(origId);
2439 }
2440 }
2441
2442 @Override
2443 public void startLockTaskModeByToken(IBinder token) {
2444 synchronized (mGlobalLock) {
2445 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
2446 if (r == null) {
2447 return;
2448 }
2449 startLockTaskModeLocked(r.getTask(), false /* isSystemCaller */);
2450 }
2451 }
2452
2453 @Override
Riddle Hsu090ac6f2018-10-31 12:55:29 +08002454 public void startSystemLockTaskMode(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002455 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startSystemLockTaskMode");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002456 // This makes inner call to look as if it was initiated by system.
2457 long ident = Binder.clearCallingIdentity();
2458 try {
2459 synchronized (mGlobalLock) {
Riddle Hsu090ac6f2018-10-31 12:55:29 +08002460 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
2461 MATCH_TASK_IN_STACKS_ONLY);
2462 if (task == null) {
2463 return;
2464 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002465
2466 // When starting lock task mode the stack must be in front and focused
2467 task.getStack().moveToFront("startSystemLockTaskMode");
2468 startLockTaskModeLocked(task, true /* isSystemCaller */);
2469 }
2470 } finally {
2471 Binder.restoreCallingIdentity(ident);
2472 }
2473 }
2474
2475 @Override
2476 public void stopLockTaskModeByToken(IBinder token) {
2477 synchronized (mGlobalLock) {
2478 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
2479 if (r == null) {
2480 return;
2481 }
2482 stopLockTaskModeInternal(r.getTask(), false /* isSystemCaller */);
2483 }
2484 }
2485
2486 /**
2487 * This API should be called by SystemUI only when user perform certain action to dismiss
2488 * lock task mode. We should only dismiss pinned lock task mode in this case.
2489 */
2490 @Override
2491 public void stopSystemLockTaskMode() throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002492 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "stopSystemLockTaskMode");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002493 stopLockTaskModeInternal(null, true /* isSystemCaller */);
2494 }
2495
2496 private void startLockTaskModeLocked(@Nullable TaskRecord task, boolean isSystemCaller) {
2497 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "startLockTaskModeLocked: " + task);
2498 if (task == null || task.mLockTaskAuth == LOCK_TASK_AUTH_DONT_LOCK) {
2499 return;
2500 }
2501
Andrii Kulian5f750bc2018-07-17 08:57:23 -07002502 final ActivityStack stack = mStackSupervisor.getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002503 if (stack == null || task != stack.topTask()) {
2504 throw new IllegalArgumentException("Invalid task, not in foreground");
2505 }
2506
2507 // {@code isSystemCaller} is used to distinguish whether this request is initiated by the
2508 // system or a specific app.
2509 // * System-initiated requests will only start the pinned mode (screen pinning)
2510 // * App-initiated requests
2511 // - will put the device in fully locked mode (LockTask), if the app is whitelisted
2512 // - will start the pinned mode, otherwise
2513 final int callingUid = Binder.getCallingUid();
2514 long ident = Binder.clearCallingIdentity();
2515 try {
2516 // When a task is locked, dismiss the pinned stack if it exists
2517 mStackSupervisor.removeStacksInWindowingModes(WINDOWING_MODE_PINNED);
2518
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002519 getLockTaskController().startLockTaskMode(task, isSystemCaller, callingUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002520 } finally {
2521 Binder.restoreCallingIdentity(ident);
2522 }
2523 }
2524
2525 private void stopLockTaskModeInternal(@Nullable TaskRecord task, boolean isSystemCaller) {
2526 final int callingUid = Binder.getCallingUid();
2527 long ident = Binder.clearCallingIdentity();
2528 try {
2529 synchronized (mGlobalLock) {
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002530 getLockTaskController().stopLockTaskMode(task, isSystemCaller, callingUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002531 }
2532 // Launch in-call UI if a call is ongoing. This is necessary to allow stopping the lock
2533 // task and jumping straight into a call in the case of emergency call back.
2534 TelecomManager tm = (TelecomManager) mContext.getSystemService(Context.TELECOM_SERVICE);
2535 if (tm != null) {
2536 tm.showInCallScreen(false);
2537 }
2538 } finally {
2539 Binder.restoreCallingIdentity(ident);
2540 }
2541 }
2542
2543 @Override
Wale Ogunwale27c48ae2018-10-25 19:01:01 -07002544 public void updateLockTaskPackages(int userId, String[] packages) {
2545 final int callingUid = Binder.getCallingUid();
2546 if (callingUid != 0 && callingUid != SYSTEM_UID) {
2547 mAmInternal.enforceCallingPermission(Manifest.permission.UPDATE_LOCK_TASK_PACKAGES,
2548 "updateLockTaskPackages()");
2549 }
2550 synchronized (this) {
2551 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Whitelisting " + userId + ":"
2552 + Arrays.toString(packages));
2553 getLockTaskController().updateLockTaskPackages(userId, packages);
2554 }
2555 }
2556
2557 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002558 public boolean isInLockTaskMode() {
2559 return getLockTaskModeState() != LOCK_TASK_MODE_NONE;
2560 }
2561
2562 @Override
2563 public int getLockTaskModeState() {
2564 synchronized (mGlobalLock) {
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002565 return getLockTaskController().getLockTaskModeState();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002566 }
2567 }
2568
2569 @Override
2570 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) {
2571 synchronized (mGlobalLock) {
2572 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2573 if (r != null) {
2574 r.setTaskDescription(td);
2575 final TaskRecord task = r.getTask();
2576 task.updateTaskDescription();
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002577 mTaskChangeNotificationController.notifyTaskDescriptionChanged(task.taskId, td);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002578 }
2579 }
2580 }
2581
2582 @Override
2583 public Bundle getActivityOptions(IBinder token) {
2584 final long origId = Binder.clearCallingIdentity();
2585 try {
2586 synchronized (mGlobalLock) {
2587 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
2588 if (r != null) {
2589 final ActivityOptions activityOptions = r.takeOptionsLocked();
2590 return activityOptions == null ? null : activityOptions.toBundle();
2591 }
2592 return null;
2593 }
2594 } finally {
2595 Binder.restoreCallingIdentity(origId);
2596 }
2597 }
2598
2599 @Override
2600 public List<IBinder> getAppTasks(String callingPackage) {
2601 int callingUid = Binder.getCallingUid();
2602 long ident = Binder.clearCallingIdentity();
2603 try {
2604 synchronized (mGlobalLock) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002605 return mRecentTasks.getAppTasksList(callingUid, callingPackage);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002606 }
2607 } finally {
2608 Binder.restoreCallingIdentity(ident);
2609 }
2610 }
2611
2612 @Override
2613 public void finishVoiceTask(IVoiceInteractionSession session) {
2614 synchronized (mGlobalLock) {
2615 final long origId = Binder.clearCallingIdentity();
2616 try {
2617 // TODO: VI Consider treating local voice interactions and voice tasks
2618 // differently here
2619 mStackSupervisor.finishVoiceTask(session);
2620 } finally {
2621 Binder.restoreCallingIdentity(origId);
2622 }
2623 }
2624
2625 }
2626
2627 @Override
2628 public boolean isTopOfTask(IBinder token) {
2629 synchronized (mGlobalLock) {
2630 ActivityRecord r = ActivityRecord.isInStackLocked(token);
Riddle Hsu66b74a82018-07-26 00:20:12 +08002631 return r != null && r.getTask().getTopActivity() == r;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002632 }
2633 }
2634
2635 @Override
2636 public void notifyLaunchTaskBehindComplete(IBinder token) {
2637 mStackSupervisor.scheduleLaunchTaskBehindComplete(token);
2638 }
2639
2640 @Override
2641 public void notifyEnterAnimationComplete(IBinder token) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002642 mH.post(() -> {
2643 synchronized (mGlobalLock) {
2644 ActivityRecord r = ActivityRecord.forTokenLocked(token);
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07002645 if (r != null && r.attachedToProcess()) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002646 try {
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07002647 r.app.getThread().scheduleEnterAnimationComplete(r.appToken);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002648 } catch (RemoteException e) {
2649 }
2650 }
2651 }
2652
2653 });
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002654 }
2655
2656 /** Called from an app when assist data is ready. */
2657 @Override
2658 public void reportAssistContextExtras(IBinder token, Bundle extras, AssistStructure structure,
2659 AssistContent content, Uri referrer) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002660 PendingAssistExtras pae = (PendingAssistExtras) token;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002661 synchronized (pae) {
2662 pae.result = extras;
2663 pae.structure = structure;
2664 pae.content = content;
2665 if (referrer != null) {
2666 pae.extras.putParcelable(Intent.EXTRA_REFERRER, referrer);
2667 }
2668 if (structure != null) {
2669 structure.setHomeActivity(pae.isHome);
2670 }
2671 pae.haveResult = true;
2672 pae.notifyAll();
2673 if (pae.intent == null && pae.receiver == null) {
2674 // Caller is just waiting for the result.
2675 return;
2676 }
2677 }
2678 // We are now ready to launch the assist activity.
2679 IAssistDataReceiver sendReceiver = null;
2680 Bundle sendBundle = null;
2681 synchronized (mGlobalLock) {
2682 buildAssistBundleLocked(pae, extras);
2683 boolean exists = mPendingAssistExtras.remove(pae);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002684 mUiHandler.removeCallbacks(pae);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002685 if (!exists) {
2686 // Timed out.
2687 return;
2688 }
2689
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002690 if ((sendReceiver = pae.receiver) != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002691 // Caller wants result sent back to them.
2692 sendBundle = new Bundle();
2693 sendBundle.putBundle(ASSIST_KEY_DATA, pae.extras);
2694 sendBundle.putParcelable(ASSIST_KEY_STRUCTURE, pae.structure);
2695 sendBundle.putParcelable(ASSIST_KEY_CONTENT, pae.content);
2696 sendBundle.putBundle(ASSIST_KEY_RECEIVER_EXTRAS, pae.receiverExtras);
2697 }
2698 }
2699 if (sendReceiver != null) {
2700 try {
2701 sendReceiver.onHandleAssistData(sendBundle);
2702 } catch (RemoteException e) {
2703 }
2704 return;
2705 }
2706
2707 final long ident = Binder.clearCallingIdentity();
2708 try {
2709 if (TextUtils.equals(pae.intent.getAction(),
2710 android.service.voice.VoiceInteractionService.SERVICE_INTERFACE)) {
2711 pae.intent.putExtras(pae.extras);
2712 mContext.startServiceAsUser(pae.intent, new UserHandle(pae.userHandle));
2713 } else {
2714 pae.intent.replaceExtras(pae.extras);
2715 pae.intent.setFlags(FLAG_ACTIVITY_NEW_TASK
2716 | Intent.FLAG_ACTIVITY_SINGLE_TOP
2717 | Intent.FLAG_ACTIVITY_CLEAR_TOP);
Wale Ogunwale31913b52018-10-13 08:29:31 -07002718 mInternal.closeSystemDialogs("assist");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002719
2720 try {
2721 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle));
2722 } catch (ActivityNotFoundException e) {
2723 Slog.w(TAG, "No activity to handle assist action.", e);
2724 }
2725 }
2726 } finally {
2727 Binder.restoreCallingIdentity(ident);
2728 }
2729 }
2730
2731 @Override
2732 public int addAppTask(IBinder activityToken, Intent intent,
2733 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException {
2734 final int callingUid = Binder.getCallingUid();
2735 final long callingIdent = Binder.clearCallingIdentity();
2736
2737 try {
2738 synchronized (mGlobalLock) {
2739 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
2740 if (r == null) {
2741 throw new IllegalArgumentException("Activity does not exist; token="
2742 + activityToken);
2743 }
2744 ComponentName comp = intent.getComponent();
2745 if (comp == null) {
2746 throw new IllegalArgumentException("Intent " + intent
2747 + " must specify explicit component");
2748 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002749 if (thumbnail.getWidth() != mThumbnailWidth
2750 || thumbnail.getHeight() != mThumbnailHeight) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002751 throw new IllegalArgumentException("Bad thumbnail size: got "
2752 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require "
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002753 + mThumbnailWidth + "x" + mThumbnailHeight);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002754 }
2755 if (intent.getSelector() != null) {
2756 intent.setSelector(null);
2757 }
2758 if (intent.getSourceBounds() != null) {
2759 intent.setSourceBounds(null);
2760 }
2761 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) {
2762 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) {
2763 // The caller has added this as an auto-remove task... that makes no
2764 // sense, so turn off auto-remove.
2765 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS);
2766 }
2767 }
2768 final ActivityInfo ainfo = AppGlobals.getPackageManager().getActivityInfo(comp,
2769 STOCK_PM_FLAGS, UserHandle.getUserId(callingUid));
2770 if (ainfo.applicationInfo.uid != callingUid) {
2771 throw new SecurityException(
2772 "Can't add task for another application: target uid="
2773 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid);
2774 }
2775
2776 final ActivityStack stack = r.getStack();
2777 final TaskRecord task = stack.createTaskRecord(
2778 mStackSupervisor.getNextTaskIdForUserLocked(r.userId), ainfo, intent,
2779 null /* voiceSession */, null /* voiceInteractor */, !ON_TOP);
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002780 if (!mRecentTasks.addToBottom(task)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002781 // The app has too many tasks already and we can't add any more
2782 stack.removeTask(task, "addAppTask", REMOVE_TASK_MODE_DESTROYING);
2783 return INVALID_TASK_ID;
2784 }
2785 task.lastTaskDescription.copyFrom(description);
2786
2787 // TODO: Send the thumbnail to WM to store it.
2788
2789 return task.taskId;
2790 }
2791 } finally {
2792 Binder.restoreCallingIdentity(callingIdent);
2793 }
2794 }
2795
2796 @Override
2797 public Point getAppTaskThumbnailSize() {
2798 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002799 return new Point(mThumbnailWidth, mThumbnailHeight);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002800 }
2801 }
2802
2803 @Override
2804 public void setTaskResizeable(int taskId, int resizeableMode) {
2805 synchronized (mGlobalLock) {
2806 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(
2807 taskId, MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
2808 if (task == null) {
2809 Slog.w(TAG, "setTaskResizeable: taskId=" + taskId + " not found");
2810 return;
2811 }
2812 task.setResizeMode(resizeableMode);
2813 }
2814 }
2815
2816 @Override
2817 public void resizeTask(int taskId, Rect bounds, int resizeMode) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002818 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeTask()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002819 long ident = Binder.clearCallingIdentity();
2820 try {
2821 synchronized (mGlobalLock) {
Riddle Hsu090ac6f2018-10-31 12:55:29 +08002822 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
2823 MATCH_TASK_IN_STACKS_ONLY);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002824 if (task == null) {
2825 Slog.w(TAG, "resizeTask: taskId=" + taskId + " not found");
2826 return;
2827 }
2828 // Place the task in the right stack if it isn't there already based on
2829 // the requested bounds.
2830 // The stack transition logic is:
2831 // - a null bounds on a freeform task moves that task to fullscreen
2832 // - a non-null bounds on a non-freeform (fullscreen OR docked) task moves
2833 // that task to freeform
2834 // - otherwise the task is not moved
2835 ActivityStack stack = task.getStack();
2836 if (!task.getWindowConfiguration().canResizeTask()) {
2837 throw new IllegalArgumentException("resizeTask not allowed on task=" + task);
2838 }
2839 if (bounds == null && stack.getWindowingMode() == WINDOWING_MODE_FREEFORM) {
2840 stack = stack.getDisplay().getOrCreateStack(
2841 WINDOWING_MODE_FULLSCREEN, stack.getActivityType(), ON_TOP);
2842 } else if (bounds != null && stack.getWindowingMode() != WINDOWING_MODE_FREEFORM) {
2843 stack = stack.getDisplay().getOrCreateStack(
2844 WINDOWING_MODE_FREEFORM, stack.getActivityType(), ON_TOP);
2845 }
2846
2847 // Reparent the task to the right stack if necessary
2848 boolean preserveWindow = (resizeMode & RESIZE_MODE_PRESERVE_WINDOW) != 0;
2849 if (stack != task.getStack()) {
2850 // Defer resume until the task is resized below
2851 task.reparent(stack, ON_TOP, REPARENT_KEEP_STACK_AT_FRONT, ANIMATE,
2852 DEFER_RESUME, "resizeTask");
2853 preserveWindow = false;
2854 }
2855
2856 // After reparenting (which only resizes the task to the stack bounds), resize the
2857 // task to the actual bounds provided
2858 task.resize(bounds, resizeMode, preserveWindow, !DEFER_RESUME);
2859 }
2860 } finally {
2861 Binder.restoreCallingIdentity(ident);
2862 }
2863 }
2864
2865 @Override
2866 public boolean releaseActivityInstance(IBinder token) {
2867 synchronized (mGlobalLock) {
2868 final long origId = Binder.clearCallingIdentity();
2869 try {
2870 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2871 if (r == null) {
2872 return false;
2873 }
2874 return r.getStack().safelyDestroyActivityLocked(r, "app-req");
2875 } finally {
2876 Binder.restoreCallingIdentity(origId);
2877 }
2878 }
2879 }
2880
2881 @Override
2882 public void releaseSomeActivities(IApplicationThread appInt) {
2883 synchronized (mGlobalLock) {
2884 final long origId = Binder.clearCallingIdentity();
2885 try {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07002886 final WindowProcessController app = getProcessController(appInt);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002887 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem");
2888 } finally {
2889 Binder.restoreCallingIdentity(origId);
2890 }
2891 }
2892 }
2893
2894 @Override
2895 public void setLockScreenShown(boolean keyguardShowing, boolean aodShowing,
wilsonshihe7903ea2018-09-26 16:17:59 +08002896 int[] secondaryDisplaysShowing) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002897 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER)
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002898 != PackageManager.PERMISSION_GRANTED) {
2899 throw new SecurityException("Requires permission "
2900 + android.Manifest.permission.DEVICE_POWER);
2901 }
2902
2903 synchronized (mGlobalLock) {
2904 long ident = Binder.clearCallingIdentity();
2905 if (mKeyguardShown != keyguardShowing) {
2906 mKeyguardShown = keyguardShowing;
Wale Ogunwale342fbe92018-10-09 08:44:10 -07002907 final Message msg = PooledLambda.obtainMessage(
2908 ActivityManagerInternal::reportCurKeyguardUsageEvent, mAmInternal,
2909 keyguardShowing);
2910 mH.sendMessage(msg);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002911 }
2912 try {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002913 mKeyguardController.setKeyguardShown(keyguardShowing, aodShowing,
wilsonshihe7903ea2018-09-26 16:17:59 +08002914 secondaryDisplaysShowing);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002915 } finally {
2916 Binder.restoreCallingIdentity(ident);
2917 }
2918 }
2919
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002920 mH.post(() -> {
2921 for (int i = mScreenObservers.size() - 1; i >= 0; i--) {
2922 mScreenObservers.get(i).onKeyguardStateChanged(keyguardShowing);
2923 }
2924 });
2925 }
2926
Wale Ogunwale387b34c2018-10-25 19:59:40 -07002927 public void onScreenAwakeChanged(boolean isAwake) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002928 mH.post(() -> {
2929 for (int i = mScreenObservers.size() - 1; i >= 0; i--) {
2930 mScreenObservers.get(i).onAwakeStateChanged(isAwake);
2931 }
2932 });
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002933 }
2934
2935 @Override
2936 public Bitmap getTaskDescriptionIcon(String filePath, int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002937 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
2938 userId, "getTaskDescriptionIcon");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002939
2940 final File passedIconFile = new File(filePath);
2941 final File legitIconFile = new File(TaskPersister.getUserImagesDir(userId),
2942 passedIconFile.getName());
2943 if (!legitIconFile.getPath().equals(filePath)
2944 || !filePath.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) {
2945 throw new IllegalArgumentException("Bad file path: " + filePath
2946 + " passed for userId " + userId);
2947 }
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002948 return mRecentTasks.getTaskDescriptionIcon(filePath);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002949 }
2950
2951 @Override
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002952 public void startInPlaceAnimationOnFrontMostApplication(Bundle opts) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002953 final SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(opts);
2954 final ActivityOptions activityOptions = safeOptions != null
2955 ? safeOptions.getOptions(mStackSupervisor)
2956 : null;
2957 if (activityOptions == null
2958 || activityOptions.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE
2959 || activityOptions.getCustomInPlaceResId() == 0) {
2960 throw new IllegalArgumentException("Expected in-place ActivityOption " +
2961 "with valid animation");
2962 }
lumark588a3e82018-07-20 18:53:54 +08002963 // Get top display of front most application.
2964 final ActivityStack focusedStack = getTopDisplayFocusedStack();
2965 if (focusedStack != null) {
2966 final DisplayWindowController dwc =
2967 focusedStack.getDisplay().getWindowContainerController();
2968 dwc.prepareAppTransition(TRANSIT_TASK_IN_PLACE, false);
2969 dwc.overridePendingAppTransitionInPlace(activityOptions.getPackageName(),
2970 activityOptions.getCustomInPlaceResId());
2971 dwc.executeAppTransition();
2972 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002973 }
2974
2975 @Override
2976 public void removeStack(int stackId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002977 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "removeStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002978 synchronized (mGlobalLock) {
2979 final long ident = Binder.clearCallingIdentity();
2980 try {
2981 final ActivityStack stack = mStackSupervisor.getStack(stackId);
2982 if (stack == null) {
2983 Slog.w(TAG, "removeStack: No stack with id=" + stackId);
2984 return;
2985 }
2986 if (!stack.isActivityTypeStandardOrUndefined()) {
2987 throw new IllegalArgumentException(
2988 "Removing non-standard stack is not allowed.");
2989 }
2990 mStackSupervisor.removeStack(stack);
2991 } finally {
2992 Binder.restoreCallingIdentity(ident);
2993 }
2994 }
2995 }
2996
2997 @Override
2998 public void moveStackToDisplay(int stackId, int displayId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002999 mAmInternal.enforceCallingPermission(INTERNAL_SYSTEM_WINDOW, "moveStackToDisplay()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003000
3001 synchronized (mGlobalLock) {
3002 final long ident = Binder.clearCallingIdentity();
3003 try {
3004 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveStackToDisplay: moving stackId=" + stackId
3005 + " to displayId=" + displayId);
3006 mStackSupervisor.moveStackToDisplayLocked(stackId, displayId, ON_TOP);
3007 } finally {
3008 Binder.restoreCallingIdentity(ident);
3009 }
3010 }
3011 }
3012
3013 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003014 public void exitFreeformMode(IBinder token) {
3015 synchronized (mGlobalLock) {
3016 long ident = Binder.clearCallingIdentity();
3017 try {
3018 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
3019 if (r == null) {
3020 throw new IllegalArgumentException(
3021 "exitFreeformMode: No activity record matching token=" + token);
3022 }
3023
3024 final ActivityStack stack = r.getStack();
3025 if (stack == null || !stack.inFreeformWindowingMode()) {
3026 throw new IllegalStateException(
3027 "exitFreeformMode: You can only go fullscreen from freeform.");
3028 }
3029
3030 stack.setWindowingMode(WINDOWING_MODE_FULLSCREEN);
3031 } finally {
3032 Binder.restoreCallingIdentity(ident);
3033 }
3034 }
3035 }
3036
3037 /** Sets the task stack listener that gets callbacks when a task stack changes. */
3038 @Override
3039 public void registerTaskStackListener(ITaskStackListener listener) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003040 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003041 "registerTaskStackListener()");
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003042 mTaskChangeNotificationController.registerTaskStackListener(listener);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003043 }
3044
3045 /** Unregister a task stack listener so that it stops receiving callbacks. */
3046 @Override
3047 public void unregisterTaskStackListener(ITaskStackListener listener) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003048 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003049 "unregisterTaskStackListener()");
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003050 mTaskChangeNotificationController.unregisterTaskStackListener(listener);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003051 }
3052
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003053 @Override
3054 public boolean requestAssistContextExtras(int requestType, IAssistDataReceiver receiver,
3055 Bundle receiverExtras, IBinder activityToken, boolean focused, boolean newSessionId) {
3056 return enqueueAssistContext(requestType, null, null, receiver, receiverExtras,
3057 activityToken, focused, newSessionId, UserHandle.getCallingUserId(), null,
3058 PENDING_ASSIST_EXTRAS_LONG_TIMEOUT, 0) != null;
3059 }
3060
3061 @Override
3062 public boolean requestAutofillData(IAssistDataReceiver receiver, Bundle receiverExtras,
3063 IBinder activityToken, int flags) {
3064 return enqueueAssistContext(ActivityManager.ASSIST_CONTEXT_AUTOFILL, null, null,
3065 receiver, receiverExtras, activityToken, true, true, UserHandle.getCallingUserId(),
3066 null, PENDING_AUTOFILL_ASSIST_STRUCTURE_TIMEOUT, flags) != null;
3067 }
3068
3069 @Override
3070 public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle,
3071 Bundle args) {
3072 return enqueueAssistContext(requestType, intent, hint, null, null, null,
3073 true /* focused */, true /* newSessionId */, userHandle, args,
3074 PENDING_ASSIST_EXTRAS_TIMEOUT, 0) != null;
3075 }
3076
3077 @Override
3078 public Bundle getAssistContextExtras(int requestType) {
3079 PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, null,
3080 null, null, true /* focused */, true /* newSessionId */,
3081 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_TIMEOUT, 0);
3082 if (pae == null) {
3083 return null;
3084 }
3085 synchronized (pae) {
3086 while (!pae.haveResult) {
3087 try {
3088 pae.wait();
3089 } catch (InterruptedException e) {
3090 }
3091 }
3092 }
3093 synchronized (mGlobalLock) {
3094 buildAssistBundleLocked(pae, pae.result);
3095 mPendingAssistExtras.remove(pae);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003096 mUiHandler.removeCallbacks(pae);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003097 }
3098 return pae.extras;
3099 }
3100
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003101 /**
3102 * Binder IPC calls go through the public entry point.
3103 * This can be called with or without the global lock held.
3104 */
3105 private static int checkCallingPermission(String permission) {
3106 return checkPermission(
3107 permission, Binder.getCallingPid(), UserHandle.getAppId(Binder.getCallingUid()));
3108 }
3109
3110 /** This can be called with or without the global lock held. */
Wale Ogunwale214f3482018-10-04 11:00:47 -07003111 private void enforceCallerIsRecentsOrHasPermission(String permission, String func) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003112 if (!getRecentTasks().isCallerRecents(Binder.getCallingUid())) {
3113 mAmInternal.enforceCallingPermission(permission, func);
3114 }
3115 }
3116
3117 @VisibleForTesting
3118 int checkGetTasksPermission(String permission, int pid, int uid) {
3119 return checkPermission(permission, pid, uid);
3120 }
3121
3122 static int checkPermission(String permission, int pid, int uid) {
3123 if (permission == null) {
3124 return PackageManager.PERMISSION_DENIED;
3125 }
3126 return checkComponentPermission(permission, pid, uid, -1, true);
3127 }
3128
Wale Ogunwale214f3482018-10-04 11:00:47 -07003129 public static int checkComponentPermission(String permission, int pid, int uid,
3130 int owningUid, boolean exported) {
3131 return ActivityManagerService.checkComponentPermission(
3132 permission, pid, uid, owningUid, exported);
3133 }
3134
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003135 boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) {
3136 if (getRecentTasks().isCallerRecents(callingUid)) {
3137 // Always allow the recents component to get tasks
3138 return true;
3139 }
3140
3141 boolean allowed = checkGetTasksPermission(android.Manifest.permission.REAL_GET_TASKS,
3142 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED;
3143 if (!allowed) {
3144 if (checkGetTasksPermission(android.Manifest.permission.GET_TASKS,
3145 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) {
3146 // Temporary compatibility: some existing apps on the system image may
3147 // still be requesting the old permission and not switched to the new
3148 // one; if so, we'll still allow them full access. This means we need
3149 // to see if they are holding the old permission and are a system app.
3150 try {
3151 if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) {
3152 allowed = true;
3153 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid
3154 + " is using old GET_TASKS but privileged; allowing");
3155 }
3156 } catch (RemoteException e) {
3157 }
3158 }
3159 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid
3160 + " does not hold REAL_GET_TASKS; limiting output");
3161 }
3162 return allowed;
3163 }
3164
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003165 private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint,
3166 IAssistDataReceiver receiver, Bundle receiverExtras, IBinder activityToken,
3167 boolean focused, boolean newSessionId, int userHandle, Bundle args, long timeout,
3168 int flags) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003169 mAmInternal.enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003170 "enqueueAssistContext()");
3171
3172 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003173 ActivityRecord activity = getTopDisplayFocusedStack().getTopActivity();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003174 if (activity == null) {
3175 Slog.w(TAG, "getAssistContextExtras failed: no top activity");
3176 return null;
3177 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003178 if (!activity.attachedToProcess()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003179 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity);
3180 return null;
3181 }
3182 if (focused) {
3183 if (activityToken != null) {
3184 ActivityRecord caller = ActivityRecord.forTokenLocked(activityToken);
3185 if (activity != caller) {
3186 Slog.w(TAG, "enqueueAssistContext failed: caller " + caller
3187 + " is not current top " + activity);
3188 return null;
3189 }
3190 }
3191 } else {
3192 activity = ActivityRecord.forTokenLocked(activityToken);
3193 if (activity == null) {
3194 Slog.w(TAG, "enqueueAssistContext failed: activity for token=" + activityToken
3195 + " couldn't be found");
3196 return null;
3197 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003198 if (!activity.attachedToProcess()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003199 Slog.w(TAG, "enqueueAssistContext failed: no process for " + activity);
3200 return null;
3201 }
3202 }
3203
3204 PendingAssistExtras pae;
3205 Bundle extras = new Bundle();
3206 if (args != null) {
3207 extras.putAll(args);
3208 }
3209 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName);
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003210 extras.putInt(Intent.EXTRA_ASSIST_UID, activity.app.mUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003211
3212 pae = new PendingAssistExtras(activity, extras, intent, hint, receiver, receiverExtras,
3213 userHandle);
3214 pae.isHome = activity.isActivityTypeHome();
3215
3216 // Increment the sessionId if necessary
3217 if (newSessionId) {
3218 mViSessionId++;
3219 }
3220 try {
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003221 activity.app.getThread().requestAssistContextExtras(activity.appToken, pae,
3222 requestType, mViSessionId, flags);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003223 mPendingAssistExtras.add(pae);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003224 mUiHandler.postDelayed(pae, timeout);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003225 } catch (RemoteException e) {
3226 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity);
3227 return null;
3228 }
3229 return pae;
3230 }
3231 }
3232
3233 private void buildAssistBundleLocked(PendingAssistExtras pae, Bundle result) {
3234 if (result != null) {
3235 pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, result);
3236 }
3237 if (pae.hint != null) {
3238 pae.extras.putBoolean(pae.hint, true);
3239 }
3240 }
3241
3242 private void pendingAssistExtrasTimedOut(PendingAssistExtras pae) {
3243 IAssistDataReceiver receiver;
3244 synchronized (mGlobalLock) {
3245 mPendingAssistExtras.remove(pae);
3246 receiver = pae.receiver;
3247 }
3248 if (receiver != null) {
3249 // Caller wants result sent back to them.
3250 Bundle sendBundle = new Bundle();
3251 // At least return the receiver extras
3252 sendBundle.putBundle(ASSIST_KEY_RECEIVER_EXTRAS, pae.receiverExtras);
3253 try {
3254 pae.receiver.onHandleAssistData(sendBundle);
3255 } catch (RemoteException e) {
3256 }
3257 }
3258 }
3259
3260 public class PendingAssistExtras extends Binder implements Runnable {
3261 public final ActivityRecord activity;
3262 public boolean isHome;
3263 public final Bundle extras;
3264 public final Intent intent;
3265 public final String hint;
3266 public final IAssistDataReceiver receiver;
3267 public final int userHandle;
3268 public boolean haveResult = false;
3269 public Bundle result = null;
3270 public AssistStructure structure = null;
3271 public AssistContent content = null;
3272 public Bundle receiverExtras;
3273
3274 public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent,
3275 String _hint, IAssistDataReceiver _receiver, Bundle _receiverExtras,
3276 int _userHandle) {
3277 activity = _activity;
3278 extras = _extras;
3279 intent = _intent;
3280 hint = _hint;
3281 receiver = _receiver;
3282 receiverExtras = _receiverExtras;
3283 userHandle = _userHandle;
3284 }
3285
3286 @Override
3287 public void run() {
3288 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity);
3289 synchronized (this) {
3290 haveResult = true;
3291 notifyAll();
3292 }
3293 pendingAssistExtrasTimedOut(this);
3294 }
3295 }
3296
3297 @Override
3298 public boolean isAssistDataAllowedOnCurrentActivity() {
3299 int userId;
3300 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003301 final ActivityStack focusedStack = getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003302 if (focusedStack == null || focusedStack.isActivityTypeAssistant()) {
3303 return false;
3304 }
3305
3306 final ActivityRecord activity = focusedStack.getTopActivity();
3307 if (activity == null) {
3308 return false;
3309 }
3310 userId = activity.userId;
3311 }
3312 return !DevicePolicyCache.getInstance().getScreenCaptureDisabled(userId);
3313 }
3314
3315 @Override
3316 public boolean showAssistFromActivity(IBinder token, Bundle args) {
3317 long ident = Binder.clearCallingIdentity();
3318 try {
3319 synchronized (mGlobalLock) {
3320 ActivityRecord caller = ActivityRecord.forTokenLocked(token);
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003321 ActivityRecord top = getTopDisplayFocusedStack().getTopActivity();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003322 if (top != caller) {
3323 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller
3324 + " is not current top " + top);
3325 return false;
3326 }
3327 if (!top.nowVisible) {
3328 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller
3329 + " is not visible");
3330 return false;
3331 }
3332 }
3333 return mAssistUtils.showSessionForActiveService(args, SHOW_SOURCE_APPLICATION, null,
3334 token);
3335 } finally {
3336 Binder.restoreCallingIdentity(ident);
3337 }
3338 }
3339
3340 @Override
3341 public boolean isRootVoiceInteraction(IBinder token) {
3342 synchronized (mGlobalLock) {
3343 ActivityRecord r = ActivityRecord.isInStackLocked(token);
3344 if (r == null) {
3345 return false;
3346 }
3347 return r.rootVoiceInteraction;
3348 }
3349 }
3350
Wale Ogunwalef6733932018-06-27 05:14:34 -07003351 private void onLocalVoiceInteractionStartedLocked(IBinder activity,
3352 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
3353 ActivityRecord activityToCallback = ActivityRecord.forTokenLocked(activity);
3354 if (activityToCallback == null) return;
3355 activityToCallback.setVoiceSessionLocked(voiceSession);
3356
3357 // Inform the activity
3358 try {
3359 activityToCallback.app.getThread().scheduleLocalVoiceInteractionStarted(activity,
3360 voiceInteractor);
3361 long token = Binder.clearCallingIdentity();
3362 try {
3363 startRunningVoiceLocked(voiceSession, activityToCallback.appInfo.uid);
3364 } finally {
3365 Binder.restoreCallingIdentity(token);
3366 }
3367 // TODO: VI Should we cache the activity so that it's easier to find later
3368 // rather than scan through all the stacks and activities?
3369 } catch (RemoteException re) {
3370 activityToCallback.clearVoiceSessionLocked();
3371 // TODO: VI Should this terminate the voice session?
3372 }
3373 }
3374
3375 private void startRunningVoiceLocked(IVoiceInteractionSession session, int targetUid) {
3376 Slog.d(TAG, "<<< startRunningVoiceLocked()");
3377 mVoiceWakeLock.setWorkSource(new WorkSource(targetUid));
3378 if (mRunningVoice == null || mRunningVoice.asBinder() != session.asBinder()) {
3379 boolean wasRunningVoice = mRunningVoice != null;
3380 mRunningVoice = session;
3381 if (!wasRunningVoice) {
3382 mVoiceWakeLock.acquire();
3383 updateSleepIfNeededLocked();
3384 }
3385 }
3386 }
3387
3388 void finishRunningVoiceLocked() {
3389 if (mRunningVoice != null) {
3390 mRunningVoice = null;
3391 mVoiceWakeLock.release();
3392 updateSleepIfNeededLocked();
3393 }
3394 }
3395
3396 @Override
3397 public void setVoiceKeepAwake(IVoiceInteractionSession session, boolean keepAwake) {
3398 synchronized (mGlobalLock) {
3399 if (mRunningVoice != null && mRunningVoice.asBinder() == session.asBinder()) {
3400 if (keepAwake) {
3401 mVoiceWakeLock.acquire();
3402 } else {
3403 mVoiceWakeLock.release();
3404 }
3405 }
3406 }
3407 }
3408
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003409 @Override
3410 public ComponentName getActivityClassForToken(IBinder token) {
3411 synchronized (mGlobalLock) {
3412 ActivityRecord r = ActivityRecord.isInStackLocked(token);
3413 if (r == null) {
3414 return null;
3415 }
3416 return r.intent.getComponent();
3417 }
3418 }
3419
3420 @Override
3421 public String getPackageForToken(IBinder token) {
3422 synchronized (mGlobalLock) {
3423 ActivityRecord r = ActivityRecord.isInStackLocked(token);
3424 if (r == null) {
3425 return null;
3426 }
3427 return r.packageName;
3428 }
3429 }
3430
3431 @Override
3432 public void showLockTaskEscapeMessage(IBinder token) {
3433 synchronized (mGlobalLock) {
3434 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
3435 if (r == null) {
3436 return;
3437 }
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07003438 getLockTaskController().showLockTaskToast();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003439 }
3440 }
3441
3442 @Override
3443 public void keyguardGoingAway(int flags) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003444 enforceNotIsolatedCaller("keyguardGoingAway");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003445 final long token = Binder.clearCallingIdentity();
3446 try {
3447 synchronized (mGlobalLock) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003448 mKeyguardController.keyguardGoingAway(flags);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003449 }
3450 } finally {
3451 Binder.restoreCallingIdentity(token);
3452 }
3453 }
3454
3455 /**
3456 * Try to place task to provided position. The final position might be different depending on
3457 * current user and stacks state. The task will be moved to target stack if it's currently in
3458 * different stack.
3459 */
3460 @Override
3461 public void positionTaskInStack(int taskId, int stackId, int position) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003462 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "positionTaskInStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003463 synchronized (mGlobalLock) {
3464 long ident = Binder.clearCallingIdentity();
3465 try {
3466 if (DEBUG_STACK) Slog.d(TAG_STACK, "positionTaskInStack: positioning task="
3467 + taskId + " in stackId=" + stackId + " at position=" + position);
3468 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
3469 if (task == null) {
3470 throw new IllegalArgumentException("positionTaskInStack: no task for id="
3471 + taskId);
3472 }
3473
3474 final ActivityStack stack = mStackSupervisor.getStack(stackId);
3475
3476 if (stack == null) {
3477 throw new IllegalArgumentException("positionTaskInStack: no stack for id="
3478 + stackId);
3479 }
3480 if (!stack.isActivityTypeStandardOrUndefined()) {
3481 throw new IllegalArgumentException("positionTaskInStack: Attempt to change"
3482 + " the position of task " + taskId + " in/to non-standard stack");
3483 }
3484
3485 // TODO: Have the callers of this API call a separate reparent method if that is
3486 // what they intended to do vs. having this method also do reparenting.
3487 if (task.getStack() == stack) {
3488 // Change position in current stack.
3489 stack.positionChildAt(task, position);
3490 } else {
3491 // Reparent to new stack.
3492 task.reparent(stack, position, REPARENT_LEAVE_STACK_IN_PLACE, !ANIMATE,
3493 !DEFER_RESUME, "positionTaskInStack");
3494 }
3495 } finally {
3496 Binder.restoreCallingIdentity(ident);
3497 }
3498 }
3499 }
3500
3501 @Override
3502 public void reportSizeConfigurations(IBinder token, int[] horizontalSizeConfiguration,
3503 int[] verticalSizeConfigurations, int[] smallestSizeConfigurations) {
3504 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Report configuration: " + token + " "
3505 + horizontalSizeConfiguration + " " + verticalSizeConfigurations);
3506 synchronized (mGlobalLock) {
3507 ActivityRecord record = ActivityRecord.isInStackLocked(token);
3508 if (record == null) {
3509 throw new IllegalArgumentException("reportSizeConfigurations: ActivityRecord not "
3510 + "found for: " + token);
3511 }
3512 record.setSizeConfigurations(horizontalSizeConfiguration,
3513 verticalSizeConfigurations, smallestSizeConfigurations);
3514 }
3515 }
3516
3517 /**
3518 * Dismisses split-screen multi-window mode.
3519 * @param toTop If true the current primary split-screen stack will be placed or left on top.
3520 */
3521 @Override
3522 public void dismissSplitScreenMode(boolean toTop) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003523 enforceCallerIsRecentsOrHasPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003524 MANAGE_ACTIVITY_STACKS, "dismissSplitScreenMode()");
3525 final long ident = Binder.clearCallingIdentity();
3526 try {
3527 synchronized (mGlobalLock) {
3528 final ActivityStack stack =
3529 mStackSupervisor.getDefaultDisplay().getSplitScreenPrimaryStack();
3530 if (stack == null) {
3531 Slog.w(TAG, "dismissSplitScreenMode: primary split-screen stack not found.");
3532 return;
3533 }
3534
3535 if (toTop) {
3536 // Caller wants the current split-screen primary stack to be the top stack after
3537 // it goes fullscreen, so move it to the front.
3538 stack.moveToFront("dismissSplitScreenMode");
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003539 } else if (mStackSupervisor.isTopDisplayFocusedStack(stack)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003540 // In this case the current split-screen primary stack shouldn't be the top
3541 // stack after it goes fullscreen, but it current has focus, so we move the
3542 // focus to the top-most split-screen secondary stack next to it.
3543 final ActivityStack otherStack = stack.getDisplay().getTopStackInWindowingMode(
3544 WINDOWING_MODE_SPLIT_SCREEN_SECONDARY);
3545 if (otherStack != null) {
3546 otherStack.moveToFront("dismissSplitScreenMode_other");
3547 }
3548 }
3549
Evan Rosky10475742018-09-05 19:02:48 -07003550 stack.setWindowingMode(WINDOWING_MODE_UNDEFINED);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003551 }
3552 } finally {
3553 Binder.restoreCallingIdentity(ident);
3554 }
3555 }
3556
3557 /**
3558 * Dismisses Pip
3559 * @param animate True if the dismissal should be animated.
3560 * @param animationDuration The duration of the resize animation in milliseconds or -1 if the
3561 * default animation duration should be used.
3562 */
3563 @Override
3564 public void dismissPip(boolean animate, int animationDuration) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003565 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "dismissPip()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003566 final long ident = Binder.clearCallingIdentity();
3567 try {
3568 synchronized (mGlobalLock) {
3569 final PinnedActivityStack stack =
3570 mStackSupervisor.getDefaultDisplay().getPinnedStack();
3571 if (stack == null) {
3572 Slog.w(TAG, "dismissPip: pinned stack not found.");
3573 return;
3574 }
3575 if (stack.getWindowingMode() != WINDOWING_MODE_PINNED) {
3576 throw new IllegalArgumentException("Stack: " + stack
3577 + " doesn't support animated resize.");
3578 }
3579 if (animate) {
3580 stack.animateResizePinnedStack(null /* sourceHintBounds */,
3581 null /* destBounds */, animationDuration, false /* fromFullscreen */);
3582 } else {
3583 mStackSupervisor.moveTasksToFullscreenStackLocked(stack, true /* onTop */);
3584 }
3585 }
3586 } finally {
3587 Binder.restoreCallingIdentity(ident);
3588 }
3589 }
3590
3591 @Override
3592 public void suppressResizeConfigChanges(boolean suppress) throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003593 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "suppressResizeConfigChanges()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003594 synchronized (mGlobalLock) {
3595 mSuppressResizeConfigChanges = suppress;
3596 }
3597 }
3598
3599 /**
3600 * NOTE: For the pinned stack, this method is usually called after the bounds animation has
3601 * animated the stack to the fullscreen, but can also be called if we are relaunching an
3602 * activity and clearing the task at the same time.
3603 */
3604 @Override
3605 // TODO: API should just be about changing windowing modes...
3606 public void moveTasksToFullscreenStack(int fromStackId, boolean onTop) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003607 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003608 "moveTasksToFullscreenStack()");
3609 synchronized (mGlobalLock) {
3610 final long origId = Binder.clearCallingIdentity();
3611 try {
3612 final ActivityStack stack = mStackSupervisor.getStack(fromStackId);
3613 if (stack != null){
3614 if (!stack.isActivityTypeStandardOrUndefined()) {
3615 throw new IllegalArgumentException(
3616 "You can't move tasks from non-standard stacks.");
3617 }
3618 mStackSupervisor.moveTasksToFullscreenStackLocked(stack, onTop);
3619 }
3620 } finally {
3621 Binder.restoreCallingIdentity(origId);
3622 }
3623 }
3624 }
3625
3626 /**
3627 * Moves the top activity in the input stackId to the pinned stack.
3628 *
3629 * @param stackId Id of stack to move the top activity to pinned stack.
3630 * @param bounds Bounds to use for pinned stack.
3631 *
3632 * @return True if the top activity of the input stack was successfully moved to the pinned
3633 * stack.
3634 */
3635 @Override
3636 public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003637 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003638 "moveTopActivityToPinnedStack()");
3639 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003640 if (!mSupportsPictureInPicture) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003641 throw new IllegalStateException("moveTopActivityToPinnedStack:"
3642 + "Device doesn't support picture-in-picture mode");
3643 }
3644
3645 long ident = Binder.clearCallingIdentity();
3646 try {
3647 return mStackSupervisor.moveTopStackActivityToPinnedStackLocked(stackId, bounds);
3648 } finally {
3649 Binder.restoreCallingIdentity(ident);
3650 }
3651 }
3652 }
3653
3654 @Override
3655 public boolean isInMultiWindowMode(IBinder token) {
3656 final long origId = Binder.clearCallingIdentity();
3657 try {
3658 synchronized (mGlobalLock) {
3659 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
3660 if (r == null) {
3661 return false;
3662 }
3663 // An activity is consider to be in multi-window mode if its task isn't fullscreen.
3664 return r.inMultiWindowMode();
3665 }
3666 } finally {
3667 Binder.restoreCallingIdentity(origId);
3668 }
3669 }
3670
3671 @Override
3672 public boolean isInPictureInPictureMode(IBinder token) {
3673 final long origId = Binder.clearCallingIdentity();
3674 try {
3675 synchronized (mGlobalLock) {
3676 return isInPictureInPictureMode(ActivityRecord.forTokenLocked(token));
3677 }
3678 } finally {
3679 Binder.restoreCallingIdentity(origId);
3680 }
3681 }
3682
3683 private boolean isInPictureInPictureMode(ActivityRecord r) {
3684 if (r == null || r.getStack() == null || !r.inPinnedWindowingMode()
3685 || r.getStack().isInStackLocked(r) == null) {
3686 return false;
3687 }
3688
3689 // If we are animating to fullscreen then we have already dispatched the PIP mode
3690 // changed, so we should reflect that check here as well.
3691 final PinnedActivityStack stack = r.getStack();
3692 final PinnedStackWindowController windowController = stack.getWindowContainerController();
3693 return !windowController.isAnimatingBoundsToFullscreen();
3694 }
3695
3696 @Override
3697 public boolean enterPictureInPictureMode(IBinder token, final PictureInPictureParams params) {
3698 final long origId = Binder.clearCallingIdentity();
3699 try {
3700 synchronized (mGlobalLock) {
3701 final ActivityRecord r = ensureValidPictureInPictureActivityParamsLocked(
3702 "enterPictureInPictureMode", token, params);
3703
3704 // If the activity is already in picture in picture mode, then just return early
3705 if (isInPictureInPictureMode(r)) {
3706 return true;
3707 }
3708
3709 // Activity supports picture-in-picture, now check that we can enter PiP at this
3710 // point, if it is
3711 if (!r.checkEnterPictureInPictureState("enterPictureInPictureMode",
3712 false /* beforeStopping */)) {
3713 return false;
3714 }
3715
3716 final Runnable enterPipRunnable = () -> {
Wale Ogunwalef276a6f2018-06-15 08:26:07 -07003717 synchronized (mGlobalLock) {
3718 // Only update the saved args from the args that are set
3719 r.pictureInPictureArgs.copyOnlySet(params);
3720 final float aspectRatio = r.pictureInPictureArgs.getAspectRatio();
3721 final List<RemoteAction> actions = r.pictureInPictureArgs.getActions();
3722 // Adjust the source bounds by the insets for the transition down
3723 final Rect sourceBounds = new Rect(
3724 r.pictureInPictureArgs.getSourceRectHint());
3725 mStackSupervisor.moveActivityToPinnedStackLocked(
3726 r, sourceBounds, aspectRatio, "enterPictureInPictureMode");
3727 final PinnedActivityStack stack = r.getStack();
3728 stack.setPictureInPictureAspectRatio(aspectRatio);
3729 stack.setPictureInPictureActions(actions);
3730 MetricsLoggerWrapper.logPictureInPictureEnter(mContext, r.appInfo.uid,
3731 r.shortComponentName, r.supportsEnterPipOnTaskSwitch);
3732 logPictureInPictureArgs(params);
3733 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003734 };
3735
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003736 if (isKeyguardLocked()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003737 // If the keyguard is showing or occluded, then try and dismiss it before
3738 // entering picture-in-picture (this will prompt the user to authenticate if the
3739 // device is currently locked).
3740 dismissKeyguard(token, new KeyguardDismissCallback() {
3741 @Override
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003742 public void onDismissSucceeded() {
3743 mH.post(enterPipRunnable);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003744 }
3745 }, null /* message */);
3746 } else {
3747 // Enter picture in picture immediately otherwise
3748 enterPipRunnable.run();
3749 }
3750 return true;
3751 }
3752 } finally {
3753 Binder.restoreCallingIdentity(origId);
3754 }
3755 }
3756
3757 @Override
3758 public void setPictureInPictureParams(IBinder token, final PictureInPictureParams params) {
3759 final long origId = Binder.clearCallingIdentity();
3760 try {
3761 synchronized (mGlobalLock) {
3762 final ActivityRecord r = ensureValidPictureInPictureActivityParamsLocked(
3763 "setPictureInPictureParams", token, params);
3764
3765 // Only update the saved args from the args that are set
3766 r.pictureInPictureArgs.copyOnlySet(params);
3767 if (r.inPinnedWindowingMode()) {
3768 // If the activity is already in picture-in-picture, update the pinned stack now
3769 // if it is not already expanding to fullscreen. Otherwise, the arguments will
3770 // be used the next time the activity enters PiP
3771 final PinnedActivityStack stack = r.getStack();
3772 if (!stack.isAnimatingBoundsToFullscreen()) {
3773 stack.setPictureInPictureAspectRatio(
3774 r.pictureInPictureArgs.getAspectRatio());
3775 stack.setPictureInPictureActions(r.pictureInPictureArgs.getActions());
3776 }
3777 }
3778 logPictureInPictureArgs(params);
3779 }
3780 } finally {
3781 Binder.restoreCallingIdentity(origId);
3782 }
3783 }
3784
3785 @Override
3786 public int getMaxNumPictureInPictureActions(IBinder token) {
3787 // Currently, this is a static constant, but later, we may change this to be dependent on
3788 // the context of the activity
3789 return 3;
3790 }
3791
3792 private void logPictureInPictureArgs(PictureInPictureParams params) {
3793 if (params.hasSetActions()) {
3794 MetricsLogger.histogram(mContext, "tron_varz_picture_in_picture_actions_count",
3795 params.getActions().size());
3796 }
3797 if (params.hasSetAspectRatio()) {
3798 LogMaker lm = new LogMaker(MetricsEvent.ACTION_PICTURE_IN_PICTURE_ASPECT_RATIO_CHANGED);
3799 lm.addTaggedData(MetricsEvent.PICTURE_IN_PICTURE_ASPECT_RATIO, params.getAspectRatio());
3800 MetricsLogger.action(lm);
3801 }
3802 }
3803
3804 /**
3805 * Checks the state of the system and the activity associated with the given {@param token} to
3806 * verify that picture-in-picture is supported for that activity.
3807 *
3808 * @return the activity record for the given {@param token} if all the checks pass.
3809 */
3810 private ActivityRecord ensureValidPictureInPictureActivityParamsLocked(String caller,
3811 IBinder token, PictureInPictureParams params) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003812 if (!mSupportsPictureInPicture) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003813 throw new IllegalStateException(caller
3814 + ": Device doesn't support picture-in-picture mode.");
3815 }
3816
3817 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
3818 if (r == null) {
3819 throw new IllegalStateException(caller
3820 + ": Can't find activity for token=" + token);
3821 }
3822
3823 if (!r.supportsPictureInPicture()) {
3824 throw new IllegalStateException(caller
3825 + ": Current activity does not support picture-in-picture.");
3826 }
3827
3828 if (params.hasSetAspectRatio()
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003829 && !mWindowManager.isValidPictureInPictureAspectRatio(r.getStack().mDisplayId,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003830 params.getAspectRatio())) {
3831 final float minAspectRatio = mContext.getResources().getFloat(
3832 com.android.internal.R.dimen.config_pictureInPictureMinAspectRatio);
3833 final float maxAspectRatio = mContext.getResources().getFloat(
3834 com.android.internal.R.dimen.config_pictureInPictureMaxAspectRatio);
3835 throw new IllegalArgumentException(String.format(caller
3836 + ": Aspect ratio is too extreme (must be between %f and %f).",
3837 minAspectRatio, maxAspectRatio));
3838 }
3839
3840 // Truncate the number of actions if necessary
3841 params.truncateActions(getMaxNumPictureInPictureActions(token));
3842
3843 return r;
3844 }
3845
3846 @Override
3847 public IBinder getUriPermissionOwnerForActivity(IBinder activityToken) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003848 enforceNotIsolatedCaller("getUriPermissionOwnerForActivity");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003849 synchronized (mGlobalLock) {
3850 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
3851 if (r == null) {
3852 throw new IllegalArgumentException("Activity does not exist; token="
3853 + activityToken);
3854 }
Wale Ogunwale6d50dcc2018-07-21 23:00:40 -07003855 return r.getUriPermissionsLocked().getExternalToken();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003856 }
3857 }
3858
3859 @Override
3860 public void resizeDockedStack(Rect dockedBounds, Rect tempDockedTaskBounds,
3861 Rect tempDockedTaskInsetBounds,
3862 Rect tempOtherTaskBounds, Rect tempOtherTaskInsetBounds) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003863 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizeDockedStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003864 long ident = Binder.clearCallingIdentity();
3865 try {
3866 synchronized (mGlobalLock) {
3867 mStackSupervisor.resizeDockedStackLocked(dockedBounds, tempDockedTaskBounds,
3868 tempDockedTaskInsetBounds, tempOtherTaskBounds, tempOtherTaskInsetBounds,
3869 PRESERVE_WINDOWS);
3870 }
3871 } finally {
3872 Binder.restoreCallingIdentity(ident);
3873 }
3874 }
3875
3876 @Override
3877 public void setSplitScreenResizing(boolean resizing) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003878 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "setSplitScreenResizing()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003879 final long ident = Binder.clearCallingIdentity();
3880 try {
3881 synchronized (mGlobalLock) {
3882 mStackSupervisor.setSplitScreenResizing(resizing);
3883 }
3884 } finally {
3885 Binder.restoreCallingIdentity(ident);
3886 }
3887 }
3888
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003889 /**
3890 * Check that we have the features required for VR-related API calls, and throw an exception if
3891 * not.
3892 */
Wale Ogunwale59507092018-10-29 09:00:30 -07003893 public void enforceSystemHasVrFeature() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003894 if (!mContext.getPackageManager().hasSystemFeature(
3895 PackageManager.FEATURE_VR_MODE_HIGH_PERFORMANCE)) {
3896 throw new UnsupportedOperationException("VR mode not supported on this device!");
3897 }
3898 }
3899
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003900 @Override
3901 public int setVrMode(IBinder token, boolean enabled, ComponentName packageName) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003902 enforceSystemHasVrFeature();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003903
3904 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class);
3905
3906 ActivityRecord r;
3907 synchronized (mGlobalLock) {
3908 r = ActivityRecord.isInStackLocked(token);
3909 }
3910
3911 if (r == null) {
3912 throw new IllegalArgumentException();
3913 }
3914
3915 int err;
3916 if ((err = vrService.hasVrPackage(packageName, r.userId)) !=
3917 VrManagerInternal.NO_ERROR) {
3918 return err;
3919 }
3920
3921 // Clear the binder calling uid since this path may call moveToTask().
3922 final long callingId = Binder.clearCallingIdentity();
3923 try {
3924 synchronized (mGlobalLock) {
3925 r.requestedVrComponent = (enabled) ? packageName : null;
3926
3927 // Update associated state if this activity is currently focused
Andrii Kulian52d255c2018-07-13 11:32:19 -07003928 if (r.isResumedActivityOnDisplay()) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003929 applyUpdateVrModeLocked(r);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003930 }
3931 return 0;
3932 }
3933 } finally {
3934 Binder.restoreCallingIdentity(callingId);
3935 }
3936 }
3937
3938 @Override
3939 public void startLocalVoiceInteraction(IBinder callingActivity, Bundle options) {
3940 Slog.i(TAG, "Activity tried to startLocalVoiceInteraction");
3941 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003942 ActivityRecord activity = getTopDisplayFocusedStack().getTopActivity();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003943 if (ActivityRecord.forTokenLocked(callingActivity) != activity) {
3944 throw new SecurityException("Only focused activity can call startVoiceInteraction");
3945 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07003946 if (mRunningVoice != null || activity.getTask().voiceSession != null
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003947 || activity.voiceSession != null) {
3948 Slog.w(TAG, "Already in a voice interaction, cannot start new voice interaction");
3949 return;
3950 }
3951 if (activity.pendingVoiceInteractionStart) {
3952 Slog.w(TAG, "Pending start of voice interaction already.");
3953 return;
3954 }
3955 activity.pendingVoiceInteractionStart = true;
3956 }
3957 LocalServices.getService(VoiceInteractionManagerInternal.class)
3958 .startLocalVoiceInteraction(callingActivity, options);
3959 }
3960
3961 @Override
3962 public void stopLocalVoiceInteraction(IBinder callingActivity) {
3963 LocalServices.getService(VoiceInteractionManagerInternal.class)
3964 .stopLocalVoiceInteraction(callingActivity);
3965 }
3966
3967 @Override
3968 public boolean supportsLocalVoiceInteraction() {
3969 return LocalServices.getService(VoiceInteractionManagerInternal.class)
3970 .supportsLocalVoiceInteraction();
3971 }
3972
3973 /** Notifies all listeners when the pinned stack animation starts. */
3974 @Override
3975 public void notifyPinnedStackAnimationStarted() {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003976 mTaskChangeNotificationController.notifyPinnedStackAnimationStarted();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003977 }
3978
3979 /** Notifies all listeners when the pinned stack animation ends. */
3980 @Override
3981 public void notifyPinnedStackAnimationEnded() {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003982 mTaskChangeNotificationController.notifyPinnedStackAnimationEnded();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003983 }
3984
3985 @Override
3986 public void resizePinnedStack(Rect pinnedBounds, Rect tempPinnedTaskBounds) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003987 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizePinnedStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003988 final long ident = Binder.clearCallingIdentity();
3989 try {
3990 synchronized (mGlobalLock) {
3991 mStackSupervisor.resizePinnedStackLocked(pinnedBounds, tempPinnedTaskBounds);
3992 }
3993 } finally {
3994 Binder.restoreCallingIdentity(ident);
3995 }
3996 }
3997
3998 @Override
3999 public boolean updateDisplayOverrideConfiguration(Configuration values, int displayId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004000 mAmInternal.enforceCallingPermission(CHANGE_CONFIGURATION, "updateDisplayOverrideConfiguration()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004001
4002 synchronized (mGlobalLock) {
4003 // Check if display is initialized in AM.
4004 if (!mStackSupervisor.isDisplayAdded(displayId)) {
4005 // Call might come when display is not yet added or has already been removed.
4006 if (DEBUG_CONFIGURATION) {
4007 Slog.w(TAG, "Trying to update display configuration for non-existing displayId="
4008 + displayId);
4009 }
4010 return false;
4011 }
4012
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004013 if (values == null && mWindowManager != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004014 // sentinel: fetch the current configuration from the window manager
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004015 values = mWindowManager.computeNewConfiguration(displayId);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004016 }
4017
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004018 if (mWindowManager != null) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004019 final Message msg = PooledLambda.obtainMessage(
4020 ActivityManagerInternal::updateOomLevelsForDisplay, mAmInternal, displayId);
4021 mH.sendMessage(msg);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004022 }
4023
4024 final long origId = Binder.clearCallingIdentity();
4025 try {
4026 if (values != null) {
4027 Settings.System.clearConfiguration(values);
4028 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004029 updateDisplayOverrideConfigurationLocked(values, null /* starting */,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004030 false /* deferResume */, displayId, mTmpUpdateConfigurationResult);
4031 return mTmpUpdateConfigurationResult.changes != 0;
4032 } finally {
4033 Binder.restoreCallingIdentity(origId);
4034 }
4035 }
4036 }
4037
4038 @Override
4039 public boolean updateConfiguration(Configuration values) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004040 mAmInternal.enforceCallingPermission(CHANGE_CONFIGURATION, "updateConfiguration()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004041
4042 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004043 if (values == null && mWindowManager != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004044 // sentinel: fetch the current configuration from the window manager
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004045 values = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004046 }
4047
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004048 if (mWindowManager != null) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004049 final Message msg = PooledLambda.obtainMessage(
4050 ActivityManagerInternal::updateOomLevelsForDisplay, mAmInternal,
4051 DEFAULT_DISPLAY);
4052 mH.sendMessage(msg);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004053 }
4054
4055 final long origId = Binder.clearCallingIdentity();
4056 try {
4057 if (values != null) {
4058 Settings.System.clearConfiguration(values);
4059 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004060 updateConfigurationLocked(values, null, false, false /* persistent */,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004061 UserHandle.USER_NULL, false /* deferResume */,
4062 mTmpUpdateConfigurationResult);
4063 return mTmpUpdateConfigurationResult.changes != 0;
4064 } finally {
4065 Binder.restoreCallingIdentity(origId);
4066 }
4067 }
4068 }
4069
4070 @Override
4071 public void dismissKeyguard(IBinder token, IKeyguardDismissCallback callback,
4072 CharSequence message) {
4073 if (message != null) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004074 mAmInternal.enforceCallingPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004075 Manifest.permission.SHOW_KEYGUARD_MESSAGE, "dismissKeyguard()");
4076 }
4077 final long callingId = Binder.clearCallingIdentity();
4078 try {
4079 synchronized (mGlobalLock) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004080 mKeyguardController.dismissKeyguard(token, callback, message);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004081 }
4082 } finally {
4083 Binder.restoreCallingIdentity(callingId);
4084 }
4085 }
4086
4087 @Override
4088 public void cancelTaskWindowTransition(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004089 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004090 "cancelTaskWindowTransition()");
4091 final long ident = Binder.clearCallingIdentity();
4092 try {
4093 synchronized (mGlobalLock) {
4094 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
4095 MATCH_TASK_IN_STACKS_ONLY);
4096 if (task == null) {
4097 Slog.w(TAG, "cancelTaskWindowTransition: taskId=" + taskId + " not found");
4098 return;
4099 }
4100 task.cancelWindowTransition();
4101 }
4102 } finally {
4103 Binder.restoreCallingIdentity(ident);
4104 }
4105 }
4106
4107 @Override
4108 public ActivityManager.TaskSnapshot getTaskSnapshot(int taskId, boolean reducedResolution) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004109 enforceCallerIsRecentsOrHasPermission(READ_FRAME_BUFFER, "getTaskSnapshot()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004110 final long ident = Binder.clearCallingIdentity();
4111 try {
4112 final TaskRecord task;
4113 synchronized (mGlobalLock) {
4114 task = mStackSupervisor.anyTaskForIdLocked(taskId,
4115 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
4116 if (task == null) {
4117 Slog.w(TAG, "getTaskSnapshot: taskId=" + taskId + " not found");
4118 return null;
4119 }
4120 }
4121 // Don't call this while holding the lock as this operation might hit the disk.
4122 return task.getSnapshot(reducedResolution);
4123 } finally {
4124 Binder.restoreCallingIdentity(ident);
4125 }
4126 }
4127
4128 @Override
4129 public void setDisablePreviewScreenshots(IBinder token, boolean disable) {
4130 synchronized (mGlobalLock) {
4131 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4132 if (r == null) {
4133 Slog.w(TAG, "setDisablePreviewScreenshots: Unable to find activity for token="
4134 + token);
4135 return;
4136 }
4137 final long origId = Binder.clearCallingIdentity();
4138 try {
4139 r.setDisablePreviewScreenshots(disable);
4140 } finally {
4141 Binder.restoreCallingIdentity(origId);
4142 }
4143 }
4144 }
4145
4146 /** Return the user id of the last resumed activity. */
4147 @Override
4148 public @UserIdInt
4149 int getLastResumedActivityUserId() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004150 mAmInternal.enforceCallingPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004151 Manifest.permission.INTERACT_ACROSS_USERS_FULL, "getLastResumedActivityUserId()");
4152 synchronized (mGlobalLock) {
Wale Ogunwalef6733932018-06-27 05:14:34 -07004153 if (mLastResumedActivity == null) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004154 return getCurrentUserId();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004155 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07004156 return mLastResumedActivity.userId;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004157 }
4158 }
4159
4160 @Override
4161 public void updateLockTaskFeatures(int userId, int flags) {
4162 final int callingUid = Binder.getCallingUid();
4163 if (callingUid != 0 && callingUid != SYSTEM_UID) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004164 mAmInternal.enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004165 "updateLockTaskFeatures()");
4166 }
4167 synchronized (mGlobalLock) {
4168 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Allowing features " + userId + ":0x" +
4169 Integer.toHexString(flags));
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07004170 getLockTaskController().updateLockTaskFeatures(userId, flags);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004171 }
4172 }
4173
4174 @Override
4175 public void setShowWhenLocked(IBinder token, boolean showWhenLocked) {
4176 synchronized (mGlobalLock) {
4177 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4178 if (r == null) {
4179 return;
4180 }
4181 final long origId = Binder.clearCallingIdentity();
4182 try {
4183 r.setShowWhenLocked(showWhenLocked);
4184 } finally {
4185 Binder.restoreCallingIdentity(origId);
4186 }
4187 }
4188 }
4189
4190 @Override
4191 public void setTurnScreenOn(IBinder token, boolean turnScreenOn) {
4192 synchronized (mGlobalLock) {
4193 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4194 if (r == null) {
4195 return;
4196 }
4197 final long origId = Binder.clearCallingIdentity();
4198 try {
4199 r.setTurnScreenOn(turnScreenOn);
4200 } finally {
4201 Binder.restoreCallingIdentity(origId);
4202 }
4203 }
4204 }
4205
4206 @Override
4207 public void registerRemoteAnimations(IBinder token, RemoteAnimationDefinition definition) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004208 mAmInternal.enforceCallingPermission(CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004209 "registerRemoteAnimations");
4210 definition.setCallingPid(Binder.getCallingPid());
4211 synchronized (mGlobalLock) {
4212 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4213 if (r == null) {
4214 return;
4215 }
4216 final long origId = Binder.clearCallingIdentity();
4217 try {
4218 r.registerRemoteAnimations(definition);
4219 } finally {
4220 Binder.restoreCallingIdentity(origId);
4221 }
4222 }
4223 }
4224
4225 @Override
4226 public void registerRemoteAnimationForNextActivityStart(String packageName,
4227 RemoteAnimationAdapter adapter) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004228 mAmInternal.enforceCallingPermission(CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004229 "registerRemoteAnimationForNextActivityStart");
4230 adapter.setCallingPid(Binder.getCallingPid());
4231 synchronized (mGlobalLock) {
4232 final long origId = Binder.clearCallingIdentity();
4233 try {
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07004234 getActivityStartController().registerRemoteAnimationForNextActivityStart(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004235 packageName, adapter);
4236 } finally {
4237 Binder.restoreCallingIdentity(origId);
4238 }
4239 }
4240 }
4241
4242 /** @see android.app.ActivityManager#alwaysShowUnsupportedCompileSdkWarning */
4243 @Override
4244 public void alwaysShowUnsupportedCompileSdkWarning(ComponentName activity) {
4245 synchronized (mGlobalLock) {
4246 final long origId = Binder.clearCallingIdentity();
4247 try {
Wale Ogunwale008163e2018-07-23 23:11:08 -07004248 mAppWarnings.alwaysShowUnsupportedCompileSdkWarning(activity);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004249 } finally {
4250 Binder.restoreCallingIdentity(origId);
4251 }
4252 }
4253 }
Wale Ogunwale6767eae2018-05-03 15:52:51 -07004254
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004255 @Override
4256 public void setVrThread(int tid) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004257 enforceSystemHasVrFeature();
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004258 synchronized (mGlobalLock) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004259 final int pid = Binder.getCallingPid();
4260 final WindowProcessController wpc = mPidMap.get(pid);
4261 mVrController.setVrThreadLocked(tid, pid, wpc);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004262 }
4263 }
4264
4265 @Override
4266 public void setPersistentVrThread(int tid) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004267 if (checkCallingPermission(Manifest.permission.RESTRICTED_VR_ACCESS)
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004268 != PERMISSION_GRANTED) {
4269 final String msg = "Permission Denial: setPersistentVrThread() from pid="
4270 + Binder.getCallingPid()
4271 + ", uid=" + Binder.getCallingUid()
4272 + " requires " + Manifest.permission.RESTRICTED_VR_ACCESS;
4273 Slog.w(TAG, msg);
4274 throw new SecurityException(msg);
4275 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004276 enforceSystemHasVrFeature();
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004277 synchronized (mGlobalLock) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004278 final int pid = Binder.getCallingPid();
4279 final WindowProcessController proc = mPidMap.get(pid);
4280 mVrController.setPersistentVrThreadLocked(tid, pid, proc);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004281 }
4282 }
4283
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004284 @Override
4285 public void stopAppSwitches() {
4286 enforceCallerIsRecentsOrHasPermission(STOP_APP_SWITCHES, "stopAppSwitches");
4287 synchronized (mGlobalLock) {
4288 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() + APP_SWITCH_DELAY_TIME;
4289 mDidAppSwitch = false;
4290 getActivityStartController().schedulePendingActivityLaunches(APP_SWITCH_DELAY_TIME);
4291 }
4292 }
4293
4294 @Override
4295 public void resumeAppSwitches() {
4296 enforceCallerIsRecentsOrHasPermission(STOP_APP_SWITCHES, "resumeAppSwitches");
4297 synchronized (mGlobalLock) {
4298 // Note that we don't execute any pending app switches... we will
4299 // let those wait until either the timeout, or the next start
4300 // activity request.
4301 mAppSwitchesAllowedTime = 0;
4302 }
4303 }
4304
4305 void onStartActivitySetDidAppSwitch() {
4306 if (mDidAppSwitch) {
4307 // This is the second allowed switch since we stopped switches, so now just generally
4308 // allow switches. Use case:
4309 // - user presses home (switches disabled, switch to home, mDidAppSwitch now true);
4310 // - user taps a home icon (coming from home so allowed, we hit here and now allow
4311 // anyone to switch again).
4312 mAppSwitchesAllowedTime = 0;
4313 } else {
4314 mDidAppSwitch = true;
4315 }
4316 }
4317
4318 /** @return whether the system should disable UI modes incompatible with VR mode. */
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004319 boolean shouldDisableNonVrUiLocked() {
4320 return mVrController.shouldDisableNonVrUiLocked();
4321 }
4322
Wale Ogunwale53783742018-09-16 10:21:51 -07004323 private void applyUpdateVrModeLocked(ActivityRecord r) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004324 // VR apps are expected to run in a main display. If an app is turning on VR for
4325 // itself, but lives in a dynamic stack, then make sure that it is moved to the main
4326 // fullscreen stack before enabling VR Mode.
4327 // TODO: The goal of this code is to keep the VR app on the main display. When the
4328 // stack implementation changes in the future, keep in mind that the use of the fullscreen
4329 // stack is a means to move the activity to the main display and a moveActivityToDisplay()
4330 // option would be a better choice here.
4331 if (r.requestedVrComponent != null && r.getDisplayId() != DEFAULT_DISPLAY) {
4332 Slog.i(TAG, "Moving " + r.shortComponentName + " from stack " + r.getStackId()
4333 + " to main stack for VR");
4334 final ActivityStack stack = mStackSupervisor.getDefaultDisplay().getOrCreateStack(
4335 WINDOWING_MODE_FULLSCREEN, r.getActivityType(), true /* toTop */);
4336 moveTaskToStack(r.getTask().taskId, stack.mStackId, true /* toTop */);
4337 }
4338 mH.post(() -> {
4339 if (!mVrController.onVrModeChanged(r)) {
4340 return;
4341 }
4342 synchronized (mGlobalLock) {
4343 final boolean disableNonVrUi = mVrController.shouldDisableNonVrUiLocked();
4344 mWindowManager.disableNonVrUi(disableNonVrUi);
4345 if (disableNonVrUi) {
4346 // If we are in a VR mode where Picture-in-Picture mode is unsupported,
4347 // then remove the pinned stack.
4348 mStackSupervisor.removeStacksInWindowingModes(WINDOWING_MODE_PINNED);
4349 }
4350 }
4351 });
4352 }
4353
Wale Ogunwale53783742018-09-16 10:21:51 -07004354 @Override
4355 public int getPackageScreenCompatMode(String packageName) {
4356 enforceNotIsolatedCaller("getPackageScreenCompatMode");
4357 synchronized (mGlobalLock) {
4358 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName);
4359 }
4360 }
4361
4362 @Override
4363 public void setPackageScreenCompatMode(String packageName, int mode) {
4364 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4365 "setPackageScreenCompatMode");
4366 synchronized (mGlobalLock) {
4367 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode);
4368 }
4369 }
4370
4371 @Override
4372 public boolean getPackageAskScreenCompat(String packageName) {
4373 enforceNotIsolatedCaller("getPackageAskScreenCompat");
4374 synchronized (mGlobalLock) {
4375 return mCompatModePackages.getPackageAskCompatModeLocked(packageName);
4376 }
4377 }
4378
4379 @Override
4380 public void setPackageAskScreenCompat(String packageName, boolean ask) {
4381 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4382 "setPackageAskScreenCompat");
4383 synchronized (mGlobalLock) {
4384 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask);
4385 }
4386 }
4387
Wale Ogunwale64258362018-10-16 15:13:37 -07004388 public static String relaunchReasonToString(int relaunchReason) {
4389 switch (relaunchReason) {
4390 case RELAUNCH_REASON_WINDOWING_MODE_RESIZE:
4391 return "window_resize";
4392 case RELAUNCH_REASON_FREE_RESIZE:
4393 return "free_resize";
4394 default:
4395 return null;
4396 }
4397 }
4398
Andrii Kulian5f750bc2018-07-17 08:57:23 -07004399 ActivityStack getTopDisplayFocusedStack() {
4400 return mStackSupervisor.getTopDisplayFocusedStack();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004401 }
4402
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004403 /** Pokes the task persister. */
4404 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) {
4405 mRecentTasks.notifyTaskPersisterLocked(task, flush);
4406 }
4407
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004408 boolean isKeyguardLocked() {
4409 return mKeyguardController.isKeyguardLocked();
4410 }
4411
Wale Ogunwale31913b52018-10-13 08:29:31 -07004412 void dumpLastANRLocked(PrintWriter pw) {
4413 pw.println("ACTIVITY MANAGER LAST ANR (dumpsys activity lastanr)");
4414 if (mLastANRState == null) {
4415 pw.println(" <no ANR has occurred since boot>");
4416 } else {
4417 pw.println(mLastANRState);
4418 }
4419 }
4420
4421 void dumpLastANRTracesLocked(PrintWriter pw) {
4422 pw.println("ACTIVITY MANAGER LAST ANR TRACES (dumpsys activity lastanr-traces)");
4423
4424 final File[] files = new File(ANR_TRACE_DIR).listFiles();
4425 if (ArrayUtils.isEmpty(files)) {
4426 pw.println(" <no ANR has occurred since boot>");
4427 return;
4428 }
4429 // Find the latest file.
4430 File latest = null;
4431 for (File f : files) {
4432 if ((latest == null) || (latest.lastModified() < f.lastModified())) {
4433 latest = f;
Wale Ogunwalef6733932018-06-27 05:14:34 -07004434 }
Wale Ogunwale31913b52018-10-13 08:29:31 -07004435 }
4436 pw.print("File: ");
4437 pw.print(latest.getName());
4438 pw.println();
4439 try (BufferedReader in = new BufferedReader(new FileReader(latest))) {
4440 String line;
4441 while ((line = in.readLine()) != null) {
4442 pw.println(line);
4443 }
4444 } catch (IOException e) {
4445 pw.print("Unable to read: ");
4446 pw.print(e);
4447 pw.println();
4448 }
4449 }
4450
4451 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args,
4452 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) {
4453 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage,
4454 "ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)");
4455 }
4456
4457 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args,
4458 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage, String header) {
4459 pw.println(header);
4460
4461 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient,
4462 dumpPackage);
4463 boolean needSep = printedAnything;
4464
4465 boolean printed = ActivityStackSupervisor.printThisActivity(pw,
4466 mStackSupervisor.getTopResumedActivity(), dumpPackage, needSep,
4467 " ResumedActivity: ");
4468 if (printed) {
4469 printedAnything = true;
4470 needSep = false;
4471 }
4472
4473 if (dumpPackage == null) {
4474 if (needSep) {
4475 pw.println();
4476 }
4477 printedAnything = true;
4478 mStackSupervisor.dump(pw, " ");
4479 }
4480
4481 if (!printedAnything) {
4482 pw.println(" (nothing)");
4483 }
4484 }
4485
4486 void dumpActivityContainersLocked(PrintWriter pw) {
4487 pw.println("ACTIVITY MANAGER STARTER (dumpsys activity containers)");
4488 mStackSupervisor.dumpChildrenNames(pw, " ");
4489 pw.println(" ");
4490 }
4491
4492 void dumpActivityStarterLocked(PrintWriter pw, String dumpPackage) {
4493 pw.println("ACTIVITY MANAGER STARTER (dumpsys activity starter)");
4494 getActivityStartController().dump(pw, "", dumpPackage);
4495 }
4496
4497 /**
4498 * There are three things that cmd can be:
4499 * - a flattened component name that matches an existing activity
4500 * - the cmd arg isn't the flattened component name of an existing activity:
4501 * dump all activity whose component contains the cmd as a substring
4502 * - A hex number of the ActivityRecord object instance.
4503 *
4504 * @param dumpVisibleStacksOnly dump activity with {@param name} only if in a visible stack
4505 * @param dumpFocusedStackOnly dump activity with {@param name} only if in the focused stack
4506 */
4507 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args,
4508 int opti, boolean dumpAll, boolean dumpVisibleStacksOnly, boolean dumpFocusedStackOnly) {
4509 ArrayList<ActivityRecord> activities;
4510
4511 synchronized (mGlobalLock) {
4512 activities = mStackSupervisor.getDumpActivitiesLocked(name, dumpVisibleStacksOnly,
4513 dumpFocusedStackOnly);
4514 }
4515
4516 if (activities.size() <= 0) {
4517 return false;
4518 }
4519
4520 String[] newArgs = new String[args.length - opti];
4521 System.arraycopy(args, opti, newArgs, 0, args.length - opti);
4522
4523 TaskRecord lastTask = null;
4524 boolean needSep = false;
4525 for (int i = activities.size() - 1; i >= 0; i--) {
4526 ActivityRecord r = activities.get(i);
4527 if (needSep) {
4528 pw.println();
4529 }
4530 needSep = true;
4531 synchronized (mGlobalLock) {
4532 final TaskRecord task = r.getTask();
4533 if (lastTask != task) {
4534 lastTask = task;
4535 pw.print("TASK "); pw.print(lastTask.affinity);
4536 pw.print(" id="); pw.print(lastTask.taskId);
4537 pw.print(" userId="); pw.println(lastTask.userId);
4538 if (dumpAll) {
4539 lastTask.dump(pw, " ");
4540 }
4541 }
4542 }
4543 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll);
4544 }
4545 return true;
4546 }
4547
4548 /**
4549 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if
4550 * there is a thread associated with the activity.
4551 */
4552 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw,
4553 final ActivityRecord r, String[] args, boolean dumpAll) {
4554 String innerPrefix = prefix + " ";
4555 synchronized (mGlobalLock) {
4556 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName);
4557 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r)));
4558 pw.print(" pid=");
4559 if (r.hasProcess()) pw.println(r.app.getPid());
4560 else pw.println("(not running)");
4561 if (dumpAll) {
4562 r.dump(pw, innerPrefix);
4563 }
4564 }
4565 if (r.attachedToProcess()) {
4566 // flush anything that is already in the PrintWriter since the thread is going
4567 // to write to the file descriptor directly
4568 pw.flush();
4569 try {
4570 TransferPipe tp = new TransferPipe();
4571 try {
4572 r.app.getThread().dumpActivity(tp.getWriteFd(),
4573 r.appToken, innerPrefix, args);
4574 tp.go(fd);
4575 } finally {
4576 tp.kill();
4577 }
4578 } catch (IOException e) {
4579 pw.println(innerPrefix + "Failure while dumping the activity: " + e);
4580 } catch (RemoteException e) {
4581 pw.println(innerPrefix + "Got a RemoteException while dumping the activity");
4582 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07004583 }
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004584 }
4585
Wale Ogunwalef6733932018-06-27 05:14:34 -07004586 void writeSleepStateToProto(ProtoOutputStream proto) {
4587 for (ActivityTaskManagerInternal.SleepToken st : mStackSupervisor.mSleepTokens) {
4588 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SLEEP_TOKENS,
4589 st.toString());
4590 }
4591
4592 if (mRunningVoice != null) {
4593 final long vrToken = proto.start(
4594 ActivityManagerServiceDumpProcessesProto.RUNNING_VOICE);
4595 proto.write(ActivityManagerServiceDumpProcessesProto.Voice.SESSION,
4596 mRunningVoice.toString());
4597 mVoiceWakeLock.writeToProto(
4598 proto, ActivityManagerServiceDumpProcessesProto.Voice.WAKELOCK);
4599 proto.end(vrToken);
4600 }
4601
4602 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SLEEPING, mSleeping);
4603 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SHUTTING_DOWN,
4604 mShuttingDown);
4605 mVrController.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.VR_CONTROLLER);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004606 }
4607
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004608 int getCurrentUserId() {
4609 return mAmInternal.getCurrentUserId();
4610 }
4611
4612 private void enforceNotIsolatedCaller(String caller) {
4613 if (UserHandle.isIsolated(Binder.getCallingUid())) {
4614 throw new SecurityException("Isolated process not allowed to call " + caller);
4615 }
4616 }
4617
Wale Ogunwalef6733932018-06-27 05:14:34 -07004618 public Configuration getConfiguration() {
4619 Configuration ci;
4620 synchronized(mGlobalLock) {
Yunfan Chen75157d72018-07-27 14:47:21 +09004621 ci = new Configuration(getGlobalConfigurationForCallingPid());
Wale Ogunwalef6733932018-06-27 05:14:34 -07004622 ci.userSetLocale = false;
4623 }
4624 return ci;
4625 }
4626
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004627 /**
4628 * Current global configuration information. Contains general settings for the entire system,
4629 * also corresponds to the merged configuration of the default display.
4630 */
4631 Configuration getGlobalConfiguration() {
4632 return mStackSupervisor.getConfiguration();
4633 }
4634
4635 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4636 boolean initLocale) {
4637 return updateConfigurationLocked(values, starting, initLocale, false /* deferResume */);
4638 }
4639
4640 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4641 boolean initLocale, boolean deferResume) {
4642 // pass UserHandle.USER_NULL as userId because we don't persist configuration for any user
4643 return updateConfigurationLocked(values, starting, initLocale, false /* persistent */,
4644 UserHandle.USER_NULL, deferResume);
4645 }
4646
Wale Ogunwale59507092018-10-29 09:00:30 -07004647 public void updatePersistentConfiguration(Configuration values, @UserIdInt int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004648 final long origId = Binder.clearCallingIdentity();
4649 try {
4650 synchronized (mGlobalLock) {
4651 updateConfigurationLocked(values, null, false, true, userId,
4652 false /* deferResume */);
4653 }
4654 } finally {
4655 Binder.restoreCallingIdentity(origId);
4656 }
4657 }
4658
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004659 private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4660 boolean initLocale, boolean persistent, int userId, boolean deferResume) {
4661 return updateConfigurationLocked(values, starting, initLocale, persistent, userId,
4662 deferResume, null /* result */);
4663 }
4664
4665 /**
4666 * Do either or both things: (1) change the current configuration, and (2)
4667 * make sure the given activity is running with the (now) current
4668 * configuration. Returns true if the activity has been left running, or
4669 * false if <var>starting</var> is being destroyed to match the new
4670 * configuration.
4671 *
4672 * @param userId is only used when persistent parameter is set to true to persist configuration
4673 * for that particular user
4674 */
4675 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4676 boolean initLocale, boolean persistent, int userId, boolean deferResume,
4677 ActivityTaskManagerService.UpdateConfigurationResult result) {
4678 int changes = 0;
4679 boolean kept = true;
4680
4681 if (mWindowManager != null) {
4682 mWindowManager.deferSurfaceLayout();
4683 }
4684 try {
4685 if (values != null) {
4686 changes = updateGlobalConfigurationLocked(values, initLocale, persistent, userId,
4687 deferResume);
4688 }
4689
4690 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes);
4691 } finally {
4692 if (mWindowManager != null) {
4693 mWindowManager.continueSurfaceLayout();
4694 }
4695 }
4696
4697 if (result != null) {
4698 result.changes = changes;
4699 result.activityRelaunched = !kept;
4700 }
4701 return kept;
4702 }
4703
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004704 /** Update default (global) configuration and notify listeners about changes. */
4705 private int updateGlobalConfigurationLocked(@NonNull Configuration values, boolean initLocale,
4706 boolean persistent, int userId, boolean deferResume) {
4707 mTempConfig.setTo(getGlobalConfiguration());
4708 final int changes = mTempConfig.updateFrom(values);
4709 if (changes == 0) {
4710 // Since calling to Activity.setRequestedOrientation leads to freezing the window with
4711 // setting WindowManagerService.mWaitingForConfig to true, it is important that we call
4712 // performDisplayOverrideConfigUpdate in order to send the new display configuration
4713 // (even if there are no actual changes) to unfreeze the window.
4714 performDisplayOverrideConfigUpdate(values, deferResume, DEFAULT_DISPLAY);
4715 return 0;
4716 }
4717
4718 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) Slog.i(TAG_CONFIGURATION,
4719 "Updating global configuration to: " + values);
4720
4721 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes);
4722 StatsLog.write(StatsLog.RESOURCE_CONFIGURATION_CHANGED,
4723 values.colorMode,
4724 values.densityDpi,
4725 values.fontScale,
4726 values.hardKeyboardHidden,
4727 values.keyboard,
4728 values.keyboardHidden,
4729 values.mcc,
4730 values.mnc,
4731 values.navigation,
4732 values.navigationHidden,
4733 values.orientation,
4734 values.screenHeightDp,
4735 values.screenLayout,
4736 values.screenWidthDp,
4737 values.smallestScreenWidthDp,
4738 values.touchscreen,
4739 values.uiMode);
4740
4741
4742 if (!initLocale && !values.getLocales().isEmpty() && values.userSetLocale) {
4743 final LocaleList locales = values.getLocales();
4744 int bestLocaleIndex = 0;
4745 if (locales.size() > 1) {
4746 if (mSupportedSystemLocales == null) {
4747 mSupportedSystemLocales = Resources.getSystem().getAssets().getLocales();
4748 }
4749 bestLocaleIndex = Math.max(0, locales.getFirstMatchIndex(mSupportedSystemLocales));
4750 }
4751 SystemProperties.set("persist.sys.locale",
4752 locales.get(bestLocaleIndex).toLanguageTag());
4753 LocaleList.setDefault(locales, bestLocaleIndex);
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004754
4755 final Message m = PooledLambda.obtainMessage(
4756 ActivityTaskManagerService::sendLocaleToMountDaemonMsg, this,
4757 locales.get(bestLocaleIndex));
4758 mH.sendMessage(m);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004759 }
4760
Yunfan Chen75157d72018-07-27 14:47:21 +09004761 mTempConfig.seq = increaseConfigurationSeqLocked();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004762
4763 // Update stored global config and notify everyone about the change.
4764 mStackSupervisor.onConfigurationChanged(mTempConfig);
4765
4766 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + mTempConfig);
4767 // TODO(multi-display): Update UsageEvents#Event to include displayId.
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004768 mUsageStatsInternal.reportConfigurationChange(mTempConfig, mAmInternal.getCurrentUserId());
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004769
4770 // TODO: If our config changes, should we auto dismiss any currently showing dialogs?
Wale Ogunwalef6733932018-06-27 05:14:34 -07004771 updateShouldShowDialogsLocked(mTempConfig);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004772
4773 AttributeCache ac = AttributeCache.instance();
4774 if (ac != null) {
4775 ac.updateConfiguration(mTempConfig);
4776 }
4777
4778 // Make sure all resources in our process are updated right now, so that anyone who is going
4779 // to retrieve resource values after we return will be sure to get the new ones. This is
4780 // especially important during boot, where the first config change needs to guarantee all
4781 // resources have that config before following boot code is executed.
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004782 mSystemThread.applyConfigurationToResources(mTempConfig);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004783
4784 // We need another copy of global config because we're scheduling some calls instead of
4785 // running them in place. We need to be sure that object we send will be handled unchanged.
4786 final Configuration configCopy = new Configuration(mTempConfig);
4787 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004788 final Message msg = PooledLambda.obtainMessage(
4789 ActivityTaskManagerService::sendPutConfigurationForUserMsg,
4790 this, userId, configCopy);
4791 mH.sendMessage(msg);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004792 }
4793
Yunfan Chen34fcc7a2018-10-11 16:26:09 -07004794 for (int i = mPidMap.size() - 1; i >= 0; i--) {
Yunfan Chen79b96062018-10-17 12:45:23 -07004795 final int pid = mPidMap.keyAt(i);
4796 final WindowProcessController app = mPidMap.get(pid);
Yunfan Chen34fcc7a2018-10-11 16:26:09 -07004797 if (DEBUG_CONFIGURATION) {
4798 Slog.v(TAG_CONFIGURATION, "Update process config of "
4799 + app.mName + " to new config " + configCopy);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004800 }
Yunfan Chen34fcc7a2018-10-11 16:26:09 -07004801 app.onConfigurationChanged(configCopy);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004802 }
4803
Wale Ogunwale2ea36d42018-10-18 10:27:31 -07004804 final Message msg = PooledLambda.obtainMessage(
4805 ActivityManagerInternal::broadcastGlobalConfigurationChanged,
4806 mAmInternal, changes, initLocale);
4807 mH.sendMessage(msg);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004808
4809 // Override configuration of the default display duplicates global config, so we need to
4810 // update it also. This will also notify WindowManager about changes.
4811 performDisplayOverrideConfigUpdate(mStackSupervisor.getConfiguration(), deferResume,
4812 DEFAULT_DISPLAY);
4813
4814 return changes;
4815 }
4816
4817 boolean updateDisplayOverrideConfigurationLocked(Configuration values, ActivityRecord starting,
4818 boolean deferResume, int displayId) {
4819 return updateDisplayOverrideConfigurationLocked(values, starting, deferResume /* deferResume */,
4820 displayId, null /* result */);
4821 }
4822
4823 /**
4824 * Updates override configuration specific for the selected display. If no config is provided,
4825 * new one will be computed in WM based on current display info.
4826 */
4827 boolean updateDisplayOverrideConfigurationLocked(Configuration values,
4828 ActivityRecord starting, boolean deferResume, int displayId,
4829 ActivityTaskManagerService.UpdateConfigurationResult result) {
4830 int changes = 0;
4831 boolean kept = true;
4832
4833 if (mWindowManager != null) {
4834 mWindowManager.deferSurfaceLayout();
4835 }
4836 try {
4837 if (values != null) {
4838 if (displayId == DEFAULT_DISPLAY) {
4839 // Override configuration of the default display duplicates global config, so
4840 // we're calling global config update instead for default display. It will also
4841 // apply the correct override config.
4842 changes = updateGlobalConfigurationLocked(values, false /* initLocale */,
4843 false /* persistent */, UserHandle.USER_NULL /* userId */, deferResume);
4844 } else {
4845 changes = performDisplayOverrideConfigUpdate(values, deferResume, displayId);
4846 }
4847 }
4848
4849 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes);
4850 } finally {
4851 if (mWindowManager != null) {
4852 mWindowManager.continueSurfaceLayout();
4853 }
4854 }
4855
4856 if (result != null) {
4857 result.changes = changes;
4858 result.activityRelaunched = !kept;
4859 }
4860 return kept;
4861 }
4862
4863 private int performDisplayOverrideConfigUpdate(Configuration values, boolean deferResume,
4864 int displayId) {
4865 mTempConfig.setTo(mStackSupervisor.getDisplayOverrideConfiguration(displayId));
4866 final int changes = mTempConfig.updateFrom(values);
4867 if (changes != 0) {
4868 Slog.i(TAG, "Override config changes=" + Integer.toHexString(changes) + " "
4869 + mTempConfig + " for displayId=" + displayId);
4870 mStackSupervisor.setDisplayOverrideConfiguration(mTempConfig, displayId);
4871
4872 final boolean isDensityChange = (changes & ActivityInfo.CONFIG_DENSITY) != 0;
4873 if (isDensityChange && displayId == DEFAULT_DISPLAY) {
Wale Ogunwale008163e2018-07-23 23:11:08 -07004874 mAppWarnings.onDensityChanged();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004875
Wale Ogunwale5c918702018-10-18 11:06:33 -07004876 // Post message to start process to avoid possible deadlock of calling into AMS with
4877 // the ATMS lock held.
4878 final Message msg = PooledLambda.obtainMessage(
4879 ActivityManagerInternal::killAllBackgroundProcessesExcept, mAmInternal,
4880 N, ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE);
4881 mH.sendMessage(msg);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004882 }
4883 }
4884
4885 // Update the configuration with WM first and check if any of the stacks need to be resized
4886 // due to the configuration change. If so, resize the stacks now and do any relaunches if
4887 // necessary. This way we don't need to relaunch again afterwards in
4888 // ensureActivityConfiguration().
4889 if (mWindowManager != null) {
4890 final int[] resizedStacks =
4891 mWindowManager.setNewDisplayOverrideConfiguration(mTempConfig, displayId);
4892 if (resizedStacks != null) {
4893 for (int stackId : resizedStacks) {
4894 resizeStackWithBoundsFromWindowManager(stackId, deferResume);
4895 }
4896 }
4897 }
4898
4899 return changes;
4900 }
4901
Wale Ogunwalef6733932018-06-27 05:14:34 -07004902 private void updateEventDispatchingLocked(boolean booted) {
4903 mWindowManager.setEventDispatching(booted && !mShuttingDown);
4904 }
4905
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004906 private void sendPutConfigurationForUserMsg(int userId, Configuration config) {
4907 final ContentResolver resolver = mContext.getContentResolver();
4908 Settings.System.putConfigurationForUser(resolver, config, userId);
4909 }
4910
4911 private void sendLocaleToMountDaemonMsg(Locale l) {
4912 try {
4913 IBinder service = ServiceManager.getService("mount");
4914 IStorageManager storageManager = IStorageManager.Stub.asInterface(service);
4915 Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI");
4916 storageManager.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag());
4917 } catch (RemoteException e) {
4918 Log.e(TAG, "Error storing locale for decryption UI", e);
4919 }
4920 }
4921
4922 boolean isActivityStartsLoggingEnabled() {
4923 return mAmInternal.isActivityStartsLoggingEnabled();
4924 }
4925
Wale Ogunwalef6733932018-06-27 05:14:34 -07004926 void enableScreenAfterBoot(boolean booted) {
4927 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN,
4928 SystemClock.uptimeMillis());
4929 mWindowManager.enableScreenAfterBoot();
4930
4931 synchronized (mGlobalLock) {
4932 updateEventDispatchingLocked(booted);
4933 }
4934 }
4935
Wale Ogunwale906f9c62018-07-23 11:23:44 -07004936 static long getInputDispatchingTimeoutLocked(ActivityRecord r) {
4937 if (r == null || !r.hasProcess()) {
4938 return KEY_DISPATCHING_TIMEOUT_MS;
4939 }
4940 return getInputDispatchingTimeoutLocked(r.app);
4941 }
4942
4943 private static long getInputDispatchingTimeoutLocked(WindowProcessController r) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07004944 return r != null ? r.getInputDispatchingTimeout() : KEY_DISPATCHING_TIMEOUT_MS;
Wale Ogunwale906f9c62018-07-23 11:23:44 -07004945 }
4946
Wale Ogunwalef6733932018-06-27 05:14:34 -07004947 /**
4948 * Decide based on the configuration whether we should show the ANR,
4949 * crash, etc dialogs. The idea is that if there is no affordance to
4950 * press the on-screen buttons, or the user experience would be more
4951 * greatly impacted than the crash itself, we shouldn't show the dialog.
4952 *
4953 * A thought: SystemUI might also want to get told about this, the Power
4954 * dialog / global actions also might want different behaviors.
4955 */
4956 private void updateShouldShowDialogsLocked(Configuration config) {
4957 final boolean inputMethodExists = !(config.keyboard == Configuration.KEYBOARD_NOKEYS
4958 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH
4959 && config.navigation == Configuration.NAVIGATION_NONAV);
4960 int modeType = config.uiMode & Configuration.UI_MODE_TYPE_MASK;
4961 final boolean uiModeSupportsDialogs = (modeType != Configuration.UI_MODE_TYPE_CAR
4962 && !(modeType == Configuration.UI_MODE_TYPE_WATCH && Build.IS_USER)
4963 && modeType != Configuration.UI_MODE_TYPE_TELEVISION
4964 && modeType != Configuration.UI_MODE_TYPE_VR_HEADSET);
4965 final boolean hideDialogsSet = Settings.Global.getInt(mContext.getContentResolver(),
4966 HIDE_ERROR_DIALOGS, 0) != 0;
4967 mShowDialogs = inputMethodExists && uiModeSupportsDialogs && !hideDialogsSet;
4968 }
4969
4970 private void updateFontScaleIfNeeded(@UserIdInt int userId) {
4971 final float scaleFactor = Settings.System.getFloatForUser(mContext.getContentResolver(),
4972 FONT_SCALE, 1.0f, userId);
4973
4974 synchronized (this) {
4975 if (getGlobalConfiguration().fontScale == scaleFactor) {
4976 return;
4977 }
4978
4979 final Configuration configuration
4980 = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY);
4981 configuration.fontScale = scaleFactor;
4982 updatePersistentConfiguration(configuration, userId);
4983 }
4984 }
4985
4986 // Actually is sleeping or shutting down or whatever else in the future
4987 // is an inactive state.
4988 boolean isSleepingOrShuttingDownLocked() {
4989 return isSleepingLocked() || mShuttingDown;
4990 }
4991
4992 boolean isSleepingLocked() {
4993 return mSleeping;
4994 }
4995
Riddle Hsu16567132018-08-16 21:37:47 +08004996 /** Update AMS states when an activity is resumed. */
Wale Ogunwalef6733932018-06-27 05:14:34 -07004997 void setResumedActivityUncheckLocked(ActivityRecord r, String reason) {
4998 final TaskRecord task = r.getTask();
4999 if (task.isActivityTypeStandard()) {
5000 if (mCurAppTimeTracker != r.appTimeTracker) {
5001 // We are switching app tracking. Complete the current one.
5002 if (mCurAppTimeTracker != null) {
5003 mCurAppTimeTracker.stop();
5004 mH.obtainMessage(
5005 REPORT_TIME_TRACKER_MSG, mCurAppTimeTracker).sendToTarget();
5006 mStackSupervisor.clearOtherAppTimeTrackers(r.appTimeTracker);
5007 mCurAppTimeTracker = null;
5008 }
5009 if (r.appTimeTracker != null) {
5010 mCurAppTimeTracker = r.appTimeTracker;
5011 startTimeTrackingFocusedActivityLocked();
5012 }
5013 } else {
5014 startTimeTrackingFocusedActivityLocked();
5015 }
5016 } else {
5017 r.appTimeTracker = null;
5018 }
5019 // TODO: VI Maybe r.task.voiceInteractor || r.voiceInteractor != null
5020 // TODO: Probably not, because we don't want to resume voice on switching
5021 // back to this activity
5022 if (task.voiceInteractor != null) {
5023 startRunningVoiceLocked(task.voiceSession, r.info.applicationInfo.uid);
5024 } else {
5025 finishRunningVoiceLocked();
5026
5027 if (mLastResumedActivity != null) {
5028 final IVoiceInteractionSession session;
5029
5030 final TaskRecord lastResumedActivityTask = mLastResumedActivity.getTask();
5031 if (lastResumedActivityTask != null
5032 && lastResumedActivityTask.voiceSession != null) {
5033 session = lastResumedActivityTask.voiceSession;
5034 } else {
5035 session = mLastResumedActivity.voiceSession;
5036 }
5037
5038 if (session != null) {
5039 // We had been in a voice interaction session, but now focused has
5040 // move to something different. Just finish the session, we can't
5041 // return to it and retain the proper state and synchronization with
5042 // the voice interaction service.
5043 finishVoiceTask(session);
5044 }
5045 }
5046 }
5047
5048 if (mLastResumedActivity != null && r.userId != mLastResumedActivity.userId) {
5049 mAmInternal.sendForegroundProfileChanged(r.userId);
5050 }
5051 updateResumedAppTrace(r);
5052 mLastResumedActivity = r;
5053
Tiger Huang1e5b10a2018-07-30 20:19:51 +08005054 r.getDisplay().setFocusedApp(r, true);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005055
5056 applyUpdateLockStateLocked(r);
5057 applyUpdateVrModeLocked(r);
5058
5059 EventLogTags.writeAmSetResumedActivity(
5060 r == null ? -1 : r.userId,
5061 r == null ? "NULL" : r.shortComponentName,
5062 reason);
5063 }
5064
5065 ActivityTaskManagerInternal.SleepToken acquireSleepToken(String tag, int displayId) {
5066 synchronized (mGlobalLock) {
5067 final ActivityTaskManagerInternal.SleepToken token = mStackSupervisor.createSleepTokenLocked(tag, displayId);
5068 updateSleepIfNeededLocked();
5069 return token;
5070 }
5071 }
5072
5073 void updateSleepIfNeededLocked() {
5074 final boolean shouldSleep = !mStackSupervisor.hasAwakeDisplay();
5075 final boolean wasSleeping = mSleeping;
5076 boolean updateOomAdj = false;
5077
5078 if (!shouldSleep) {
5079 // If wasSleeping is true, we need to wake up activity manager state from when
5080 // we started sleeping. In either case, we need to apply the sleep tokens, which
5081 // will wake up stacks or put them to sleep as appropriate.
5082 if (wasSleeping) {
5083 mSleeping = false;
Chenjie Yubd1a28f2018-07-17 14:55:19 -07005084 StatsLog.write(StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED,
5085 StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED__STATE__AWAKE);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005086 startTimeTrackingFocusedActivityLocked();
5087 mTopProcessState = ActivityManager.PROCESS_STATE_TOP;
5088 mStackSupervisor.comeOutOfSleepIfNeededLocked();
5089 }
5090 mStackSupervisor.applySleepTokensLocked(true /* applyToStacks */);
5091 if (wasSleeping) {
5092 updateOomAdj = true;
5093 }
5094 } else if (!mSleeping && shouldSleep) {
5095 mSleeping = true;
Chenjie Yubd1a28f2018-07-17 14:55:19 -07005096 StatsLog.write(StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED,
5097 StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED__STATE__ASLEEP);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005098 if (mCurAppTimeTracker != null) {
5099 mCurAppTimeTracker.stop();
5100 }
5101 mTopProcessState = ActivityManager.PROCESS_STATE_TOP_SLEEPING;
5102 mStackSupervisor.goingToSleepLocked();
5103 updateResumedAppTrace(null /* resumed */);
5104 updateOomAdj = true;
5105 }
5106 if (updateOomAdj) {
5107 mH.post(mAmInternal::updateOomAdj);
5108 }
5109 }
5110
5111 void updateOomAdj() {
5112 mH.post(mAmInternal::updateOomAdj);
5113 }
5114
Wale Ogunwale53783742018-09-16 10:21:51 -07005115 void updateCpuStats() {
5116 mH.post(mAmInternal::updateCpuStats);
5117 }
5118
5119 void updateUsageStats(ActivityRecord component, boolean resumed) {
5120 final Message m = PooledLambda.obtainMessage(ActivityManagerInternal::updateUsageStats,
5121 mAmInternal, component.realActivity, component.app.mUid, component.userId, resumed);
5122 mH.sendMessage(m);
5123 }
5124
5125 void setBooting(boolean booting) {
5126 mAmInternal.setBooting(booting);
5127 }
5128
5129 boolean isBooting() {
5130 return mAmInternal.isBooting();
5131 }
5132
5133 void setBooted(boolean booted) {
5134 mAmInternal.setBooted(booted);
5135 }
5136
5137 boolean isBooted() {
5138 return mAmInternal.isBooted();
5139 }
5140
5141 void postFinishBooting(boolean finishBooting, boolean enableScreen) {
5142 mH.post(() -> {
5143 if (finishBooting) {
5144 mAmInternal.finishBooting();
5145 }
5146 if (enableScreen) {
5147 mInternal.enableScreenAfterBoot(isBooted());
5148 }
5149 });
5150 }
5151
5152 void setHeavyWeightProcess(ActivityRecord root) {
5153 mHeavyWeightProcess = root.app;
5154 final Message m = PooledLambda.obtainMessage(
5155 ActivityTaskManagerService::postHeavyWeightProcessNotification, this,
5156 root.app, root.intent, root.userId);
5157 mH.sendMessage(m);
5158 }
5159
5160 void clearHeavyWeightProcessIfEquals(WindowProcessController proc) {
5161 if (mHeavyWeightProcess == null || mHeavyWeightProcess != proc) {
5162 return;
5163 }
5164
5165 mHeavyWeightProcess = null;
5166 final Message m = PooledLambda.obtainMessage(
5167 ActivityTaskManagerService::cancelHeavyWeightProcessNotification, this,
5168 proc.mUserId);
5169 mH.sendMessage(m);
5170 }
5171
5172 private void cancelHeavyWeightProcessNotification(int userId) {
5173 final INotificationManager inm = NotificationManager.getService();
5174 if (inm == null) {
5175 return;
5176 }
5177 try {
5178 inm.cancelNotificationWithTag("android", null,
5179 SystemMessage.NOTE_HEAVY_WEIGHT_NOTIFICATION, userId);
5180 } catch (RuntimeException e) {
5181 Slog.w(TAG, "Error canceling notification for service", e);
5182 } catch (RemoteException e) {
5183 }
5184
5185 }
5186
5187 private void postHeavyWeightProcessNotification(
5188 WindowProcessController proc, Intent intent, int userId) {
5189 if (proc == null) {
5190 return;
5191 }
5192
5193 final INotificationManager inm = NotificationManager.getService();
5194 if (inm == null) {
5195 return;
5196 }
5197
5198 try {
5199 Context context = mContext.createPackageContext(proc.mInfo.packageName, 0);
5200 String text = mContext.getString(R.string.heavy_weight_notification,
5201 context.getApplicationInfo().loadLabel(context.getPackageManager()));
5202 Notification notification =
5203 new Notification.Builder(context,
5204 SystemNotificationChannels.HEAVY_WEIGHT_APP)
5205 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb)
5206 .setWhen(0)
5207 .setOngoing(true)
5208 .setTicker(text)
5209 .setColor(mContext.getColor(
5210 com.android.internal.R.color.system_notification_accent_color))
5211 .setContentTitle(text)
5212 .setContentText(
5213 mContext.getText(R.string.heavy_weight_notification_detail))
5214 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0,
5215 intent, PendingIntent.FLAG_CANCEL_CURRENT, null,
5216 new UserHandle(userId)))
5217 .build();
5218 try {
5219 inm.enqueueNotificationWithTag("android", "android", null,
5220 SystemMessage.NOTE_HEAVY_WEIGHT_NOTIFICATION, notification, userId);
5221 } catch (RuntimeException e) {
5222 Slog.w(TAG, "Error showing notification for heavy-weight app", e);
5223 } catch (RemoteException e) {
5224 }
5225 } catch (PackageManager.NameNotFoundException e) {
5226 Slog.w(TAG, "Unable to create context for heavy notification", e);
5227 }
5228
5229 }
5230
Wale Ogunwaleee6eca12018-09-19 20:37:53 -07005231 IIntentSender getIntentSenderLocked(int type, String packageName, int callingUid, int userId,
5232 IBinder token, String resultWho, int requestCode, Intent[] intents,
5233 String[] resolvedTypes, int flags, Bundle bOptions) {
5234
5235 ActivityRecord activity = null;
5236 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) {
5237 activity = ActivityRecord.isInStackLocked(token);
5238 if (activity == null) {
5239 Slog.w(TAG, "Failed createPendingResult: activity " + token + " not in any stack");
5240 return null;
5241 }
5242 if (activity.finishing) {
5243 Slog.w(TAG, "Failed createPendingResult: activity " + activity + " is finishing");
5244 return null;
5245 }
5246 }
5247
5248 final PendingIntentRecord rec = mPendingIntentController.getIntentSender(type, packageName,
5249 callingUid, userId, token, resultWho, requestCode, intents, resolvedTypes, flags,
5250 bOptions);
5251 final boolean noCreate = (flags & PendingIntent.FLAG_NO_CREATE) != 0;
5252 if (noCreate) {
5253 return rec;
5254 }
5255 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) {
5256 if (activity.pendingResults == null) {
5257 activity.pendingResults = new HashSet<>();
5258 }
5259 activity.pendingResults.add(rec.ref);
5260 }
5261 return rec;
5262 }
5263
Andrii Kulian52d255c2018-07-13 11:32:19 -07005264 // TODO(b/111541062): Update app time tracking to make it aware of multiple resumed activities
Wale Ogunwalef6733932018-06-27 05:14:34 -07005265 private void startTimeTrackingFocusedActivityLocked() {
Andrii Kulian52d255c2018-07-13 11:32:19 -07005266 final ActivityRecord resumedActivity = mStackSupervisor.getTopResumedActivity();
Wale Ogunwalef6733932018-06-27 05:14:34 -07005267 if (!mSleeping && mCurAppTimeTracker != null && resumedActivity != null) {
5268 mCurAppTimeTracker.start(resumedActivity.packageName);
5269 }
5270 }
5271
5272 private void updateResumedAppTrace(@Nullable ActivityRecord resumed) {
5273 if (mTracedResumedActivity != null) {
5274 Trace.asyncTraceEnd(TRACE_TAG_ACTIVITY_MANAGER,
5275 constructResumedTraceName(mTracedResumedActivity.packageName), 0);
5276 }
5277 if (resumed != null) {
5278 Trace.asyncTraceBegin(TRACE_TAG_ACTIVITY_MANAGER,
5279 constructResumedTraceName(resumed.packageName), 0);
5280 }
5281 mTracedResumedActivity = resumed;
5282 }
5283
5284 private String constructResumedTraceName(String packageName) {
5285 return "focused app: " + packageName;
5286 }
5287
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005288 /** Helper method that requests bounds from WM and applies them to stack. */
5289 private void resizeStackWithBoundsFromWindowManager(int stackId, boolean deferResume) {
5290 final Rect newStackBounds = new Rect();
5291 final ActivityStack stack = mStackSupervisor.getStack(stackId);
5292
5293 // TODO(b/71548119): Revert CL introducing below once cause of mismatch is found.
5294 if (stack == null) {
5295 final StringWriter writer = new StringWriter();
5296 final PrintWriter printWriter = new PrintWriter(writer);
5297 mStackSupervisor.dumpDisplays(printWriter);
5298 printWriter.flush();
5299
5300 Log.wtf(TAG, "stack not found:" + stackId + " displays:" + writer);
5301 }
5302
5303 stack.getBoundsForNewConfiguration(newStackBounds);
5304 mStackSupervisor.resizeStackLocked(
5305 stack, !newStackBounds.isEmpty() ? newStackBounds : null /* bounds */,
5306 null /* tempTaskBounds */, null /* tempTaskInsetBounds */,
5307 false /* preserveWindows */, false /* allowResizeInDockedMode */, deferResume);
5308 }
5309
5310 /** Applies latest configuration and/or visibility updates if needed. */
5311 private boolean ensureConfigAndVisibilityAfterUpdate(ActivityRecord starting, int changes) {
5312 boolean kept = true;
Andrii Kulian5f750bc2018-07-17 08:57:23 -07005313 final ActivityStack mainStack = mStackSupervisor.getTopDisplayFocusedStack();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005314 // mainStack is null during startup.
5315 if (mainStack != null) {
5316 if (changes != 0 && starting == null) {
5317 // If the configuration changed, and the caller is not already
5318 // in the process of starting an activity, then find the top
5319 // activity to check if its configuration needs to change.
5320 starting = mainStack.topRunningActivityLocked();
5321 }
5322
5323 if (starting != null) {
5324 kept = starting.ensureActivityConfiguration(changes,
5325 false /* preserveWindow */);
5326 // And we need to make sure at this point that all other activities
5327 // are made visible with the correct configuration.
5328 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes,
5329 !PRESERVE_WINDOWS);
5330 }
5331 }
5332
5333 return kept;
5334 }
5335
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005336 void scheduleAppGcsLocked() {
5337 mH.post(() -> mAmInternal.scheduleAppGcs());
5338 }
5339
Wale Ogunwale53783742018-09-16 10:21:51 -07005340 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) {
5341 return mCompatModePackages.compatibilityInfoForPackageLocked(ai);
5342 }
5343
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005344 /**
5345 * Returns the PackageManager. Used by classes hosted by {@link ActivityTaskManagerService}. The
5346 * PackageManager could be unavailable at construction time and therefore needs to be accessed
5347 * on demand.
5348 */
5349 IPackageManager getPackageManager() {
5350 return AppGlobals.getPackageManager();
5351 }
5352
5353 PackageManagerInternal getPackageManagerInternalLocked() {
5354 if (mPmInternal == null) {
5355 mPmInternal = LocalServices.getService(PackageManagerInternal.class);
5356 }
5357 return mPmInternal;
5358 }
5359
Wale Ogunwale008163e2018-07-23 23:11:08 -07005360 AppWarnings getAppWarningsLocked() {
5361 return mAppWarnings;
5362 }
5363
Wale Ogunwale214f3482018-10-04 11:00:47 -07005364 Intent getHomeIntent() {
5365 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
5366 intent.setComponent(mTopComponent);
5367 intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING);
5368 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
5369 intent.addCategory(Intent.CATEGORY_HOME);
5370 }
5371 return intent;
5372 }
5373
Wale Ogunwale214f3482018-10-04 11:00:47 -07005374 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) {
5375 if (info == null) return null;
5376 ApplicationInfo newInfo = new ApplicationInfo(info);
5377 newInfo.initForUser(userId);
5378 return newInfo;
5379 }
5380
Wale Ogunwale9c103022018-10-18 07:44:54 -07005381 WindowProcessController getProcessController(String processName, int uid) {
Wale Ogunwale214f3482018-10-04 11:00:47 -07005382 if (uid == SYSTEM_UID) {
5383 // The system gets to run in any process. If there are multiple processes with the same
5384 // uid, just pick the first (this should never happen).
5385 final SparseArray<WindowProcessController> procs =
5386 mProcessNames.getMap().get(processName);
5387 if (procs == null) return null;
5388 final int procCount = procs.size();
5389 for (int i = 0; i < procCount; i++) {
5390 final int procUid = procs.keyAt(i);
5391 if (UserHandle.isApp(procUid) || !UserHandle.isSameUser(procUid, uid)) {
5392 // Don't use an app process or different user process for system component.
5393 continue;
5394 }
5395 return procs.valueAt(i);
5396 }
5397 }
5398
5399 return mProcessNames.get(processName, uid);
5400 }
5401
Wale Ogunwale342fbe92018-10-09 08:44:10 -07005402 WindowProcessController getProcessController(IApplicationThread thread) {
5403 if (thread == null) {
5404 return null;
5405 }
5406
5407 final IBinder threadBinder = thread.asBinder();
5408 final ArrayMap<String, SparseArray<WindowProcessController>> pmap = mProcessNames.getMap();
5409 for (int i = pmap.size()-1; i >= 0; i--) {
5410 final SparseArray<WindowProcessController> procs = pmap.valueAt(i);
5411 for (int j = procs.size() - 1; j >= 0; j--) {
5412 final WindowProcessController proc = procs.valueAt(j);
5413 if (proc.hasThread() && proc.getThread().asBinder() == threadBinder) {
5414 return proc;
5415 }
5416 }
5417 }
5418
5419 return null;
5420 }
5421
Wale Ogunwalebff2df42018-10-18 17:09:19 -07005422 int getUidStateLocked(int uid) {
5423 return mActiveUids.get(uid, PROCESS_STATE_NONEXISTENT);
5424 }
5425
Wale Ogunwale9de19442018-10-18 19:05:03 -07005426 /**
5427 * @return whitelist tag for a uid from mPendingTempWhitelist, null if not currently on
5428 * the whitelist
5429 */
5430 String getPendingTempWhitelistTagForUidLocked(int uid) {
5431 return mPendingTempWhitelist.get(uid);
5432 }
5433
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07005434 void logAppTooSlow(WindowProcessController app, long startTime, String msg) {
5435 if (true || Build.IS_USER) {
5436 return;
5437 }
5438
5439 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads();
5440 StrictMode.allowThreadDiskWrites();
5441 try {
5442 File tracesDir = new File("/data/anr");
5443 File tracesFile = null;
5444 try {
5445 tracesFile = File.createTempFile("app_slow", null, tracesDir);
5446
5447 StringBuilder sb = new StringBuilder();
5448 Time tobj = new Time();
5449 tobj.set(System.currentTimeMillis());
5450 sb.append(tobj.format("%Y-%m-%d %H:%M:%S"));
5451 sb.append(": ");
5452 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb);
5453 sb.append(" since ");
5454 sb.append(msg);
5455 FileOutputStream fos = new FileOutputStream(tracesFile);
5456 fos.write(sb.toString().getBytes());
5457 if (app == null) {
5458 fos.write("\n*** No application process!".getBytes());
5459 }
5460 fos.close();
5461 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw-
5462 } catch (IOException e) {
5463 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesFile, e);
5464 return;
5465 }
5466
5467 if (app != null && app.getPid() > 0) {
5468 ArrayList<Integer> firstPids = new ArrayList<Integer>();
5469 firstPids.add(app.getPid());
5470 dumpStackTraces(tracesFile.getAbsolutePath(), firstPids, null, null);
5471 }
5472
5473 File lastTracesFile = null;
5474 File curTracesFile = null;
5475 for (int i=9; i>=0; i--) {
5476 String name = String.format(Locale.US, "slow%02d.txt", i);
5477 curTracesFile = new File(tracesDir, name);
5478 if (curTracesFile.exists()) {
5479 if (lastTracesFile != null) {
5480 curTracesFile.renameTo(lastTracesFile);
5481 } else {
5482 curTracesFile.delete();
5483 }
5484 }
5485 lastTracesFile = curTracesFile;
5486 }
5487 tracesFile.renameTo(curTracesFile);
5488 } finally {
5489 StrictMode.setThreadPolicy(oldPolicy);
5490 }
5491 }
5492
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005493 final class H extends Handler {
Wale Ogunwalef6733932018-06-27 05:14:34 -07005494 static final int REPORT_TIME_TRACKER_MSG = 1;
Wale Ogunwale98875612018-10-12 07:53:02 -07005495 static final int FIRST_ACTIVITY_STACK_MSG = 100;
5496 static final int FIRST_SUPERVISOR_STACK_MSG = 200;
Wale Ogunwalef6733932018-06-27 05:14:34 -07005497
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -08005498 public H() {
5499 super(DisplayThread.get().getLooper());
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005500 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07005501
5502 @Override
5503 public void handleMessage(Message msg) {
5504 switch (msg.what) {
5505 case REPORT_TIME_TRACKER_MSG: {
5506 AppTimeTracker tracker = (AppTimeTracker) msg.obj;
5507 tracker.deliverResult(mContext);
5508 } break;
5509 }
5510 }
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005511 }
5512
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005513 final class UiHandler extends Handler {
Wale Ogunwalef6733932018-06-27 05:14:34 -07005514 static final int DISMISS_DIALOG_UI_MSG = 1;
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005515
5516 public UiHandler() {
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -08005517 super(UiThread.get().getLooper(), null, true);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005518 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07005519
5520 @Override
5521 public void handleMessage(Message msg) {
5522 switch (msg.what) {
5523 case DISMISS_DIALOG_UI_MSG: {
5524 final Dialog d = (Dialog) msg.obj;
5525 d.dismiss();
5526 break;
5527 }
5528 }
5529 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005530 }
5531
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005532 final class LocalService extends ActivityTaskManagerInternal {
5533 @Override
5534 public SleepToken acquireSleepToken(String tag, int displayId) {
5535 Preconditions.checkNotNull(tag);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005536 return ActivityTaskManagerService.this.acquireSleepToken(tag, displayId);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005537 }
5538
5539 @Override
5540 public ComponentName getHomeActivityForUser(int userId) {
5541 synchronized (mGlobalLock) {
Louis Changbd48dca2018-08-29 17:44:34 +08005542 ActivityRecord homeActivity =
5543 mStackSupervisor.getDefaultDisplayHomeActivityForUser(userId);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005544 return homeActivity == null ? null : homeActivity.realActivity;
5545 }
5546 }
5547
5548 @Override
5549 public void onLocalVoiceInteractionStarted(IBinder activity,
5550 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
5551 synchronized (mGlobalLock) {
Wale Ogunwalef6733932018-06-27 05:14:34 -07005552 onLocalVoiceInteractionStartedLocked(activity, voiceSession, voiceInteractor);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005553 }
5554 }
5555
5556 @Override
5557 public void notifyAppTransitionStarting(SparseIntArray reasons, long timestamp) {
5558 synchronized (mGlobalLock) {
5559 mStackSupervisor.getActivityMetricsLogger().notifyTransitionStarting(
5560 reasons, timestamp);
5561 }
5562 }
5563
5564 @Override
5565 public void notifyAppTransitionFinished() {
5566 synchronized (mGlobalLock) {
5567 mStackSupervisor.notifyAppTransitionDone();
5568 }
5569 }
5570
5571 @Override
5572 public void notifyAppTransitionCancelled() {
5573 synchronized (mGlobalLock) {
5574 mStackSupervisor.notifyAppTransitionDone();
5575 }
5576 }
5577
5578 @Override
5579 public List<IBinder> getTopVisibleActivities() {
5580 synchronized (mGlobalLock) {
5581 return mStackSupervisor.getTopVisibleActivities();
5582 }
5583 }
5584
5585 @Override
5586 public void notifyDockedStackMinimizedChanged(boolean minimized) {
5587 synchronized (mGlobalLock) {
5588 mStackSupervisor.setDockedStackMinimized(minimized);
5589 }
5590 }
5591
5592 @Override
5593 public int startActivitiesAsPackage(String packageName, int userId, Intent[] intents,
5594 Bundle bOptions) {
5595 Preconditions.checkNotNull(intents, "intents");
5596 final String[] resolvedTypes = new String[intents.length];
5597
5598 // UID of the package on user userId.
5599 // "= 0" is needed because otherwise catch(RemoteException) would make it look like
5600 // packageUid may not be initialized.
5601 int packageUid = 0;
5602 final long ident = Binder.clearCallingIdentity();
5603
5604 try {
5605 for (int i = 0; i < intents.length; i++) {
5606 resolvedTypes[i] =
5607 intents[i].resolveTypeIfNeeded(mContext.getContentResolver());
5608 }
5609
5610 packageUid = AppGlobals.getPackageManager().getPackageUid(
5611 packageName, PackageManager.MATCH_DEBUG_TRIAGED_MISSING, userId);
5612 } catch (RemoteException e) {
5613 // Shouldn't happen.
5614 } finally {
5615 Binder.restoreCallingIdentity(ident);
5616 }
5617
5618 synchronized (mGlobalLock) {
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07005619 return getActivityStartController().startActivitiesInPackage(
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005620 packageUid, packageName,
5621 intents, resolvedTypes, null /* resultTo */,
5622 SafeActivityOptions.fromBundle(bOptions), userId,
Michal Karpinski201bc0c2018-07-20 15:32:00 +01005623 false /* validateIncomingUser */, null /* originatingPendingIntent */);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005624 }
5625 }
5626
5627 @Override
Wale Ogunwaleee6eca12018-09-19 20:37:53 -07005628 public int startActivitiesInPackage(int uid, String callingPackage, Intent[] intents,
5629 String[] resolvedTypes, IBinder resultTo, SafeActivityOptions options, int userId,
5630 boolean validateIncomingUser, PendingIntentRecord originatingPendingIntent) {
5631 synchronized (mGlobalLock) {
5632 return getActivityStartController().startActivitiesInPackage(uid, callingPackage,
5633 intents, resolvedTypes, resultTo, options, userId, validateIncomingUser,
5634 originatingPendingIntent);
5635 }
5636 }
5637
5638 @Override
5639 public int startActivityInPackage(int uid, int realCallingPid, int realCallingUid,
5640 String callingPackage, Intent intent, String resolvedType, IBinder resultTo,
5641 String resultWho, int requestCode, int startFlags, SafeActivityOptions options,
5642 int userId, TaskRecord inTask, String reason, boolean validateIncomingUser,
5643 PendingIntentRecord originatingPendingIntent) {
5644 synchronized (mGlobalLock) {
5645 return getActivityStartController().startActivityInPackage(uid, realCallingPid,
5646 realCallingUid, callingPackage, intent, resolvedType, resultTo, resultWho,
5647 requestCode, startFlags, options, userId, inTask, reason,
5648 validateIncomingUser, originatingPendingIntent);
5649 }
5650 }
5651
5652 @Override
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005653 public int startActivityAsUser(IApplicationThread caller, String callerPacakge,
5654 Intent intent, Bundle options, int userId) {
5655 return ActivityTaskManagerService.this.startActivityAsUser(
5656 caller, callerPacakge, intent,
5657 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
5658 null, null, 0, Intent.FLAG_ACTIVITY_NEW_TASK, null, options, userId,
5659 false /*validateIncomingUser*/);
5660 }
5661
5662 @Override
lumark588a3e82018-07-20 18:53:54 +08005663 public void notifyKeyguardFlagsChanged(@Nullable Runnable callback, int displayId) {
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005664 synchronized (mGlobalLock) {
5665
5666 // We might change the visibilities here, so prepare an empty app transition which
5667 // might be overridden later if we actually change visibilities.
lumark588a3e82018-07-20 18:53:54 +08005668 final DisplayWindowController dwc = mStackSupervisor.getActivityDisplay(displayId)
5669 .getWindowContainerController();
5670 final boolean wasTransitionSet = dwc.getPendingAppTransition() != TRANSIT_NONE;
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005671 if (!wasTransitionSet) {
lumark588a3e82018-07-20 18:53:54 +08005672 dwc.prepareAppTransition(TRANSIT_NONE, false /* alwaysKeepCurrent */);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005673 }
5674 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
5675
5676 // If there was a transition set already we don't want to interfere with it as we
5677 // might be starting it too early.
5678 if (!wasTransitionSet) {
lumark588a3e82018-07-20 18:53:54 +08005679 dwc.executeAppTransition();
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005680 }
5681 }
5682 if (callback != null) {
5683 callback.run();
5684 }
5685 }
5686
5687 @Override
5688 public void notifyKeyguardTrustedChanged() {
5689 synchronized (mGlobalLock) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005690 if (mKeyguardController.isKeyguardShowing(DEFAULT_DISPLAY)) {
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005691 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
5692 }
5693 }
5694 }
5695
5696 /**
5697 * Called after virtual display Id is updated by
5698 * {@link com.android.server.vr.Vr2dDisplay} with a specific
5699 * {@param vrVr2dDisplayId}.
5700 */
5701 @Override
5702 public void setVr2dDisplayId(int vr2dDisplayId) {
5703 if (DEBUG_STACK) Slog.d(TAG, "setVr2dDisplayId called for: " + vr2dDisplayId);
5704 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005705 mVr2dDisplayId = vr2dDisplayId;
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005706 }
5707 }
5708
5709 @Override
5710 public void setFocusedActivity(IBinder token) {
5711 synchronized (mGlobalLock) {
5712 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
5713 if (r == null) {
5714 throw new IllegalArgumentException(
5715 "setFocusedActivity: No activity record matching token=" + token);
5716 }
Louis Chang19443452018-10-09 12:10:21 +08005717 if (r.moveFocusableActivityToTop("setFocusedActivity")) {
Andrii Kulianab132ee2018-07-24 22:10:21 +08005718 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005719 }
5720 }
5721 }
5722
5723 @Override
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005724 public void registerScreenObserver(ScreenObserver observer) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005725 mScreenObservers.add(observer);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005726 }
5727
5728 @Override
5729 public boolean isCallerRecents(int callingUid) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07005730 return getRecentTasks().isCallerRecents(callingUid);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005731 }
5732
5733 @Override
5734 public boolean isRecentsComponentHomeActivity(int userId) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07005735 return getRecentTasks().isRecentsComponentHomeActivity(userId);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005736 }
5737
5738 @Override
5739 public void cancelRecentsAnimation(boolean restoreHomeStackPosition) {
5740 ActivityTaskManagerService.this.cancelRecentsAnimation(restoreHomeStackPosition);
5741 }
5742
5743 @Override
5744 public void enforceCallerIsRecentsOrHasPermission(String permission, String func) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005745 ActivityTaskManagerService.this.enforceCallerIsRecentsOrHasPermission(permission, func);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005746 }
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005747
5748 @Override
5749 public void notifyActiveVoiceInteractionServiceChanged(ComponentName component) {
5750 synchronized (mGlobalLock) {
5751 mActiveVoiceInteractionServiceComponent = component;
5752 }
5753 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005754
5755 @Override
5756 public void setAllowAppSwitches(@NonNull String type, int uid, int userId) {
5757 if (!mAmInternal.isUserRunning(userId, ActivityManager.FLAG_OR_STOPPED)) {
5758 return;
5759 }
5760 synchronized (mGlobalLock) {
5761 ArrayMap<String, Integer> types = mAllowAppSwitchUids.get(userId);
5762 if (types == null) {
5763 if (uid < 0) {
5764 return;
5765 }
5766 types = new ArrayMap<>();
5767 mAllowAppSwitchUids.put(userId, types);
5768 }
5769 if (uid < 0) {
5770 types.remove(type);
5771 } else {
5772 types.put(type, uid);
5773 }
5774 }
5775 }
5776
5777 @Override
5778 public void onUserStopped(int userId) {
5779 synchronized (mGlobalLock) {
5780 getRecentTasks().unloadUserDataFromMemoryLocked(userId);
5781 mAllowAppSwitchUids.remove(userId);
5782 }
5783 }
5784
5785 @Override
5786 public boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) {
5787 synchronized (mGlobalLock) {
5788 return ActivityTaskManagerService.this.isGetTasksAllowed(
5789 caller, callingPid, callingUid);
5790 }
5791 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07005792
5793 @Override
5794 public void onProcessAdded(WindowProcessController proc) {
5795 synchronized (mGlobalLock) {
5796 mProcessNames.put(proc.mName, proc.mUid, proc);
5797 }
5798 }
5799
5800 @Override
5801 public void onProcessRemoved(String name, int uid) {
5802 synchronized (mGlobalLock) {
5803 mProcessNames.remove(name, uid);
5804 }
5805 }
5806
5807 @Override
5808 public void onCleanUpApplicationRecord(WindowProcessController proc) {
5809 synchronized (mGlobalLock) {
5810 if (proc == mHomeProcess) {
5811 mHomeProcess = null;
5812 }
5813 if (proc == mPreviousProcess) {
5814 mPreviousProcess = null;
5815 }
5816 }
5817 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07005818
5819 @Override
5820 public int getTopProcessState() {
5821 synchronized (mGlobalLock) {
5822 return mTopProcessState;
5823 }
5824 }
5825
5826 @Override
Wale Ogunwale53783742018-09-16 10:21:51 -07005827 public boolean isHeavyWeightProcess(WindowProcessController proc) {
5828 synchronized (mGlobalLock) {
5829 return proc == mHeavyWeightProcess;
5830 }
5831 }
5832
5833 @Override
5834 public void clearHeavyWeightProcessIfEquals(WindowProcessController proc) {
5835 synchronized (mGlobalLock) {
5836 ActivityTaskManagerService.this.clearHeavyWeightProcessIfEquals(proc);
5837 }
5838 }
5839
5840 @Override
5841 public void finishHeavyWeightApp() {
5842 synchronized (mGlobalLock) {
Sudheer Shankaee1da272018-10-20 20:11:44 -07005843 if (mHeavyWeightProcess != null) {
5844 mHeavyWeightProcess.finishActivities();
5845 }
Wale Ogunwale53783742018-09-16 10:21:51 -07005846 ActivityTaskManagerService.this.clearHeavyWeightProcessIfEquals(
5847 mHeavyWeightProcess);
5848 }
5849 }
5850
5851 @Override
Wale Ogunwalef6733932018-06-27 05:14:34 -07005852 public boolean isSleeping() {
5853 synchronized (mGlobalLock) {
5854 return isSleepingLocked();
5855 }
5856 }
5857
5858 @Override
5859 public boolean isShuttingDown() {
5860 synchronized (mGlobalLock) {
5861 return mShuttingDown;
5862 }
5863 }
5864
5865 @Override
5866 public boolean shuttingDown(boolean booted, int timeout) {
5867 synchronized (mGlobalLock) {
5868 mShuttingDown = true;
5869 mStackSupervisor.prepareForShutdownLocked();
5870 updateEventDispatchingLocked(booted);
Wale Ogunwaled4d67d02018-10-25 18:09:39 -07005871 notifyTaskPersisterLocked(null, true);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005872 return mStackSupervisor.shutdownLocked(timeout);
5873 }
5874 }
5875
5876 @Override
5877 public void enableScreenAfterBoot(boolean booted) {
5878 synchronized (mGlobalLock) {
5879 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN,
5880 SystemClock.uptimeMillis());
5881 mWindowManager.enableScreenAfterBoot();
5882 updateEventDispatchingLocked(booted);
5883 }
5884 }
5885
5886 @Override
5887 public boolean showStrictModeViolationDialog() {
5888 synchronized (mGlobalLock) {
5889 return mShowDialogs && !mSleeping && !mShuttingDown;
5890 }
5891 }
5892
5893 @Override
5894 public void showSystemReadyErrorDialogsIfNeeded() {
5895 synchronized (mGlobalLock) {
5896 try {
5897 if (AppGlobals.getPackageManager().hasSystemUidErrors()) {
5898 Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your"
5899 + " data partition or your device will be unstable.");
5900 mUiHandler.post(() -> {
5901 if (mShowDialogs) {
5902 AlertDialog d = new BaseErrorDialog(mUiContext);
5903 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
5904 d.setCancelable(false);
5905 d.setTitle(mUiContext.getText(R.string.android_system_label));
5906 d.setMessage(mUiContext.getText(R.string.system_error_wipe_data));
5907 d.setButton(DialogInterface.BUTTON_POSITIVE,
5908 mUiContext.getText(R.string.ok),
5909 mUiHandler.obtainMessage(DISMISS_DIALOG_UI_MSG, d));
5910 d.show();
5911 }
5912 });
5913 }
5914 } catch (RemoteException e) {
5915 }
5916
5917 if (!Build.isBuildConsistent()) {
5918 Slog.e(TAG, "Build fingerprint is not consistent, warning user");
5919 mUiHandler.post(() -> {
5920 if (mShowDialogs) {
5921 AlertDialog d = new BaseErrorDialog(mUiContext);
5922 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
5923 d.setCancelable(false);
5924 d.setTitle(mUiContext.getText(R.string.android_system_label));
5925 d.setMessage(mUiContext.getText(R.string.system_error_manufacturer));
5926 d.setButton(DialogInterface.BUTTON_POSITIVE,
5927 mUiContext.getText(R.string.ok),
5928 mUiHandler.obtainMessage(DISMISS_DIALOG_UI_MSG, d));
5929 d.show();
5930 }
5931 });
5932 }
5933 }
5934 }
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005935
5936 @Override
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005937 public void onProcessMapped(int pid, WindowProcessController proc) {
5938 synchronized (mGlobalLock) {
5939 mPidMap.put(pid, proc);
5940 }
5941 }
5942
5943 @Override
5944 public void onProcessUnMapped(int pid) {
5945 synchronized (mGlobalLock) {
5946 mPidMap.remove(pid);
5947 }
5948 }
Wale Ogunwale008163e2018-07-23 23:11:08 -07005949
5950 @Override
5951 public void onPackageDataCleared(String name) {
5952 synchronized (mGlobalLock) {
Wale Ogunwale53783742018-09-16 10:21:51 -07005953 mCompatModePackages.handlePackageDataClearedLocked(name);
Wale Ogunwale008163e2018-07-23 23:11:08 -07005954 mAppWarnings.onPackageDataCleared(name);
5955 }
5956 }
5957
5958 @Override
5959 public void onPackageUninstalled(String name) {
5960 synchronized (mGlobalLock) {
5961 mAppWarnings.onPackageUninstalled(name);
Wale Ogunwale53783742018-09-16 10:21:51 -07005962 mCompatModePackages.handlePackageUninstalledLocked(name);
Wale Ogunwale008163e2018-07-23 23:11:08 -07005963 }
5964 }
Wale Ogunwale53783742018-09-16 10:21:51 -07005965
5966 @Override
5967 public void onPackageAdded(String name, boolean replacing) {
5968 synchronized (mGlobalLock) {
5969 mCompatModePackages.handlePackageAddedLocked(name, replacing);
5970 }
5971 }
5972
5973 @Override
Wale Ogunwale31913b52018-10-13 08:29:31 -07005974 public void onPackageReplaced(ApplicationInfo aInfo) {
5975 synchronized (mGlobalLock) {
5976 mStackSupervisor.updateActivityApplicationInfoLocked(aInfo);
5977 }
5978 }
5979
5980 @Override
Wale Ogunwale53783742018-09-16 10:21:51 -07005981 public CompatibilityInfo compatibilityInfoForPackage(ApplicationInfo ai) {
5982 synchronized (mGlobalLock) {
5983 return compatibilityInfoForPackageLocked(ai);
5984 }
5985 }
5986
Yunfan Chen75157d72018-07-27 14:47:21 +09005987 /**
5988 * Set the corresponding display information for the process global configuration. To be
5989 * called when we need to show IME on a different display.
5990 *
5991 * @param pid The process id associated with the IME window.
5992 * @param displayId The ID of the display showing the IME.
5993 */
5994 @Override
Yunfan Chen79b96062018-10-17 12:45:23 -07005995 public void onImeWindowSetOnDisplay(final int pid, final int displayId) {
Yunfan Chen75157d72018-07-27 14:47:21 +09005996 if (pid == MY_PID || pid < 0) {
5997 if (DEBUG_CONFIGURATION) {
5998 Slog.w(TAG,
5999 "Trying to update display configuration for system/invalid process.");
6000 }
6001 return;
6002 }
6003 mH.post(() -> {
6004 synchronized (mGlobalLock) {
Yunfan Chen79b96062018-10-17 12:45:23 -07006005 final ActivityDisplay activityDisplay =
6006 mStackSupervisor.getActivityDisplay(displayId);
6007 if (activityDisplay == null) {
6008 // Call might come when display is not yet added or has been removed.
Yunfan Chen75157d72018-07-27 14:47:21 +09006009 if (DEBUG_CONFIGURATION) {
6010 Slog.w(TAG, "Trying to update display configuration for non-existing "
Yunfan Chen79b96062018-10-17 12:45:23 -07006011 + "displayId=" + displayId);
Yunfan Chen75157d72018-07-27 14:47:21 +09006012 }
6013 return;
6014 }
Yunfan Chen79b96062018-10-17 12:45:23 -07006015 final WindowProcessController process = mPidMap.get(pid);
6016 if (process == null) {
Yunfan Chen75157d72018-07-27 14:47:21 +09006017 if (DEBUG_CONFIGURATION) {
Yunfan Chen79b96062018-10-17 12:45:23 -07006018 Slog.w(TAG, "Trying to update display configuration for invalid "
6019 + "process, pid=" + pid);
Yunfan Chen75157d72018-07-27 14:47:21 +09006020 }
6021 return;
6022 }
Yunfan Chen79b96062018-10-17 12:45:23 -07006023 process.registerDisplayConfigurationListenerLocked(activityDisplay);
Yunfan Chen75157d72018-07-27 14:47:21 +09006024 }
6025 });
Yunfan Chen79b96062018-10-17 12:45:23 -07006026
Yunfan Chen75157d72018-07-27 14:47:21 +09006027 }
Wale Ogunwaleee6eca12018-09-19 20:37:53 -07006028
6029 @Override
6030 public void sendActivityResult(int callingUid, IBinder activityToken, String resultWho,
6031 int requestCode, int resultCode, Intent data) {
6032 synchronized (mGlobalLock) {
6033 final ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
6034 if (r != null && r.getStack() != null) {
6035 r.getStack().sendActivityResultLocked(callingUid, r, resultWho, requestCode,
6036 resultCode, data);
6037 }
6038 }
6039 }
6040
6041 @Override
6042 public void clearPendingResultForActivity(IBinder activityToken,
6043 WeakReference<PendingIntentRecord> pir) {
6044 synchronized (mGlobalLock) {
6045 final ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
6046 if (r != null && r.pendingResults != null) {
6047 r.pendingResults.remove(pir);
6048 }
6049 }
6050 }
6051
6052 @Override
6053 public IIntentSender getIntentSender(int type, String packageName,
6054 int callingUid, int userId, IBinder token, String resultWho,
6055 int requestCode, Intent[] intents, String[] resolvedTypes, int flags,
6056 Bundle bOptions) {
6057 synchronized (mGlobalLock) {
6058 return getIntentSenderLocked(type, packageName, callingUid, userId, token,
6059 resultWho, requestCode, intents, resolvedTypes, flags, bOptions);
6060 }
6061 }
Wale Ogunwalec4e63a42018-10-02 13:19:54 -07006062
6063 @Override
6064 public ActivityServiceConnectionsHolder getServiceConnectionsHolder(IBinder token) {
6065 synchronized (mGlobalLock) {
6066 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
6067 if (r == null) {
6068 return null;
6069 }
6070 if (r.mServiceConnectionsHolder == null) {
6071 r.mServiceConnectionsHolder = new ActivityServiceConnectionsHolder(
6072 ActivityTaskManagerService.this, r);
6073 }
6074
6075 return r.mServiceConnectionsHolder;
6076 }
6077 }
Wale Ogunwale214f3482018-10-04 11:00:47 -07006078
6079 @Override
6080 public Intent getHomeIntent() {
6081 synchronized (mGlobalLock) {
6082 return ActivityTaskManagerService.this.getHomeIntent();
6083 }
6084 }
6085
6086 @Override
6087 public boolean startHomeActivity(int userId, String reason) {
6088 synchronized (mGlobalLock) {
Louis Chang89f43fc2018-10-05 10:59:14 +08006089 return mStackSupervisor.startHomeOnDisplay(userId, reason, DEFAULT_DISPLAY);
6090 }
6091 }
6092
6093 @Override
6094 public boolean startHomeOnAllDisplays(int userId, String reason) {
6095 synchronized (mGlobalLock) {
6096 return mStackSupervisor.startHomeOnAllDisplays(userId, reason);
Wale Ogunwale214f3482018-10-04 11:00:47 -07006097 }
6098 }
6099
6100 @Override
6101 public boolean isFactoryTestProcess(WindowProcessController wpc) {
6102 synchronized (mGlobalLock) {
6103 if (mFactoryTest == FACTORY_TEST_OFF) {
6104 return false;
6105 }
6106 if (mFactoryTest == FACTORY_TEST_LOW_LEVEL && mTopComponent != null
6107 && wpc.mName.equals(mTopComponent.getPackageName())) {
6108 return true;
6109 }
6110 return mFactoryTest == FACTORY_TEST_HIGH_LEVEL
6111 && (wpc.mInfo.flags & FLAG_FACTORY_TEST) != 0;
6112 }
6113 }
6114
6115 @Override
6116 public void updateTopComponentForFactoryTest() {
6117 synchronized (mGlobalLock) {
6118 if (mFactoryTest != FACTORY_TEST_LOW_LEVEL) {
6119 return;
6120 }
6121 final ResolveInfo ri = mContext.getPackageManager()
6122 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), STOCK_PM_FLAGS);
6123 final CharSequence errorMsg;
6124 if (ri != null) {
6125 final ActivityInfo ai = ri.activityInfo;
6126 final ApplicationInfo app = ai.applicationInfo;
6127 if ((app.flags & ApplicationInfo.FLAG_SYSTEM) != 0) {
6128 mTopAction = Intent.ACTION_FACTORY_TEST;
6129 mTopData = null;
6130 mTopComponent = new ComponentName(app.packageName, ai.name);
6131 errorMsg = null;
6132 } else {
6133 errorMsg = mContext.getResources().getText(
6134 com.android.internal.R.string.factorytest_not_system);
6135 }
6136 } else {
6137 errorMsg = mContext.getResources().getText(
6138 com.android.internal.R.string.factorytest_no_action);
6139 }
6140 if (errorMsg == null) {
6141 return;
6142 }
6143
6144 mTopAction = null;
6145 mTopData = null;
6146 mTopComponent = null;
6147 mUiHandler.post(() -> {
6148 Dialog d = new FactoryErrorDialog(mUiContext, errorMsg);
6149 d.show();
Wale Ogunwale342fbe92018-10-09 08:44:10 -07006150 mAmInternal.ensureBootCompleted();
Wale Ogunwale214f3482018-10-04 11:00:47 -07006151 });
6152 }
6153 }
Wale Ogunwale31913b52018-10-13 08:29:31 -07006154
6155 @Override
6156 public void handleAppDied(WindowProcessController wpc, boolean restarting,
6157 Runnable finishInstrumentationCallback) {
6158 synchronized (mGlobalLock) {
6159 // Remove this application's activities from active lists.
6160 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(wpc);
6161
6162 wpc.clearRecentTasks();
6163 wpc.clearActivities();
6164
6165 if (wpc.isInstrumenting()) {
6166 finishInstrumentationCallback.run();
6167 }
6168
6169 mWindowManager.deferSurfaceLayout();
6170 try {
6171 if (!restarting && hasVisibleActivities
6172 && !mStackSupervisor.resumeFocusedStacksTopActivitiesLocked()) {
6173 // If there was nothing to resume, and we are not already restarting this
6174 // process, but there is a visible activity that is hosted by the process...
6175 // then make sure all visible activities are running, taking care of
6176 // restarting this process.
6177 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
6178 }
6179 } finally {
6180 mWindowManager.continueSurfaceLayout();
6181 }
6182 }
6183 }
6184
6185 @Override
6186 public void closeSystemDialogs(String reason) {
6187 enforceNotIsolatedCaller("closeSystemDialogs");
6188
6189 final int pid = Binder.getCallingPid();
6190 final int uid = Binder.getCallingUid();
6191 final long origId = Binder.clearCallingIdentity();
6192 try {
6193 synchronized (mGlobalLock) {
6194 // Only allow this from foreground processes, so that background
6195 // applications can't abuse it to prevent system UI from being shown.
6196 if (uid >= FIRST_APPLICATION_UID) {
6197 final WindowProcessController proc = mPidMap.get(pid);
6198 if (!proc.isPerceptible()) {
6199 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason
6200 + " from background process " + proc);
6201 return;
6202 }
6203 }
Wale Ogunwale31913b52018-10-13 08:29:31 -07006204 mWindowManager.closeSystemDialogs(reason);
6205
6206 mStackSupervisor.closeSystemDialogsLocked();
Wale Ogunwale31913b52018-10-13 08:29:31 -07006207 }
Wale Ogunwale2ea36d42018-10-18 10:27:31 -07006208 // Call into AM outside the synchronized block.
6209 mAmInternal.broadcastCloseSystemDialogs(reason);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006210 } finally {
6211 Binder.restoreCallingIdentity(origId);
6212 }
6213 }
6214
6215 @Override
6216 public void cleanupDisabledPackageComponents(
6217 String packageName, Set<String> disabledClasses, int userId, boolean booted) {
6218 synchronized (mGlobalLock) {
6219 // Clean-up disabled activities.
6220 if (mStackSupervisor.finishDisabledPackageActivitiesLocked(
6221 packageName, disabledClasses, true, false, userId) && booted) {
6222 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
6223 mStackSupervisor.scheduleIdleLocked();
6224 }
6225
6226 // Clean-up disabled tasks
6227 getRecentTasks().cleanupDisabledPackageTasksLocked(
6228 packageName, disabledClasses, userId);
6229 }
6230 }
6231
6232 @Override
6233 public boolean onForceStopPackage(String packageName, boolean doit, boolean evenPersistent,
6234 int userId) {
6235 synchronized (mGlobalLock) {
6236
6237 boolean didSomething =
6238 getActivityStartController().clearPendingActivityLaunches(packageName);
6239 didSomething |= mStackSupervisor.finishDisabledPackageActivitiesLocked(packageName,
6240 null, doit, evenPersistent, userId);
6241 return didSomething;
6242 }
6243 }
6244
6245 @Override
6246 public void resumeTopActivities(boolean scheduleIdle) {
6247 synchronized (mGlobalLock) {
6248 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
6249 if (scheduleIdle) {
6250 mStackSupervisor.scheduleIdleLocked();
6251 }
6252 }
6253 }
6254
6255 @Override
6256 public void preBindApplication(WindowProcessController wpc) {
6257 synchronized (mGlobalLock) {
6258 mStackSupervisor.getActivityMetricsLogger().notifyBindApplication(wpc.mInfo);
6259 }
6260 }
6261
6262 @Override
6263 public boolean attachApplication(WindowProcessController wpc) throws RemoteException {
6264 synchronized (mGlobalLock) {
6265 return mStackSupervisor.attachApplicationLocked(wpc);
6266 }
6267 }
6268
6269 @Override
6270 public void notifyLockedProfile(@UserIdInt int userId, int currentUserId) {
6271 try {
6272 if (!AppGlobals.getPackageManager().isUidPrivileged(Binder.getCallingUid())) {
6273 throw new SecurityException("Only privileged app can call notifyLockedProfile");
6274 }
6275 } catch (RemoteException ex) {
6276 throw new SecurityException("Fail to check is caller a privileged app", ex);
6277 }
6278
6279 synchronized (mGlobalLock) {
6280 final long ident = Binder.clearCallingIdentity();
6281 try {
6282 if (mAmInternal.shouldConfirmCredentials(userId)) {
6283 if (mKeyguardController.isKeyguardLocked()) {
6284 // Showing launcher to avoid user entering credential twice.
6285 startHomeActivity(currentUserId, "notifyLockedProfile");
6286 }
6287 mStackSupervisor.lockAllProfileTasks(userId);
6288 }
6289 } finally {
6290 Binder.restoreCallingIdentity(ident);
6291 }
6292 }
6293 }
6294
6295 @Override
6296 public void startConfirmDeviceCredentialIntent(Intent intent, Bundle options) {
6297 mAmInternal.enforceCallingPermission(
6298 MANAGE_ACTIVITY_STACKS, "startConfirmDeviceCredentialIntent");
6299
6300 synchronized (mGlobalLock) {
6301 final long ident = Binder.clearCallingIdentity();
6302 try {
6303 intent.addFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS |
6304 FLAG_ACTIVITY_TASK_ON_HOME);
6305 ActivityOptions activityOptions = options != null
6306 ? new ActivityOptions(options) : ActivityOptions.makeBasic();
6307 activityOptions.setLaunchTaskId(
6308 mStackSupervisor.getDefaultDisplayHomeActivity().getTask().taskId);
6309 mContext.startActivityAsUser(intent, activityOptions.toBundle(),
6310 UserHandle.CURRENT);
6311 } finally {
6312 Binder.restoreCallingIdentity(ident);
6313 }
6314 }
6315 }
6316
6317 @Override
6318 public void writeActivitiesToProto(ProtoOutputStream proto) {
6319 synchronized (mGlobalLock) {
6320 // The output proto of "activity --proto activities"
6321 // is ActivityManagerServiceDumpActivitiesProto
6322 mStackSupervisor.writeToProto(proto,
6323 ActivityManagerServiceDumpActivitiesProto.ACTIVITY_STACK_SUPERVISOR);
6324 }
6325 }
6326
6327 @Override
6328 public void saveANRState(String reason) {
6329 synchronized (mGlobalLock) {
6330 final StringWriter sw = new StringWriter();
6331 final PrintWriter pw = new FastPrintWriter(sw, false, 1024);
6332 pw.println(" ANR time: " + DateFormat.getDateTimeInstance().format(new Date()));
6333 if (reason != null) {
6334 pw.println(" Reason: " + reason);
6335 }
6336 pw.println();
6337 getActivityStartController().dump(pw, " ", null);
6338 pw.println();
6339 pw.println("-------------------------------------------------------------------------------");
6340 dumpActivitiesLocked(null /* fd */, pw, null /* args */, 0 /* opti */,
6341 true /* dumpAll */, false /* dumpClient */, null /* dumpPackage */,
6342 "" /* header */);
6343 pw.println();
6344 pw.close();
6345
6346 mLastANRState = sw.toString();
6347 }
6348 }
6349
6350 @Override
6351 public void clearSavedANRState() {
6352 synchronized (mGlobalLock) {
6353 mLastANRState = null;
6354 }
6355 }
6356
6357 @Override
6358 public void dump(String cmd, FileDescriptor fd, PrintWriter pw, String[] args, int opti,
6359 boolean dumpAll, boolean dumpClient, String dumpPackage) {
6360 synchronized (mGlobalLock) {
6361 if (DUMP_ACTIVITIES_CMD.equals(cmd) || DUMP_ACTIVITIES_SHORT_CMD.equals(cmd)) {
6362 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage);
6363 } else if (DUMP_LASTANR_CMD.equals(cmd)) {
6364 dumpLastANRLocked(pw);
6365 } else if (DUMP_LASTANR_TRACES_CMD.equals(cmd)) {
6366 dumpLastANRTracesLocked(pw);
6367 } else if (DUMP_STARTER_CMD.equals(cmd)) {
6368 dumpActivityStarterLocked(pw, dumpPackage);
6369 } else if (DUMP_CONTAINERS_CMD.equals(cmd)) {
6370 dumpActivityContainersLocked(pw);
6371 } else if (DUMP_RECENTS_CMD.equals(cmd) || DUMP_RECENTS_SHORT_CMD.equals(cmd)) {
6372 if (getRecentTasks() != null) {
6373 getRecentTasks().dump(pw, dumpAll, dumpPackage);
6374 }
6375 }
6376 }
6377 }
6378
6379 @Override
6380 public boolean dumpForProcesses(FileDescriptor fd, PrintWriter pw, boolean dumpAll,
6381 String dumpPackage, int dumpAppId, boolean needSep, boolean testPssMode,
6382 int wakefulness) {
6383 synchronized (mGlobalLock) {
6384 if (mHomeProcess != null && (dumpPackage == null
6385 || mHomeProcess.mPkgList.contains(dumpPackage))) {
6386 if (needSep) {
6387 pw.println();
6388 needSep = false;
6389 }
6390 pw.println(" mHomeProcess: " + mHomeProcess);
6391 }
6392 if (mPreviousProcess != null && (dumpPackage == null
6393 || mPreviousProcess.mPkgList.contains(dumpPackage))) {
6394 if (needSep) {
6395 pw.println();
6396 needSep = false;
6397 }
6398 pw.println(" mPreviousProcess: " + mPreviousProcess);
6399 }
6400 if (dumpAll && (mPreviousProcess == null || dumpPackage == null
6401 || mPreviousProcess.mPkgList.contains(dumpPackage))) {
6402 StringBuilder sb = new StringBuilder(128);
6403 sb.append(" mPreviousProcessVisibleTime: ");
6404 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb);
6405 pw.println(sb);
6406 }
6407 if (mHeavyWeightProcess != null && (dumpPackage == null
6408 || mHeavyWeightProcess.mPkgList.contains(dumpPackage))) {
6409 if (needSep) {
6410 pw.println();
6411 needSep = false;
6412 }
6413 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess);
6414 }
6415 if (dumpPackage == null) {
6416 pw.println(" mGlobalConfiguration: " + getGlobalConfiguration());
6417 mStackSupervisor.dumpDisplayConfigs(pw, " ");
6418 }
6419 if (dumpAll) {
6420 if (dumpPackage == null) {
6421 pw.println(" mConfigWillChange: "
6422 + getTopDisplayFocusedStack().mConfigWillChange);
6423 }
6424 if (mCompatModePackages.getPackages().size() > 0) {
6425 boolean printed = false;
6426 for (Map.Entry<String, Integer> entry
6427 : mCompatModePackages.getPackages().entrySet()) {
6428 String pkg = entry.getKey();
6429 int mode = entry.getValue();
6430 if (dumpPackage != null && !dumpPackage.equals(pkg)) {
6431 continue;
6432 }
6433 if (!printed) {
6434 pw.println(" mScreenCompatPackages:");
6435 printed = true;
6436 }
6437 pw.println(" " + pkg + ": " + mode);
6438 }
6439 }
6440 }
6441
6442 if (dumpPackage == null) {
6443 pw.println(" mWakefulness="
6444 + PowerManagerInternal.wakefulnessToString(wakefulness));
6445 pw.println(" mSleepTokens=" + mStackSupervisor.mSleepTokens);
6446 if (mRunningVoice != null) {
6447 pw.println(" mRunningVoice=" + mRunningVoice);
6448 pw.println(" mVoiceWakeLock" + mVoiceWakeLock);
6449 }
6450 pw.println(" mSleeping=" + mSleeping);
6451 pw.println(" mShuttingDown=" + mShuttingDown + " mTestPssMode=" + testPssMode);
6452 pw.println(" mVrController=" + mVrController);
6453 }
6454 if (mCurAppTimeTracker != null) {
6455 mCurAppTimeTracker.dumpWithHeader(pw, " ", true);
6456 }
6457 if (mAllowAppSwitchUids.size() > 0) {
6458 boolean printed = false;
6459 for (int i = 0; i < mAllowAppSwitchUids.size(); i++) {
6460 ArrayMap<String, Integer> types = mAllowAppSwitchUids.valueAt(i);
6461 for (int j = 0; j < types.size(); j++) {
6462 if (dumpPackage == null ||
6463 UserHandle.getAppId(types.valueAt(j).intValue()) == dumpAppId) {
6464 if (needSep) {
6465 pw.println();
6466 needSep = false;
6467 }
6468 if (!printed) {
6469 pw.println(" mAllowAppSwitchUids:");
6470 printed = true;
6471 }
6472 pw.print(" User ");
6473 pw.print(mAllowAppSwitchUids.keyAt(i));
6474 pw.print(": Type ");
6475 pw.print(types.keyAt(j));
6476 pw.print(" = ");
6477 UserHandle.formatUid(pw, types.valueAt(j).intValue());
6478 pw.println();
6479 }
6480 }
6481 }
6482 }
6483 if (dumpPackage == null) {
6484 if (mController != null) {
6485 pw.println(" mController=" + mController
6486 + " mControllerIsAMonkey=" + mControllerIsAMonkey);
6487 }
6488 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep);
6489 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity);
6490 }
6491
6492 return needSep;
6493 }
6494 }
6495
6496 @Override
6497 public void writeProcessesToProto(ProtoOutputStream proto, String dumpPackage) {
6498 synchronized (mGlobalLock) {
6499 if (dumpPackage == null) {
6500 getGlobalConfiguration().writeToProto(proto, GLOBAL_CONFIGURATION);
6501 proto.write(CONFIG_WILL_CHANGE, getTopDisplayFocusedStack().mConfigWillChange);
6502 writeSleepStateToProto(proto);
6503 if (mController != null) {
6504 final long token = proto.start(CONTROLLER);
6505 proto.write(CONTROLLER, mController.toString());
6506 proto.write(IS_A_MONKEY, mControllerIsAMonkey);
6507 proto.end(token);
6508 }
6509 mStackSupervisor.mGoingToSleep.writeToProto(proto, GOING_TO_SLEEP);
6510 mStackSupervisor.mLaunchingActivity.writeToProto(proto, LAUNCHING_ACTIVITY);
6511 }
6512
6513 if (mHomeProcess != null && (dumpPackage == null
6514 || mHomeProcess.mPkgList.contains(dumpPackage))) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07006515 mHomeProcess.writeToProto(proto, HOME_PROC);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006516 }
6517
6518 if (mPreviousProcess != null && (dumpPackage == null
6519 || mPreviousProcess.mPkgList.contains(dumpPackage))) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07006520 mPreviousProcess.writeToProto(proto, PREVIOUS_PROC);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006521 proto.write(PREVIOUS_PROC_VISIBLE_TIME_MS, mPreviousProcessVisibleTime);
6522 }
6523
6524 if (mHeavyWeightProcess != null && (dumpPackage == null
6525 || mHeavyWeightProcess.mPkgList.contains(dumpPackage))) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07006526 mHeavyWeightProcess.writeToProto(proto, HEAVY_WEIGHT_PROC);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006527 }
6528
6529 for (Map.Entry<String, Integer> entry
6530 : mCompatModePackages.getPackages().entrySet()) {
6531 String pkg = entry.getKey();
6532 int mode = entry.getValue();
6533 if (dumpPackage == null || dumpPackage.equals(pkg)) {
6534 long compatToken = proto.start(SCREEN_COMPAT_PACKAGES);
6535 proto.write(PACKAGE, pkg);
6536 proto.write(MODE, mode);
6537 proto.end(compatToken);
6538 }
6539 }
6540
6541 if (mCurAppTimeTracker != null) {
6542 mCurAppTimeTracker.writeToProto(proto, CURRENT_TRACKER, true);
6543 }
6544
6545 }
6546 }
6547
6548 @Override
6549 public boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name,
6550 String[] args, int opti, boolean dumpAll, boolean dumpVisibleStacksOnly,
6551 boolean dumpFocusedStackOnly) {
6552 synchronized (mGlobalLock) {
6553 return ActivityTaskManagerService.this.dumpActivity(fd, pw, name, args, opti,
6554 dumpAll, dumpVisibleStacksOnly, dumpFocusedStackOnly);
6555 }
6556 }
6557
6558 @Override
Wale Ogunwaled4d67d02018-10-25 18:09:39 -07006559 public void dumpForOom(PrintWriter pw) {
6560 synchronized (mGlobalLock) {
6561 pw.println(" mHomeProcess: " + mHomeProcess);
6562 pw.println(" mPreviousProcess: " + mPreviousProcess);
6563 if (mHeavyWeightProcess != null) {
6564 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess);
6565 }
6566 }
6567 }
6568
6569 @Override
Wale Ogunwale31913b52018-10-13 08:29:31 -07006570 public boolean canGcNow() {
6571 synchronized (mGlobalLock) {
6572 return isSleeping() || mStackSupervisor.allResumedActivitiesIdle();
6573 }
6574 }
6575
6576 @Override
6577 public WindowProcessController getTopApp() {
6578 synchronized (mGlobalLock) {
6579 final ActivityRecord top = mStackSupervisor.getTopResumedActivity();
6580 return top != null ? top.app : null;
6581 }
6582 }
6583
6584 @Override
6585 public void rankTaskLayersIfNeeded() {
6586 synchronized (mGlobalLock) {
6587 if (mStackSupervisor != null) {
6588 mStackSupervisor.rankTaskLayersIfNeeded();
6589 }
6590 }
6591 }
6592
6593 @Override
6594 public void scheduleDestroyAllActivities(String reason) {
6595 synchronized (mGlobalLock) {
6596 mStackSupervisor.scheduleDestroyAllActivities(null, reason);
6597 }
6598 }
6599
6600 @Override
6601 public void removeUser(int userId) {
6602 synchronized (mGlobalLock) {
6603 mStackSupervisor.removeUserLocked(userId);
6604 }
6605 }
6606
6607 @Override
6608 public boolean switchUser(int userId, UserState userState) {
6609 synchronized (mGlobalLock) {
6610 return mStackSupervisor.switchUserLocked(userId, userState);
6611 }
6612 }
6613
6614 @Override
6615 public void onHandleAppCrash(WindowProcessController wpc) {
6616 synchronized (mGlobalLock) {
6617 mStackSupervisor.handleAppCrashLocked(wpc);
6618 }
6619 }
Wale Ogunwale64258362018-10-16 15:13:37 -07006620
6621 @Override
6622 public int finishTopCrashedActivities(WindowProcessController crashedApp, String reason) {
6623 synchronized (mGlobalLock) {
6624 return mStackSupervisor.finishTopCrashedActivitiesLocked(crashedApp, reason);
6625 }
6626 }
Wale Ogunwalebff2df42018-10-18 17:09:19 -07006627
6628 @Override
6629 public void onUidActive(int uid, int procState) {
6630 synchronized (mGlobalLock) {
6631 mActiveUids.put(uid, procState);
6632 }
6633 }
6634
6635 @Override
6636 public void onUidInactive(int uid) {
6637 synchronized (mGlobalLock) {
6638 mActiveUids.remove(uid);
6639 }
6640 }
6641
6642 @Override
6643 public void onActiveUidsCleared() {
6644 synchronized (mGlobalLock) {
6645 mActiveUids.clear();
6646 }
6647 }
6648
6649 @Override
6650 public void onUidProcStateChanged(int uid, int procState) {
6651 synchronized (mGlobalLock) {
6652 if (mActiveUids.get(uid) != null) {
6653 mActiveUids.put(uid, procState);
6654 }
6655 }
6656 }
Wale Ogunwale9de19442018-10-18 19:05:03 -07006657
6658 @Override
6659 public void onUidAddedToPendingTempWhitelist(int uid, String tag) {
6660 synchronized (mGlobalLock) {
6661 mPendingTempWhitelist.put(uid, tag);
6662 }
6663 }
6664
6665 @Override
6666 public void onUidRemovedFromPendingTempWhitelist(int uid) {
6667 synchronized (mGlobalLock) {
6668 mPendingTempWhitelist.remove(uid);
6669 }
6670 }
Wale Ogunwalee2172292018-10-25 10:11:10 -07006671
6672 @Override
6673 public boolean handleAppCrashInActivityController(String processName, int pid,
6674 String shortMsg, String longMsg, long timeMillis, String stackTrace,
6675 Runnable killCrashingAppCallback) {
6676 synchronized (mGlobalLock) {
6677 if (mController == null) {
6678 return false;
6679 }
6680
6681 try {
6682 if (!mController.appCrashed(processName, pid, shortMsg, longMsg, timeMillis,
6683 stackTrace)) {
6684 killCrashingAppCallback.run();
6685 return true;
6686 }
6687 } catch (RemoteException e) {
6688 mController = null;
6689 Watchdog.getInstance().setActivityController(null);
6690 }
6691 return false;
6692 }
6693 }
Wale Ogunwaled7889f52018-10-25 11:03:20 -07006694
6695 @Override
6696 public void removeRecentTasksByPackageName(String packageName, int userId) {
6697 synchronized (mGlobalLock) {
6698 mRecentTasks.removeTasksByPackageName(packageName, userId);
6699 }
6700 }
6701
6702 @Override
6703 public void cleanupRecentTasksForUser(int userId) {
6704 synchronized (mGlobalLock) {
6705 mRecentTasks.cleanupLocked(userId);
6706 }
6707 }
6708
6709 @Override
6710 public void loadRecentTasksForUser(int userId) {
6711 synchronized (mGlobalLock) {
6712 mRecentTasks.loadUserRecentsLocked(userId);
6713 }
6714 }
6715
6716 @Override
6717 public void onPackagesSuspendedChanged(String[] packages, boolean suspended, int userId) {
6718 synchronized (mGlobalLock) {
6719 mRecentTasks.onPackagesSuspendedChanged(packages, suspended, userId);
6720 }
6721 }
6722
6723 @Override
6724 public void flushRecentTasks() {
6725 mRecentTasks.flush();
6726 }
Wale Ogunwaled4d67d02018-10-25 18:09:39 -07006727
6728 @Override
6729 public WindowProcessController getHomeProcess() {
6730 synchronized (mGlobalLock) {
6731 return mHomeProcess;
6732 }
6733 }
6734
6735 @Override
6736 public WindowProcessController getPreviousProcess() {
6737 synchronized (mGlobalLock) {
6738 return mPreviousProcess;
6739 }
6740 }
Wale Ogunwale27c48ae2018-10-25 19:01:01 -07006741
6742 @Override
6743 public void clearLockedTasks(String reason) {
6744 synchronized (mGlobalLock) {
6745 getLockTaskController().clearLockedTasks(reason);
6746 }
6747 }
6748
6749 @Override
6750 public void updateUserConfiguration() {
6751 synchronized (mGlobalLock) {
6752 final Configuration configuration = new Configuration(getGlobalConfiguration());
6753 final int currentUserId = mAmInternal.getCurrentUserId();
6754 Settings.System.adjustConfigurationForUser(mContext.getContentResolver(),
6755 configuration, currentUserId, Settings.System.canWrite(mContext));
6756 updateConfigurationLocked(configuration, null /* starting */,
6757 false /* initLocale */, false /* persistent */, currentUserId,
6758 false /* deferResume */);
6759 }
6760 }
Wale Ogunwale387b34c2018-10-25 19:59:40 -07006761
6762 @Override
6763 public boolean canShowErrorDialogs() {
6764 synchronized (mGlobalLock) {
6765 return mShowDialogs && !mSleeping && !mShuttingDown
6766 && !mKeyguardController.isKeyguardOrAodShowing(DEFAULT_DISPLAY)
6767 && !hasUserRestriction(UserManager.DISALLOW_SYSTEM_ERROR_DIALOGS,
6768 mAmInternal.getCurrentUserId())
6769 && !(UserManager.isDeviceInDemoMode(mContext)
6770 && mAmInternal.getCurrentUser().isDemo());
6771 }
6772 }
Wale Ogunwale1f5e53d2018-11-05 05:12:46 -08006773
6774 @Override
6775 public void setProfileApp(String profileApp) {
6776 synchronized (mGlobalLock) {
6777 mProfileApp = profileApp;
6778 }
6779 }
6780
6781 @Override
6782 public void setProfileProc(WindowProcessController wpc) {
6783 synchronized (mGlobalLock) {
6784 mProfileProc = wpc;
6785 }
6786 }
6787
6788 @Override
6789 public void setProfilerInfo(ProfilerInfo profilerInfo) {
6790 synchronized (mGlobalLock) {
6791 mProfilerInfo = profilerInfo;
6792 }
6793 }
Wale Ogunwale6767eae2018-05-03 15:52:51 -07006794 }
Wale Ogunwale65ebd952018-04-25 15:41:44 -07006795}