blob: cb729a85ef8277aa3e645c16de35f5f001dc4682 [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
17package com.android.server.am;
18
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;
Wale Ogunwale906f9c62018-07-23 11:23:44 -070022import static android.Manifest.permission.FILTER_EVENTS;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070023import static android.Manifest.permission.INTERNAL_SYSTEM_WINDOW;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070024import static android.Manifest.permission.MANAGE_ACTIVITY_STACKS;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070025import static android.Manifest.permission.READ_FRAME_BUFFER;
26import static android.Manifest.permission.REMOVE_TASKS;
27import static android.Manifest.permission.START_TASKS_FROM_RECENTS;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070028import static android.Manifest.permission.STOP_APP_SWITCHES;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070029import static android.app.ActivityManager.LOCK_TASK_MODE_NONE;
Evan Rosky4505b352018-09-06 11:20:40 -070030import static android.app.ActivityManagerInternal.ALLOW_FULL_ONLY;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070031import static android.app.ActivityTaskManager.RESIZE_MODE_PRESERVE_WINDOW;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070032import static android.app.ActivityTaskManager.SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT;
Wale Ogunwalea6191b42018-05-09 07:41:32 -070033import static android.app.AppOpsManager.OP_NONE;
Wale Ogunwale65ebd952018-04-25 15:41:44 -070034import 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 Ogunwaled0412b32018-05-08 09:25:50 -070068import static android.view.WindowManager.TRANSIT_ACTIVITY_OPEN;
Wale Ogunwale6767eae2018-05-03 15:52:51 -070069import static android.view.WindowManager.TRANSIT_NONE;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -070070import static android.view.WindowManager.TRANSIT_TASK_IN_PLACE;
Wale Ogunwaled0412b32018-05-08 09:25:50 -070071import static android.view.WindowManager.TRANSIT_TASK_OPEN;
72import static android.view.WindowManager.TRANSIT_TASK_TO_FRONT;
Evan Rosky4505b352018-09-06 11:20:40 -070073
Wale Ogunwale31913b52018-10-13 08:29:31 -070074import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.CONFIG_WILL_CHANGE;
75import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.CONTROLLER;
76import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.CURRENT_TRACKER;
77import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.Controller.IS_A_MONKEY;
78import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.GLOBAL_CONFIGURATION;
79import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.GOING_TO_SLEEP;
80import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.HEAVY_WEIGHT_PROC;
81import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.HOME_PROC;
82import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.LAUNCHING_ACTIVITY;
83import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.PREVIOUS_PROC;
84import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.PREVIOUS_PROC_VISIBLE_TIME_MS;
85import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.SCREEN_COMPAT_PACKAGES;
86import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.ScreenCompatPackage.MODE;
87import static com.android.server.am.ActivityManagerServiceDumpProcessesProto.ScreenCompatPackage.PACKAGE;
Wale Ogunwale98875612018-10-12 07:53:02 -070088import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_ALL;
Wale Ogunwale31913b52018-10-13 08:29:31 -070089import static com.android.server.am.ActivityManagerService.ANR_TRACE_DIR;
Wale Ogunwale98875612018-10-12 07:53:02 -070090import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_CONFIGURATION;
91import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_FOCUS;
92import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_IMMERSIVE;
93import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_LOCKTASK;
94import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_STACK;
95import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_SWITCH;
96import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_TASKS;
97import static com.android.server.am.ActivityTaskManagerDebugConfig.DEBUG_VISIBILITY;
98import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_CONFIGURATION;
99import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_FOCUS;
100import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_IMMERSIVE;
101import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_LOCKTASK;
102import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_STACK;
103import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_SWITCH;
104import static com.android.server.am.ActivityTaskManagerDebugConfig.POSTFIX_VISIBILITY;
105import static com.android.server.am.ActivityTaskManagerDebugConfig.TAG_ATM;
106import static com.android.server.am.ActivityTaskManagerDebugConfig.TAG_WITH_CLASS_NAME;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700107import static com.android.server.am.ActivityManagerService.MY_PID;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700108import static com.android.server.am.ActivityManagerService.STOCK_PM_FLAGS;
Evan Rosky4505b352018-09-06 11:20:40 -0700109import static com.android.server.am.ActivityManagerService.dumpStackTraces;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700110import static com.android.server.am.ActivityStack.REMOVE_TASK_MODE_DESTROYING;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700111import static com.android.server.am.ActivityStackSupervisor.DEFER_RESUME;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700112import static com.android.server.am.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_ONLY;
113import static com.android.server.am.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_OR_RECENT_TASKS;
114import static com.android.server.am.ActivityStackSupervisor.ON_TOP;
115import static com.android.server.am.ActivityStackSupervisor.PRESERVE_WINDOWS;
116import static com.android.server.am.ActivityStackSupervisor.REMOVE_FROM_RECENTS;
Evan Rosky4505b352018-09-06 11:20:40 -0700117import static com.android.server.am.ActivityTaskManagerService.H.REPORT_TIME_TRACKER_MSG;
118import static com.android.server.am.ActivityTaskManagerService.UiHandler.DISMISS_DIALOG_UI_MSG;
Wale Ogunwale98875612018-10-12 07:53:02 -0700119import static android.app.ActivityTaskManager.INVALID_TASK_ID;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700120import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_DONT_LOCK;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700121import static com.android.server.am.TaskRecord.REPARENT_KEEP_STACK_AT_FRONT;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700122import static com.android.server.am.TaskRecord.REPARENT_LEAVE_STACK_IN_PLACE;
Evan Rosky4505b352018-09-06 11:20:40 -0700123import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_CONTENT;
124import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_DATA;
125import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_RECEIVER_EXTRAS;
126import static com.android.server.wm.ActivityTaskManagerInternal.ASSIST_KEY_STRUCTURE;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700127import static com.android.server.wm.RecentsAnimationController.REORDER_KEEP_IN_PLACE;
128import static com.android.server.wm.RecentsAnimationController.REORDER_MOVE_TO_ORIGINAL_POSITION;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700129
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700130import android.Manifest;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700131import android.annotation.NonNull;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700132import android.annotation.Nullable;
133import android.annotation.UserIdInt;
134import android.app.Activity;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700135import android.app.ActivityManager;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700136import android.app.ActivityManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700137import android.app.ActivityOptions;
138import android.app.ActivityTaskManager;
Wale Ogunwalef6733932018-06-27 05:14:34 -0700139import android.app.ActivityThread;
140import android.app.AlertDialog;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700141import android.app.AppGlobals;
Evan Rosky4505b352018-09-06 11:20:40 -0700142import android.app.Dialog;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700143import android.app.IActivityController;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700144import android.app.IActivityTaskManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700145import android.app.IApplicationThread;
146import android.app.IAssistDataReceiver;
Wale Ogunwale53783742018-09-16 10:21:51 -0700147import android.app.INotificationManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700148import android.app.ITaskStackListener;
Wale Ogunwale53783742018-09-16 10:21:51 -0700149import android.app.Notification;
150import android.app.NotificationManager;
151import android.app.PendingIntent;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700152import android.app.PictureInPictureParams;
153import android.app.ProfilerInfo;
154import android.app.RemoteAction;
155import android.app.WaitResult;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700156import android.app.WindowConfiguration;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700157import android.app.admin.DevicePolicyCache;
158import android.app.assist.AssistContent;
159import android.app.assist.AssistStructure;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700160import android.app.usage.UsageStatsManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700161import android.content.ActivityNotFoundException;
162import android.content.ComponentName;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700163import android.content.ContentResolver;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700164import android.content.Context;
Evan Rosky4505b352018-09-06 11:20:40 -0700165import android.content.DialogInterface;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700166import android.content.IIntentSender;
167import android.content.Intent;
168import android.content.pm.ActivityInfo;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700169import android.content.pm.ApplicationInfo;
Yunfan Chen75157d72018-07-27 14:47:21 +0900170import android.content.pm.ConfigurationInfo;
Evan Rosky4505b352018-09-06 11:20:40 -0700171import android.content.pm.IPackageManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700172import android.content.pm.PackageManager;
Evan Rosky4505b352018-09-06 11:20:40 -0700173import android.content.pm.PackageManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700174import android.content.pm.ParceledListSlice;
175import android.content.pm.ResolveInfo;
Wale Ogunwale53783742018-09-16 10:21:51 -0700176import android.content.res.CompatibilityInfo;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700177import android.content.res.Configuration;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700178import android.content.res.Resources;
Evan Rosky4505b352018-09-06 11:20:40 -0700179import android.database.ContentObserver;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700180import android.graphics.Bitmap;
181import android.graphics.Point;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700182import android.graphics.Rect;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700183import android.metrics.LogMaker;
184import android.net.Uri;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700185import android.os.Binder;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700186import android.os.Build;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700187import android.os.Bundle;
Wale Ogunwale214f3482018-10-04 11:00:47 -0700188import android.os.FactoryTest;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700189import android.os.FileUtils;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700190import android.os.Handler;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700191import android.os.IBinder;
Evan Rosky4505b352018-09-06 11:20:40 -0700192import android.os.IUserManager;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700193import android.os.LocaleList;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700194import android.os.Looper;
195import android.os.Message;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700196import android.os.PersistableBundle;
Evan Rosky4505b352018-09-06 11:20:40 -0700197import android.os.PowerManager;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700198import android.os.PowerManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700199import android.os.RemoteException;
Evan Rosky4505b352018-09-06 11:20:40 -0700200import android.os.ServiceManager;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700201import android.os.StrictMode;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700202import android.os.SystemClock;
203import android.os.SystemProperties;
Evan Rosky4505b352018-09-06 11:20:40 -0700204import android.os.Trace;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700205import android.os.UpdateLock;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700206import android.os.UserHandle;
Evan Rosky4505b352018-09-06 11:20:40 -0700207import android.os.UserManager;
208import android.os.WorkSource;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700209import android.os.storage.IStorageManager;
210import android.os.storage.StorageManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700211import android.provider.Settings;
212import android.service.voice.IVoiceInteractionSession;
213import android.service.voice.VoiceInteractionManagerInternal;
214import android.telecom.TelecomManager;
215import android.text.TextUtils;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700216import android.text.format.Time;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700217import android.util.ArrayMap;
218import android.util.EventLog;
219import android.util.Log;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700220import android.util.Slog;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700221import android.util.SparseArray;
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700222import android.util.SparseIntArray;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700223import android.util.StatsLog;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700224import android.util.TimeUtils;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700225import android.util.proto.ProtoOutputStream;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700226import android.view.IRecentsAnimationRunner;
227import android.view.RemoteAnimationAdapter;
228import android.view.RemoteAnimationDefinition;
Evan Rosky4505b352018-09-06 11:20:40 -0700229import android.view.WindowManager;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700230
Evan Rosky4505b352018-09-06 11:20:40 -0700231import com.android.internal.R;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700232import com.android.internal.annotations.VisibleForTesting;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700233import com.android.internal.app.AssistUtils;
Evan Rosky4505b352018-09-06 11:20:40 -0700234import com.android.internal.app.IAppOpsService;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700235import com.android.internal.app.IVoiceInteractor;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700236import com.android.internal.app.ProcessMap;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700237import com.android.internal.logging.MetricsLogger;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700238import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
Wale Ogunwale53783742018-09-16 10:21:51 -0700239import com.android.internal.messages.nano.SystemMessageProto.SystemMessage;
240import com.android.internal.notification.SystemNotificationChannels;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700241import com.android.internal.os.TransferPipe;
Evan Rosky4505b352018-09-06 11:20:40 -0700242import com.android.internal.os.logging.MetricsLoggerWrapper;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700243import com.android.internal.policy.IKeyguardDismissCallback;
244import com.android.internal.policy.KeyguardDismissCallback;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700245import com.android.internal.util.ArrayUtils;
246import com.android.internal.util.FastPrintWriter;
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700247import com.android.internal.util.Preconditions;
Wale Ogunwale53783742018-09-16 10:21:51 -0700248import com.android.internal.util.function.pooled.PooledLambda;
Evan Rosky4505b352018-09-06 11:20:40 -0700249import com.android.server.AppOpsService;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700250import com.android.server.AttributeCache;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700251import com.android.server.LocalServices;
252import com.android.server.SystemService;
Evan Rosky4505b352018-09-06 11:20:40 -0700253import com.android.server.SystemServiceManager;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700254import com.android.server.Watchdog;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700255import com.android.server.firewall.IntentFirewall;
Evan Rosky4505b352018-09-06 11:20:40 -0700256import com.android.server.pm.UserManagerService;
257import com.android.server.uri.UriGrantsManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700258import com.android.server.vr.VrManagerInternal;
Evan Rosky4505b352018-09-06 11:20:40 -0700259import com.android.server.wm.ActivityTaskManagerInternal;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700260import com.android.server.wm.PinnedStackWindowController;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700261import com.android.server.wm.WindowManagerService;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700262
Wale Ogunwale31913b52018-10-13 08:29:31 -0700263import java.io.BufferedReader;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700264import java.io.File;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700265import java.io.FileDescriptor;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700266import java.io.FileOutputStream;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700267import java.io.FileReader;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700268import java.io.IOException;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700269import java.io.PrintWriter;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700270import java.io.StringWriter;
Wale Ogunwaleee6eca12018-09-19 20:37:53 -0700271import java.lang.ref.WeakReference;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700272import java.text.DateFormat;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700273import java.util.ArrayList;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700274import java.util.Date;
Wale Ogunwaleee6eca12018-09-19 20:37:53 -0700275import java.util.HashSet;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700276import java.util.List;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700277import java.util.Locale;
Wale Ogunwale31913b52018-10-13 08:29:31 -0700278import java.util.Map;
279import java.util.Set;
280import java.util.function.Predicate;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700281
282/**
283 * System service for managing activities and their containers (task, stacks, displays,... ).
284 *
285 * {@hide}
286 */
287public class ActivityTaskManagerService extends IActivityTaskManager.Stub {
Wale Ogunwale98875612018-10-12 07:53:02 -0700288 private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityTaskManagerService" : TAG_ATM;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700289 private static final String TAG_STACK = TAG + POSTFIX_STACK;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700290 private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH;
291 private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE;
292 private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS;
293 private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY;
294 private static final String TAG_LOCKTASK = TAG + POSTFIX_LOCKTASK;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700295 private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700296
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700297 // How long we wait until we timeout on key dispatching.
Wale Ogunwale51cc98a2018-10-15 10:41:05 -0700298 public static final int KEY_DISPATCHING_TIMEOUT_MS = 5 * 1000;
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700299 // How long we wait until we timeout on key dispatching during instrumentation.
Wale Ogunwale51cc98a2018-10-15 10:41:05 -0700300 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT_MS = 60 * 1000;
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700301
Wale Ogunwale98875612018-10-12 07:53:02 -0700302 /** Used to indicate that an app transition should be animated. */
303 static final boolean ANIMATE = true;
304
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700305 /** Hardware-reported OpenGLES version. */
306 final int GL_ES_VERSION;
307
Wale Ogunwale31913b52018-10-13 08:29:31 -0700308 public static final String DUMP_ACTIVITIES_CMD = "activities" ;
309 public static final String DUMP_ACTIVITIES_SHORT_CMD = "a" ;
310 public static final String DUMP_LASTANR_CMD = "lastanr" ;
311 public static final String DUMP_LASTANR_TRACES_CMD = "lastanr-traces" ;
312 public static final String DUMP_STARTER_CMD = "starter" ;
313 public static final String DUMP_CONTAINERS_CMD = "containers" ;
314 public static final String DUMP_RECENTS_CMD = "recents" ;
315 public static final String DUMP_RECENTS_SHORT_CMD = "r" ;
316
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700317 Context mContext;
Wale Ogunwalef6733932018-06-27 05:14:34 -0700318 /**
319 * This Context is themable and meant for UI display (AlertDialogs, etc.). The theme can
320 * change at runtime. Use mContext for non-UI purposes.
321 */
322 final Context mUiContext;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700323 final ActivityThread mSystemThread;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700324 H mH;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700325 UiHandler mUiHandler;
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700326 ActivityManagerService mAm;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700327 ActivityManagerInternal mAmInternal;
Wale Ogunwale6d50dcc2018-07-21 23:00:40 -0700328 UriGrantsManagerInternal mUgmInternal;
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700329 private PackageManagerInternal mPmInternal;
Wale Ogunwale53783742018-09-16 10:21:51 -0700330 private ActivityTaskManagerInternal mInternal;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700331 PowerManagerInternal mPowerManagerInternal;
332 private UsageStatsManagerInternal mUsageStatsInternal;
333
Wale Ogunwaleee6eca12018-09-19 20:37:53 -0700334 PendingIntentController mPendingIntentController;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700335 IntentFirewall mIntentFirewall;
336
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700337 /* Global service lock used by the package the owns this service. */
338 Object mGlobalLock;
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700339 ActivityStackSupervisor mStackSupervisor;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700340 WindowManagerService mWindowManager;
Wale Ogunwalef6733932018-06-27 05:14:34 -0700341 private UserManagerService mUserManager;
342 private AppOpsService mAppOpsService;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700343 /** All processes currently running that might have a window organized by name. */
344 final ProcessMap<WindowProcessController> mProcessNames = new ProcessMap<>();
Wale Ogunwale906f9c62018-07-23 11:23:44 -0700345 /** All processes we currently have running mapped by pid */
346 final SparseArray<WindowProcessController> mPidMap = new SparseArray<>();
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700347 /** This is the process holding what we currently consider to be the "home" activity. */
348 WindowProcessController mHomeProcess;
Wale Ogunwale53783742018-09-16 10:21:51 -0700349 /** The currently running heavy-weight process, if any. */
350 WindowProcessController mHeavyWeightProcess = null;
Wale Ogunwale214f3482018-10-04 11:00:47 -0700351 boolean mHasHeavyWeightFeature;
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700352 /**
353 * This is the process holding the activity the user last visited that is in a different process
354 * from the one they are currently in.
355 */
356 WindowProcessController mPreviousProcess;
357 /** The time at which the previous process was last visible. */
358 long mPreviousProcessVisibleTime;
359
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700360 /** List of intents that were used to start the most recent tasks. */
361 private RecentTasks mRecentTasks;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700362 /** State of external calls telling us if the device is awake or asleep. */
363 private boolean mKeyguardShown = false;
364
365 // Wrapper around VoiceInteractionServiceManager
366 private AssistUtils mAssistUtils;
367
368 // VoiceInteraction session ID that changes for each new request except when
369 // being called for multi-window assist in a single session.
370 private int mViSessionId = 1000;
371
372 // How long to wait in getAssistContextExtras for the activity and foreground services
373 // to respond with the result.
374 private static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500;
375
376 // How long top wait when going through the modern assist (which doesn't need to block
377 // on getting this result before starting to launch its UI).
378 private static final int PENDING_ASSIST_EXTRAS_LONG_TIMEOUT = 2000;
379
380 // How long to wait in getAutofillAssistStructure() for the activity to respond with the result.
381 private static final int PENDING_AUTOFILL_ASSIST_STRUCTURE_TIMEOUT = 2000;
382
383 private final ArrayList<PendingAssistExtras> mPendingAssistExtras = new ArrayList<>();
384
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700385 // Keeps track of the active voice interaction service component, notified from
386 // VoiceInteractionManagerService
387 ComponentName mActiveVoiceInteractionServiceComponent;
388
389 private VrController mVrController;
390 KeyguardController mKeyguardController;
391 private final ClientLifecycleManager mLifecycleManager;
392 private TaskChangeNotificationController mTaskChangeNotificationController;
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700393 /** The controller for all operations related to locktask. */
394 private LockTaskController mLockTaskController;
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700395 private ActivityStartController mActivityStartController;
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700396
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700397 boolean mSuppressResizeConfigChanges;
398
399 private final UpdateConfigurationResult mTmpUpdateConfigurationResult =
400 new UpdateConfigurationResult();
401
402 static final class UpdateConfigurationResult {
403 // Configuration changes that were updated.
404 int changes;
405 // If the activity was relaunched to match the new configuration.
406 boolean activityRelaunched;
407
408 void reset() {
409 changes = 0;
410 activityRelaunched = false;
411 }
412 }
413
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700414 /** Current sequencing integer of the configuration, for skipping old configurations. */
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700415 private int mConfigurationSeq;
416 // To cache the list of supported system locales
417 private String[] mSupportedSystemLocales = null;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700418
419 /**
420 * Temp object used when global and/or display override configuration is updated. It is also
421 * sent to outer world instead of {@link #getGlobalConfiguration} because we don't trust
422 * anyone...
423 */
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700424 private Configuration mTempConfig = new Configuration();
425
Wale Ogunwalef6733932018-06-27 05:14:34 -0700426 /** Temporary to avoid allocations. */
427 final StringBuilder mStringBuilder = new StringBuilder(256);
428
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700429 // Amount of time after a call to stopAppSwitches() during which we will
430 // prevent further untrusted switches from happening.
431 private static final long APP_SWITCH_DELAY_TIME = 5 * 1000;
432
433 /**
434 * The time at which we will allow normal application switches again,
435 * after a call to {@link #stopAppSwitches()}.
436 */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700437 private long mAppSwitchesAllowedTime;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700438 /**
439 * This is set to true after the first switch after mAppSwitchesAllowedTime
440 * is set; any switches after that will clear the time.
441 */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700442 private boolean mDidAppSwitch;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700443
444 IActivityController mController = null;
445 boolean mControllerIsAMonkey = false;
446
Wale Ogunwale214f3482018-10-04 11:00:47 -0700447 final int mFactoryTest;
448
449 /** Used to control how we initialize the service. */
450 ComponentName mTopComponent;
451 String mTopAction = Intent.ACTION_MAIN;
452 String mTopData;
453
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700454 /**
Wale Ogunwale31913b52018-10-13 08:29:31 -0700455 * Dump of the activity state at the time of the last ANR. Cleared after
456 * {@link WindowManagerService#LAST_ANR_LIFETIME_DURATION_MSECS}
457 */
458 String mLastANRState;
459
460 /**
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700461 * Used to retain an update lock when the foreground activity is in
462 * immersive mode.
463 */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700464 private final UpdateLock mUpdateLock = new UpdateLock("immersive");
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700465
466 /**
467 * Packages that are being allowed to perform unrestricted app switches. Mapping is
468 * User -> Type -> uid.
469 */
470 final SparseArray<ArrayMap<String, Integer>> mAllowAppSwitchUids = new SparseArray<>();
471
472 /** The dimensions of the thumbnails in the Recents UI. */
Wale Ogunwalef6733932018-06-27 05:14:34 -0700473 private int mThumbnailWidth;
474 private int mThumbnailHeight;
475 private float mFullscreenThumbnailScale;
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700476
477 /**
478 * Flag that indicates if multi-window is enabled.
479 *
480 * For any particular form of multi-window to be enabled, generic multi-window must be enabled
481 * in {@link com.android.internal.R.bool#config_supportsMultiWindow} config or
482 * {@link Settings.Global#DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES} development option set.
483 * At least one of the forms of multi-window must be enabled in order for this flag to be
484 * initialized to 'true'.
485 *
486 * @see #mSupportsSplitScreenMultiWindow
487 * @see #mSupportsFreeformWindowManagement
488 * @see #mSupportsPictureInPicture
489 * @see #mSupportsMultiDisplay
490 */
491 boolean mSupportsMultiWindow;
492 boolean mSupportsSplitScreenMultiWindow;
493 boolean mSupportsFreeformWindowManagement;
494 boolean mSupportsPictureInPicture;
495 boolean mSupportsMultiDisplay;
496 boolean mForceResizableActivities;
497
498 final List<ActivityTaskManagerInternal.ScreenObserver> mScreenObservers = new ArrayList<>();
499
500 // VR Vr2d Display Id.
501 int mVr2dDisplayId = INVALID_DISPLAY;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700502
Wale Ogunwalef6733932018-06-27 05:14:34 -0700503 /**
504 * Set while we are wanting to sleep, to prevent any
505 * activities from being started/resumed.
506 *
507 * TODO(b/33594039): Clarify the actual state transitions represented by mSleeping.
508 *
509 * Currently mSleeping is set to true when transitioning into the sleep state, and remains true
510 * while in the sleep state until there is a pending transition out of sleep, in which case
511 * mSleeping is set to false, and remains false while awake.
512 *
513 * Whether mSleeping can quickly toggled between true/false without the device actually
514 * display changing states is undefined.
515 */
516 private boolean mSleeping = false;
517
518 /**
519 * The process state used for processes that are running the top activities.
520 * This changes between TOP and TOP_SLEEPING to following mSleeping.
521 */
522 int mTopProcessState = ActivityManager.PROCESS_STATE_TOP;
523
524 // Whether we should show our dialogs (ANR, crash, etc) or just perform their default action
525 // automatically. Important for devices without direct input devices.
526 private boolean mShowDialogs = true;
527
528 /** Set if we are shutting down the system, similar to sleeping. */
529 boolean mShuttingDown = false;
530
531 /**
532 * We want to hold a wake lock while running a voice interaction session, since
533 * this may happen with the screen off and we need to keep the CPU running to
534 * be able to continue to interact with the user.
535 */
536 PowerManager.WakeLock mVoiceWakeLock;
537
538 /**
539 * Set while we are running a voice interaction. This overrides sleeping while it is active.
540 */
541 IVoiceInteractionSession mRunningVoice;
542
543 /**
544 * The last resumed activity. This is identical to the current resumed activity most
545 * of the time but could be different when we're pausing one activity before we resume
546 * another activity.
547 */
548 ActivityRecord mLastResumedActivity;
549
550 /**
551 * The activity that is currently being traced as the active resumed activity.
552 *
553 * @see #updateResumedAppTrace
554 */
555 private @Nullable ActivityRecord mTracedResumedActivity;
556
557 /** If non-null, we are tracking the time the user spends in the currently focused app. */
558 AppTimeTracker mCurAppTimeTracker;
559
Wale Ogunwale008163e2018-07-23 23:11:08 -0700560 private AppWarnings mAppWarnings;
561
Wale Ogunwale53783742018-09-16 10:21:51 -0700562 /**
563 * Packages that the user has asked to have run in screen size
564 * compatibility mode instead of filling the screen.
565 */
566 CompatModePackages mCompatModePackages;
567
Wale Ogunwalef6733932018-06-27 05:14:34 -0700568 private FontScaleSettingObserver mFontScaleSettingObserver;
569
570 private final class FontScaleSettingObserver extends ContentObserver {
571 private final Uri mFontScaleUri = Settings.System.getUriFor(FONT_SCALE);
572 private final Uri mHideErrorDialogsUri = Settings.Global.getUriFor(HIDE_ERROR_DIALOGS);
573
574 public FontScaleSettingObserver() {
575 super(mH);
576 final ContentResolver resolver = mContext.getContentResolver();
577 resolver.registerContentObserver(mFontScaleUri, false, this, UserHandle.USER_ALL);
578 resolver.registerContentObserver(mHideErrorDialogsUri, false, this,
579 UserHandle.USER_ALL);
580 }
581
582 @Override
583 public void onChange(boolean selfChange, Uri uri, @UserIdInt int userId) {
584 if (mFontScaleUri.equals(uri)) {
585 updateFontScaleIfNeeded(userId);
586 } else if (mHideErrorDialogsUri.equals(uri)) {
587 synchronized (mGlobalLock) {
588 updateShouldShowDialogsLocked(getGlobalConfiguration());
589 }
590 }
591 }
592 }
593
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700594 ActivityTaskManagerService(Context context) {
595 mContext = context;
Wale Ogunwale214f3482018-10-04 11:00:47 -0700596 mFactoryTest = FactoryTest.getMode();
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700597 mSystemThread = ActivityThread.currentActivityThread();
598 mUiContext = mSystemThread.getSystemUiContext();
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700599 mLifecycleManager = new ClientLifecycleManager();
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700600 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", GL_ES_VERSION_UNDEFINED);
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700601 }
602
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700603 void onSystemReady() {
Wale Ogunwale214f3482018-10-04 11:00:47 -0700604 mHasHeavyWeightFeature = mContext.getPackageManager().hasSystemFeature(
605 PackageManager.FEATURE_CANT_SAVE_STATE);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700606 mAssistUtils = new AssistUtils(mContext);
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700607 mVrController.onSystemReady();
608 mRecentTasks.onSystemReadyLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700609 }
610
Wale Ogunwalef6733932018-06-27 05:14:34 -0700611 void onInitPowerManagement() {
612 mStackSupervisor.initPowerManagement();
613 final PowerManager pm = (PowerManager)mContext.getSystemService(Context.POWER_SERVICE);
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700614 mPowerManagerInternal = LocalServices.getService(PowerManagerInternal.class);
Wale Ogunwalef6733932018-06-27 05:14:34 -0700615 mVoiceWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "*voice*");
616 mVoiceWakeLock.setReferenceCounted(false);
617 }
618
619 void installSystemProviders() {
620 mFontScaleSettingObserver = new FontScaleSettingObserver();
621 }
622
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700623 void retrieveSettings(ContentResolver resolver) {
624 final boolean freeformWindowManagement =
625 mContext.getPackageManager().hasSystemFeature(FEATURE_FREEFORM_WINDOW_MANAGEMENT)
626 || Settings.Global.getInt(
627 resolver, DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT, 0) != 0;
628
629 final boolean supportsMultiWindow = ActivityTaskManager.supportsMultiWindow(mContext);
630 final boolean supportsPictureInPicture = supportsMultiWindow &&
631 mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE);
632 final boolean supportsSplitScreenMultiWindow =
633 ActivityTaskManager.supportsSplitScreenMultiWindow(mContext);
634 final boolean supportsMultiDisplay = mContext.getPackageManager()
635 .hasSystemFeature(FEATURE_ACTIVITIES_ON_SECONDARY_DISPLAYS);
636 final boolean alwaysFinishActivities =
637 Settings.Global.getInt(resolver, ALWAYS_FINISH_ACTIVITIES, 0) != 0;
638 final boolean forceRtl = Settings.Global.getInt(resolver, DEVELOPMENT_FORCE_RTL, 0) != 0;
639 final boolean forceResizable = Settings.Global.getInt(
640 resolver, DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES, 0) != 0;
Garfield Tane0846042018-07-26 13:42:04 -0700641 final boolean isPc = mContext.getPackageManager().hasSystemFeature(FEATURE_PC);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700642
643 // Transfer any global setting for forcing RTL layout, into a System Property
644 SystemProperties.set(DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0");
645
646 final Configuration configuration = new Configuration();
647 Settings.System.getConfiguration(resolver, configuration);
648 if (forceRtl) {
649 // This will take care of setting the correct layout direction flags
650 configuration.setLayoutDirection(configuration.locale);
651 }
652
653 synchronized (mGlobalLock) {
654 mForceResizableActivities = forceResizable;
655 final boolean multiWindowFormEnabled = freeformWindowManagement
656 || supportsSplitScreenMultiWindow
657 || supportsPictureInPicture
658 || supportsMultiDisplay;
659 if ((supportsMultiWindow || forceResizable) && multiWindowFormEnabled) {
660 mSupportsMultiWindow = true;
661 mSupportsFreeformWindowManagement = freeformWindowManagement;
662 mSupportsSplitScreenMultiWindow = supportsSplitScreenMultiWindow;
663 mSupportsPictureInPicture = supportsPictureInPicture;
664 mSupportsMultiDisplay = supportsMultiDisplay;
665 } else {
666 mSupportsMultiWindow = false;
667 mSupportsFreeformWindowManagement = false;
668 mSupportsSplitScreenMultiWindow = false;
669 mSupportsPictureInPicture = false;
670 mSupportsMultiDisplay = false;
671 }
672 mWindowManager.setForceResizableTasks(mForceResizableActivities);
673 mWindowManager.setSupportsPictureInPicture(mSupportsPictureInPicture);
Garfield Tane0846042018-07-26 13:42:04 -0700674 mWindowManager.setSupportsFreeformWindowManagement(mSupportsFreeformWindowManagement);
675 mWindowManager.setIsPc(isPc);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700676 // This happens before any activities are started, so we can change global configuration
677 // in-place.
678 updateConfigurationLocked(configuration, null, true);
679 final Configuration globalConfig = getGlobalConfiguration();
680 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Initial config: " + globalConfig);
681
682 // Load resources only after the current configuration has been set.
683 final Resources res = mContext.getResources();
684 mThumbnailWidth = res.getDimensionPixelSize(
685 com.android.internal.R.dimen.thumbnail_width);
686 mThumbnailHeight = res.getDimensionPixelSize(
687 com.android.internal.R.dimen.thumbnail_height);
688
689 if ((globalConfig.uiMode & UI_MODE_TYPE_TELEVISION) == UI_MODE_TYPE_TELEVISION) {
690 mFullscreenThumbnailScale = (float) res
691 .getInteger(com.android.internal.R.integer.thumbnail_width_tv) /
692 (float) globalConfig.screenWidthDp;
693 } else {
694 mFullscreenThumbnailScale = res.getFraction(
695 com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1);
696 }
697 }
698 }
699
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700700 // TODO: Will be converted to WM lock once transition is complete.
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700701 void setActivityManagerService(ActivityManagerService am, Looper looper,
702 IntentFirewall intentFirewall, PendingIntentController intentController) {
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700703 mAm = am;
704 mGlobalLock = mAm;
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700705 mH = new H(looper);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700706 mUiHandler = new UiHandler();
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700707 mIntentFirewall = intentFirewall;
Wale Ogunwale53783742018-09-16 10:21:51 -0700708 final File systemDir = SystemServiceManager.ensureSystemDir();
709 mAppWarnings = new AppWarnings(this, mUiContext, mH, mUiHandler, systemDir);
710 mCompatModePackages = new CompatModePackages(this, systemDir, mH);
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700711 mPendingIntentController = intentController;
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700712
713 mTempConfig.setToDefaults();
714 mTempConfig.setLocales(LocaleList.getDefault());
715 mConfigurationSeq = mTempConfig.seq = 1;
716 mStackSupervisor = createStackSupervisor();
717 mStackSupervisor.onConfigurationChanged(mTempConfig);
718
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700719 mTaskChangeNotificationController =
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700720 new TaskChangeNotificationController(mGlobalLock, mStackSupervisor, mH);
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700721 mLockTaskController = new LockTaskController(mContext, mStackSupervisor, mH);
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700722 mActivityStartController = new ActivityStartController(this);
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700723 mRecentTasks = createRecentTasks();
724 mStackSupervisor.setRecentTasks(mRecentTasks);
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700725 mVrController = new VrController(mGlobalLock);
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700726 mKeyguardController = mStackSupervisor.getKeyguardController();
727 }
728
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700729 void onActivityManagerInternalAdded() {
730 mAmInternal = LocalServices.getService(ActivityManagerInternal.class);
Wale Ogunwale6d50dcc2018-07-21 23:00:40 -0700731 mUgmInternal = LocalServices.getService(UriGrantsManagerInternal.class);
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700732 }
733
Yunfan Chen75157d72018-07-27 14:47:21 +0900734 int increaseConfigurationSeqLocked() {
735 mConfigurationSeq = Math.max(++mConfigurationSeq, 1);
736 return mConfigurationSeq;
737 }
738
Wale Ogunwalec9e57de2018-05-08 14:28:07 -0700739 protected ActivityStackSupervisor createStackSupervisor() {
740 final ActivityStackSupervisor supervisor = new ActivityStackSupervisor(this, mH.getLooper());
741 supervisor.initialize();
742 return supervisor;
743 }
744
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700745 void setWindowManager(WindowManagerService wm) {
746 mWindowManager = wm;
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700747 mLockTaskController.setWindowManager(wm);
Wale Ogunwale31913b52018-10-13 08:29:31 -0700748 mStackSupervisor.setWindowManager(wm);
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700749 }
750
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700751 void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) {
752 mUsageStatsInternal = usageStatsManager;
753 }
754
Wale Ogunwalef6733932018-06-27 05:14:34 -0700755 UserManagerService getUserManager() {
756 if (mUserManager == null) {
757 IBinder b = ServiceManager.getService(Context.USER_SERVICE);
758 mUserManager = (UserManagerService) IUserManager.Stub.asInterface(b);
759 }
760 return mUserManager;
761 }
762
763 AppOpsService getAppOpsService() {
764 if (mAppOpsService == null) {
765 IBinder b = ServiceManager.getService(Context.APP_OPS_SERVICE);
766 mAppOpsService = (AppOpsService) IAppOpsService.Stub.asInterface(b);
767 }
768 return mAppOpsService;
769 }
770
771 boolean hasUserRestriction(String restriction, int userId) {
772 return getUserManager().hasUserRestriction(restriction, userId);
773 }
774
Wale Ogunwale16e505a2018-05-07 15:00:49 -0700775 protected RecentTasks createRecentTasks() {
776 return new RecentTasks(this, mStackSupervisor);
777 }
778
779 RecentTasks getRecentTasks() {
780 return mRecentTasks;
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700781 }
782
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700783 ClientLifecycleManager getLifecycleManager() {
784 return mLifecycleManager;
785 }
786
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700787 ActivityStartController getActivityStartController() {
788 return mActivityStartController;
789 }
790
Wale Ogunwaled0412b32018-05-08 09:25:50 -0700791 TaskChangeNotificationController getTaskChangeNotificationController() {
792 return mTaskChangeNotificationController;
793 }
794
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700795 LockTaskController getLockTaskController() {
796 return mLockTaskController;
797 }
798
Yunfan Chen75157d72018-07-27 14:47:21 +0900799 /**
800 * Return the global configuration used by the process corresponding to the input pid. This is
801 * usually the global configuration with some overrides specific to that process.
802 */
803 Configuration getGlobalConfigurationForCallingPid() {
804 final int pid = Binder.getCallingPid();
805 if (pid == MY_PID || pid < 0) {
806 return getGlobalConfiguration();
807 }
808 synchronized (mGlobalLock) {
809 final WindowProcessController app = mPidMap.get(pid);
810 return app != null ? app.getConfiguration() : getGlobalConfiguration();
811 }
812 }
813
814 /**
815 * Return the device configuration info used by the process corresponding to the input pid.
816 * The value is consistent with the global configuration for the process.
817 */
818 @Override
819 public ConfigurationInfo getDeviceConfigurationInfo() {
820 ConfigurationInfo config = new ConfigurationInfo();
821 synchronized (mGlobalLock) {
822 final Configuration globalConfig = getGlobalConfigurationForCallingPid();
823 config.reqTouchScreen = globalConfig.touchscreen;
824 config.reqKeyboardType = globalConfig.keyboard;
825 config.reqNavigation = globalConfig.navigation;
826 if (globalConfig.navigation == Configuration.NAVIGATION_DPAD
827 || globalConfig.navigation == Configuration.NAVIGATION_TRACKBALL) {
828 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV;
829 }
830 if (globalConfig.keyboard != Configuration.KEYBOARD_UNDEFINED
831 && globalConfig.keyboard != Configuration.KEYBOARD_NOKEYS) {
832 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD;
833 }
Wale Ogunwale342fbe92018-10-09 08:44:10 -0700834 config.reqGlEsVersion = GL_ES_VERSION;
Yunfan Chen75157d72018-07-27 14:47:21 +0900835 }
836 return config;
837 }
838
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700839 private void start() {
Wale Ogunwale53783742018-09-16 10:21:51 -0700840 mInternal = new LocalService();
841 LocalServices.addService(ActivityTaskManagerInternal.class, mInternal);
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700842 }
843
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700844 public static final class Lifecycle extends SystemService {
845 private final ActivityTaskManagerService mService;
846
847 public Lifecycle(Context context) {
848 super(context);
849 mService = new ActivityTaskManagerService(context);
850 }
851
852 @Override
853 public void onStart() {
854 publishBinderService(Context.ACTIVITY_TASK_SERVICE, mService);
Wale Ogunwale6767eae2018-05-03 15:52:51 -0700855 mService.start();
Wale Ogunwale65ebd952018-04-25 15:41:44 -0700856 }
857
858 public ActivityTaskManagerService getService() {
859 return mService;
860 }
861 }
862
863 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700864 public final int startActivity(IApplicationThread caller, String callingPackage,
865 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
866 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) {
867 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
868 resultWho, requestCode, startFlags, profilerInfo, bOptions,
869 UserHandle.getCallingUserId());
870 }
871
872 @Override
873 public final int startActivities(IApplicationThread caller, String callingPackage,
874 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle bOptions,
875 int userId) {
876 final String reason = "startActivities";
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700877 enforceNotIsolatedCaller(reason);
878 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, reason);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700879 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700880 return getActivityStartController().startActivities(caller, -1, callingPackage, intents,
Michal Karpinski201bc0c2018-07-20 15:32:00 +0100881 resolvedTypes, resultTo, SafeActivityOptions.fromBundle(bOptions), userId, reason,
882 null /* originatingPendingIntent */);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700883 }
884
885 @Override
886 public int startActivityAsUser(IApplicationThread caller, String callingPackage,
887 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
888 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) {
889 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
890 resultWho, requestCode, startFlags, profilerInfo, bOptions, userId,
891 true /*validateIncomingUser*/);
892 }
893
894 int startActivityAsUser(IApplicationThread caller, String callingPackage,
895 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
896 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId,
897 boolean validateIncomingUser) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700898 enforceNotIsolatedCaller("startActivityAsUser");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700899
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700900 userId = getActivityStartController().checkTargetUser(userId, validateIncomingUser,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700901 Binder.getCallingPid(), Binder.getCallingUid(), "startActivityAsUser");
902
903 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -0700904 return getActivityStartController().obtainStarter(intent, "startActivityAsUser")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700905 .setCaller(caller)
906 .setCallingPackage(callingPackage)
907 .setResolvedType(resolvedType)
908 .setResultTo(resultTo)
909 .setResultWho(resultWho)
910 .setRequestCode(requestCode)
911 .setStartFlags(startFlags)
912 .setProfilerInfo(profilerInfo)
913 .setActivityOptions(bOptions)
914 .setMayWait(userId)
915 .execute();
916
917 }
918
919 @Override
920 public int startActivityIntentSender(IApplicationThread caller, IIntentSender target,
921 IBinder whitelistToken, Intent fillInIntent, String resolvedType, IBinder resultTo,
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700922 String resultWho, int requestCode, int flagsMask, int flagsValues, Bundle bOptions) {
923 enforceNotIsolatedCaller("startActivityIntentSender");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700924 // Refuse possible leaked file descriptors
925 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) {
926 throw new IllegalArgumentException("File descriptors passed in Intent");
927 }
928
929 if (!(target instanceof PendingIntentRecord)) {
930 throw new IllegalArgumentException("Bad PendingIntent object");
931 }
932
933 PendingIntentRecord pir = (PendingIntentRecord)target;
934
935 synchronized (mGlobalLock) {
936 // If this is coming from the currently resumed activity, it is
937 // effectively saying that app switches are allowed at this point.
Andrii Kulian5f750bc2018-07-17 08:57:23 -0700938 final ActivityStack stack = getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700939 if (stack.mResumedActivity != null &&
940 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700941 mAppSwitchesAllowedTime = 0;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700942 }
943 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -0700944 return pir.sendInner(0, fillInIntent, resolvedType, whitelistToken, null, null,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700945 resultTo, resultWho, requestCode, flagsMask, flagsValues, bOptions);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700946 }
947
948 @Override
949 public boolean startNextMatchingActivity(IBinder callingActivity, Intent intent,
950 Bundle bOptions) {
951 // Refuse possible leaked file descriptors
952 if (intent != null && intent.hasFileDescriptors()) {
953 throw new IllegalArgumentException("File descriptors passed in Intent");
954 }
955 SafeActivityOptions options = SafeActivityOptions.fromBundle(bOptions);
956
957 synchronized (mGlobalLock) {
958 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity);
959 if (r == null) {
960 SafeActivityOptions.abort(options);
961 return false;
962 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -0700963 if (!r.attachedToProcess()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -0700964 // The caller is not running... d'oh!
965 SafeActivityOptions.abort(options);
966 return false;
967 }
968 intent = new Intent(intent);
969 // The caller is not allowed to change the data.
970 intent.setDataAndType(r.intent.getData(), r.intent.getType());
971 // And we are resetting to find the next component...
972 intent.setComponent(null);
973
974 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0);
975
976 ActivityInfo aInfo = null;
977 try {
978 List<ResolveInfo> resolves =
979 AppGlobals.getPackageManager().queryIntentActivities(
980 intent, r.resolvedType,
981 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS,
982 UserHandle.getCallingUserId()).getList();
983
984 // Look for the original activity in the list...
985 final int N = resolves != null ? resolves.size() : 0;
986 for (int i=0; i<N; i++) {
987 ResolveInfo rInfo = resolves.get(i);
988 if (rInfo.activityInfo.packageName.equals(r.packageName)
989 && rInfo.activityInfo.name.equals(r.info.name)) {
990 // We found the current one... the next matching is
991 // after it.
992 i++;
993 if (i<N) {
994 aInfo = resolves.get(i).activityInfo;
995 }
996 if (debug) {
997 Slog.v(TAG, "Next matching activity: found current " + r.packageName
998 + "/" + r.info.name);
999 Slog.v(TAG, "Next matching activity: next is " + ((aInfo == null)
1000 ? "null" : aInfo.packageName + "/" + aInfo.name));
1001 }
1002 break;
1003 }
1004 }
1005 } catch (RemoteException e) {
1006 }
1007
1008 if (aInfo == null) {
1009 // Nobody who is next!
1010 SafeActivityOptions.abort(options);
1011 if (debug) Slog.d(TAG, "Next matching activity: nothing found");
1012 return false;
1013 }
1014
1015 intent.setComponent(new ComponentName(
1016 aInfo.applicationInfo.packageName, aInfo.name));
1017 intent.setFlags(intent.getFlags()&~(
1018 Intent.FLAG_ACTIVITY_FORWARD_RESULT|
1019 Intent.FLAG_ACTIVITY_CLEAR_TOP|
1020 Intent.FLAG_ACTIVITY_MULTIPLE_TASK|
1021 FLAG_ACTIVITY_NEW_TASK));
1022
1023 // Okay now we need to start the new activity, replacing the currently running activity.
1024 // This is a little tricky because we want to start the new one as if the current one is
1025 // finished, but not finish the current one first so that there is no flicker.
1026 // And thus...
1027 final boolean wasFinishing = r.finishing;
1028 r.finishing = true;
1029
1030 // Propagate reply information over to the new activity.
1031 final ActivityRecord resultTo = r.resultTo;
1032 final String resultWho = r.resultWho;
1033 final int requestCode = r.requestCode;
1034 r.resultTo = null;
1035 if (resultTo != null) {
1036 resultTo.removeResultsLocked(r, resultWho, requestCode);
1037 }
1038
1039 final long origId = Binder.clearCallingIdentity();
1040 // TODO(b/64750076): Check if calling pid should really be -1.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001041 final int res = getActivityStartController()
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001042 .obtainStarter(intent, "startNextMatchingActivity")
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001043 .setCaller(r.app.getThread())
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001044 .setResolvedType(r.resolvedType)
1045 .setActivityInfo(aInfo)
1046 .setResultTo(resultTo != null ? resultTo.appToken : null)
1047 .setResultWho(resultWho)
1048 .setRequestCode(requestCode)
1049 .setCallingPid(-1)
1050 .setCallingUid(r.launchedFromUid)
1051 .setCallingPackage(r.launchedFromPackage)
1052 .setRealCallingPid(-1)
1053 .setRealCallingUid(r.launchedFromUid)
1054 .setActivityOptions(options)
1055 .execute();
1056 Binder.restoreCallingIdentity(origId);
1057
1058 r.finishing = wasFinishing;
1059 if (res != ActivityManager.START_SUCCESS) {
1060 return false;
1061 }
1062 return true;
1063 }
1064 }
1065
1066 @Override
1067 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage,
1068 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
1069 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) {
1070 final WaitResult res = new WaitResult();
1071 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001072 enforceNotIsolatedCaller("startActivityAndWait");
1073 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
1074 userId, "startActivityAndWait");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001075 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001076 getActivityStartController().obtainStarter(intent, "startActivityAndWait")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001077 .setCaller(caller)
1078 .setCallingPackage(callingPackage)
1079 .setResolvedType(resolvedType)
1080 .setResultTo(resultTo)
1081 .setResultWho(resultWho)
1082 .setRequestCode(requestCode)
1083 .setStartFlags(startFlags)
1084 .setActivityOptions(bOptions)
1085 .setMayWait(userId)
1086 .setProfilerInfo(profilerInfo)
1087 .setWaitResult(res)
1088 .execute();
1089 }
1090 return res;
1091 }
1092
1093 @Override
1094 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage,
1095 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
1096 int startFlags, Configuration config, Bundle bOptions, int userId) {
1097 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001098 enforceNotIsolatedCaller("startActivityWithConfig");
1099 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId,
1100 "startActivityWithConfig");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001101 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001102 return getActivityStartController().obtainStarter(intent, "startActivityWithConfig")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001103 .setCaller(caller)
1104 .setCallingPackage(callingPackage)
1105 .setResolvedType(resolvedType)
1106 .setResultTo(resultTo)
1107 .setResultWho(resultWho)
1108 .setRequestCode(requestCode)
1109 .setStartFlags(startFlags)
1110 .setGlobalConfiguration(config)
1111 .setActivityOptions(bOptions)
1112 .setMayWait(userId)
1113 .execute();
1114 }
1115 }
1116
1117 @Override
1118 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage,
1119 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
1120 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, boolean ignoreTargetSecurity,
1121 int userId) {
1122
1123 // This is very dangerous -- it allows you to perform a start activity (including
1124 // permission grants) as any app that may launch one of your own activities. So
1125 // we will only allow this to be done from activities that are part of the core framework,
1126 // and then only when they are running as the system.
1127 final ActivityRecord sourceRecord;
1128 final int targetUid;
1129 final String targetPackage;
1130 final boolean isResolver;
1131 synchronized (mGlobalLock) {
1132 if (resultTo == null) {
1133 throw new SecurityException("Must be called from an activity");
1134 }
1135 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo);
1136 if (sourceRecord == null) {
1137 throw new SecurityException("Called with bad activity token: " + resultTo);
1138 }
1139 if (!sourceRecord.info.packageName.equals("android")) {
1140 throw new SecurityException(
1141 "Must be called from an activity that is declared in the android package");
1142 }
1143 if (sourceRecord.app == null) {
1144 throw new SecurityException("Called without a process attached to activity");
1145 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001146 if (UserHandle.getAppId(sourceRecord.app.mUid) != SYSTEM_UID) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001147 // This is still okay, as long as this activity is running under the
1148 // uid of the original calling activity.
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001149 if (sourceRecord.app.mUid != sourceRecord.launchedFromUid) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001150 throw new SecurityException(
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001151 "Calling activity in uid " + sourceRecord.app.mUid
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001152 + " must be system uid or original calling uid "
1153 + sourceRecord.launchedFromUid);
1154 }
1155 }
1156 if (ignoreTargetSecurity) {
1157 if (intent.getComponent() == null) {
1158 throw new SecurityException(
1159 "Component must be specified with ignoreTargetSecurity");
1160 }
1161 if (intent.getSelector() != null) {
1162 throw new SecurityException(
1163 "Selector not allowed with ignoreTargetSecurity");
1164 }
1165 }
1166 targetUid = sourceRecord.launchedFromUid;
1167 targetPackage = sourceRecord.launchedFromPackage;
1168 isResolver = sourceRecord.isResolverOrChildActivity();
1169 }
1170
1171 if (userId == UserHandle.USER_NULL) {
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001172 userId = UserHandle.getUserId(sourceRecord.app.mUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001173 }
1174
1175 // TODO: Switch to user app stacks here.
1176 try {
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001177 return getActivityStartController().obtainStarter(intent, "startActivityAsCaller")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001178 .setCallingUid(targetUid)
1179 .setCallingPackage(targetPackage)
1180 .setResolvedType(resolvedType)
1181 .setResultTo(resultTo)
1182 .setResultWho(resultWho)
1183 .setRequestCode(requestCode)
1184 .setStartFlags(startFlags)
1185 .setActivityOptions(bOptions)
1186 .setMayWait(userId)
1187 .setIgnoreTargetSecurity(ignoreTargetSecurity)
1188 .setFilterCallingUid(isResolver ? 0 /* system */ : targetUid)
1189 .execute();
1190 } catch (SecurityException e) {
1191 // XXX need to figure out how to propagate to original app.
1192 // A SecurityException here is generally actually a fault of the original
1193 // calling activity (such as a fairly granting permissions), so propagate it
1194 // back to them.
1195 /*
1196 StringBuilder msg = new StringBuilder();
1197 msg.append("While launching");
1198 msg.append(intent.toString());
1199 msg.append(": ");
1200 msg.append(e.getMessage());
1201 */
1202 throw e;
1203 }
1204 }
1205
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001206 int handleIncomingUser(int callingPid, int callingUid, int userId, String name) {
1207 return mAmInternal.handleIncomingUser(callingPid, callingUid, userId, false /* allowAll */,
1208 ALLOW_FULL_ONLY, name, null /* callerPackage */);
1209 }
1210
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001211 @Override
1212 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid,
1213 Intent intent, String resolvedType, IVoiceInteractionSession session,
1214 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo,
1215 Bundle bOptions, int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001216 mAmInternal.enforceCallingPermission(BIND_VOICE_INTERACTION, "startVoiceActivity()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001217 if (session == null || interactor == null) {
1218 throw new NullPointerException("null session or interactor");
1219 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001220 userId = handleIncomingUser(callingPid, callingUid, userId, "startVoiceActivity");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001221 // TODO: Switch to user app stacks here.
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001222 return getActivityStartController().obtainStarter(intent, "startVoiceActivity")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001223 .setCallingUid(callingUid)
1224 .setCallingPackage(callingPackage)
1225 .setResolvedType(resolvedType)
1226 .setVoiceSession(session)
1227 .setVoiceInteractor(interactor)
1228 .setStartFlags(startFlags)
1229 .setProfilerInfo(profilerInfo)
1230 .setActivityOptions(bOptions)
1231 .setMayWait(userId)
1232 .execute();
1233 }
1234
1235 @Override
1236 public int startAssistantActivity(String callingPackage, int callingPid, int callingUid,
1237 Intent intent, String resolvedType, Bundle bOptions, int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001238 mAmInternal.enforceCallingPermission(BIND_VOICE_INTERACTION, "startAssistantActivity()");
1239 userId = handleIncomingUser(callingPid, callingUid, userId, "startAssistantActivity");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001240
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07001241 return getActivityStartController().obtainStarter(intent, "startAssistantActivity")
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001242 .setCallingUid(callingUid)
1243 .setCallingPackage(callingPackage)
1244 .setResolvedType(resolvedType)
1245 .setActivityOptions(bOptions)
1246 .setMayWait(userId)
1247 .execute();
1248 }
1249
1250 @Override
1251 public void startRecentsActivity(Intent intent, IAssistDataReceiver assistDataReceiver,
1252 IRecentsAnimationRunner recentsAnimationRunner) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001253 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "startRecentsActivity()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001254 final int callingPid = Binder.getCallingPid();
1255 final long origId = Binder.clearCallingIdentity();
1256 try {
1257 synchronized (mGlobalLock) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07001258 final ComponentName recentsComponent = mRecentTasks.getRecentsComponent();
1259 final int recentsUid = mRecentTasks.getRecentsComponentUid();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001260
1261 // Start a new recents animation
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001262 final RecentsAnimation anim = new RecentsAnimation(this, mStackSupervisor,
1263 getActivityStartController(), mWindowManager, callingPid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001264 anim.startRecentsActivity(intent, recentsAnimationRunner, recentsComponent,
1265 recentsUid, assistDataReceiver);
1266 }
1267 } finally {
1268 Binder.restoreCallingIdentity(origId);
1269 }
1270 }
1271
1272 @Override
1273 public final int startActivityFromRecents(int taskId, Bundle bOptions) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001274 enforceCallerIsRecentsOrHasPermission(START_TASKS_FROM_RECENTS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001275 "startActivityFromRecents()");
1276
1277 final int callingPid = Binder.getCallingPid();
1278 final int callingUid = Binder.getCallingUid();
1279 final SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(bOptions);
1280 final long origId = Binder.clearCallingIdentity();
1281 try {
1282 synchronized (mGlobalLock) {
1283 return mStackSupervisor.startActivityFromRecents(callingPid, callingUid, taskId,
1284 safeOptions);
1285 }
1286 } finally {
1287 Binder.restoreCallingIdentity(origId);
1288 }
1289 }
1290
1291 /**
1292 * This is the internal entry point for handling Activity.finish().
1293 *
1294 * @param token The Binder token referencing the Activity we want to finish.
1295 * @param resultCode Result code, if any, from this Activity.
1296 * @param resultData Result data (Intent), if any, from this Activity.
1297 * @param finishTask Whether to finish the task associated with this Activity.
1298 *
1299 * @return Returns true if the activity successfully finished, or false if it is still running.
1300 */
1301 @Override
1302 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData,
1303 int finishTask) {
1304 // Refuse possible leaked file descriptors
1305 if (resultData != null && resultData.hasFileDescriptors()) {
1306 throw new IllegalArgumentException("File descriptors passed in Intent");
1307 }
1308
1309 synchronized (mGlobalLock) {
1310 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1311 if (r == null) {
1312 return true;
1313 }
1314 // Keep track of the root activity of the task before we finish it
1315 TaskRecord tr = r.getTask();
1316 ActivityRecord rootR = tr.getRootActivity();
1317 if (rootR == null) {
1318 Slog.w(TAG, "Finishing task with all activities already finished");
1319 }
1320 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps can
1321 // finish.
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07001322 if (getLockTaskController().activityBlockedFromFinish(r)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001323 return false;
1324 }
1325
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001326 // TODO: There is a dup. of this block of code in ActivityStack.navigateUpToLocked
1327 // We should consolidate.
1328 if (mController != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001329 // Find the first activity that is not finishing.
1330 ActivityRecord next = r.getStack().topRunningActivityLocked(token, 0);
1331 if (next != null) {
1332 // ask watcher if this is allowed
1333 boolean resumeOK = true;
1334 try {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001335 resumeOK = mController.activityResuming(next.packageName);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001336 } catch (RemoteException e) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001337 mController = null;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001338 Watchdog.getInstance().setActivityController(null);
1339 }
1340
1341 if (!resumeOK) {
1342 Slog.i(TAG, "Not finishing activity because controller resumed");
1343 return false;
1344 }
1345 }
1346 }
1347 final long origId = Binder.clearCallingIdentity();
1348 try {
1349 boolean res;
1350 final boolean finishWithRootActivity =
1351 finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY;
1352 if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY
1353 || (finishWithRootActivity && r == rootR)) {
1354 // If requested, remove the task that is associated to this activity only if it
1355 // was the root activity in the task. The result code and data is ignored
1356 // because we don't support returning them across task boundaries. Also, to
1357 // keep backwards compatibility we remove the task from recents when finishing
1358 // task with root activity.
1359 res = mStackSupervisor.removeTaskByIdLocked(tr.taskId, false,
1360 finishWithRootActivity, "finish-activity");
1361 if (!res) {
1362 Slog.i(TAG, "Removing task failed to finish activity");
1363 }
Garfield Tan2746ab52018-07-25 12:33:01 -07001364 // Explicitly dismissing the activity so reset its relaunch flag.
1365 r.mRelaunchReason = ActivityRecord.RELAUNCH_REASON_NONE;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001366 } else {
1367 res = tr.getStack().requestFinishActivityLocked(token, resultCode,
1368 resultData, "app-request", true);
1369 if (!res) {
1370 Slog.i(TAG, "Failed to finish by app-request");
1371 }
1372 }
1373 return res;
1374 } finally {
1375 Binder.restoreCallingIdentity(origId);
1376 }
1377 }
1378 }
1379
1380 @Override
1381 public boolean finishActivityAffinity(IBinder token) {
1382 synchronized (mGlobalLock) {
1383 final long origId = Binder.clearCallingIdentity();
1384 try {
1385 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1386 if (r == null) {
1387 return false;
1388 }
1389
1390 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps
1391 // can finish.
1392 final TaskRecord task = r.getTask();
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07001393 if (getLockTaskController().activityBlockedFromFinish(r)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001394 return false;
1395 }
1396 return task.getStack().finishActivityAffinityLocked(r);
1397 } finally {
1398 Binder.restoreCallingIdentity(origId);
1399 }
1400 }
1401 }
1402
1403 @Override
1404 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) {
1405 final long origId = Binder.clearCallingIdentity();
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001406 try {
1407 WindowProcessController proc = null;
1408 synchronized (mGlobalLock) {
1409 ActivityStack stack = ActivityRecord.getStackLocked(token);
1410 if (stack == null) {
1411 return;
1412 }
1413 final ActivityRecord r = mStackSupervisor.activityIdleInternalLocked(token,
1414 false /* fromTimeout */, false /* processPausingActivities */, config);
1415 if (r != null) {
1416 proc = r.app;
1417 }
1418 if (stopProfiling && proc != null) {
1419 proc.clearProfilerIfNeeded();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001420 }
1421 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07001422 } finally {
1423 Binder.restoreCallingIdentity(origId);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001424 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001425 }
1426
1427 @Override
1428 public final void activityResumed(IBinder token) {
1429 final long origId = Binder.clearCallingIdentity();
1430 synchronized (mGlobalLock) {
1431 ActivityRecord.activityResumedLocked(token);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001432 mWindowManager.notifyAppResumedFinished(token);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001433 }
1434 Binder.restoreCallingIdentity(origId);
1435 }
1436
1437 @Override
1438 public final void activityPaused(IBinder token) {
1439 final long origId = Binder.clearCallingIdentity();
1440 synchronized (mGlobalLock) {
1441 ActivityStack stack = ActivityRecord.getStackLocked(token);
1442 if (stack != null) {
1443 stack.activityPausedLocked(token, false);
1444 }
1445 }
1446 Binder.restoreCallingIdentity(origId);
1447 }
1448
1449 @Override
1450 public final void activityStopped(IBinder token, Bundle icicle,
1451 PersistableBundle persistentState, CharSequence description) {
1452 if (DEBUG_ALL) Slog.v(TAG, "Activity stopped: token=" + token);
1453
1454 // Refuse possible leaked file descriptors
1455 if (icicle != null && icicle.hasFileDescriptors()) {
1456 throw new IllegalArgumentException("File descriptors passed in Bundle");
1457 }
1458
1459 final long origId = Binder.clearCallingIdentity();
1460
1461 synchronized (mGlobalLock) {
1462 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1463 if (r != null) {
1464 r.activityStoppedLocked(icicle, persistentState, description);
1465 }
1466 }
1467
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001468 mAmInternal.trimApplications();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001469
1470 Binder.restoreCallingIdentity(origId);
1471 }
1472
1473 @Override
1474 public final void activityDestroyed(IBinder token) {
1475 if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "ACTIVITY DESTROYED: " + token);
1476 synchronized (mGlobalLock) {
1477 ActivityStack stack = ActivityRecord.getStackLocked(token);
1478 if (stack != null) {
1479 stack.activityDestroyedLocked(token, "activityDestroyed");
1480 }
1481 }
1482 }
1483
1484 @Override
1485 public final void activityRelaunched(IBinder token) {
1486 final long origId = Binder.clearCallingIdentity();
1487 synchronized (mGlobalLock) {
1488 mStackSupervisor.activityRelaunchedLocked(token);
1489 }
1490 Binder.restoreCallingIdentity(origId);
1491 }
1492
1493 public final void activitySlept(IBinder token) {
1494 if (DEBUG_ALL) Slog.v(TAG, "Activity slept: token=" + token);
1495
1496 final long origId = Binder.clearCallingIdentity();
1497
1498 synchronized (mGlobalLock) {
1499 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1500 if (r != null) {
1501 mStackSupervisor.activitySleptLocked(r);
1502 }
1503 }
1504
1505 Binder.restoreCallingIdentity(origId);
1506 }
1507
1508 @Override
1509 public void setRequestedOrientation(IBinder token, int requestedOrientation) {
1510 synchronized (mGlobalLock) {
1511 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1512 if (r == null) {
1513 return;
1514 }
1515 final long origId = Binder.clearCallingIdentity();
1516 try {
1517 r.setRequestedOrientation(requestedOrientation);
1518 } finally {
1519 Binder.restoreCallingIdentity(origId);
1520 }
1521 }
1522 }
1523
1524 @Override
1525 public int getRequestedOrientation(IBinder token) {
1526 synchronized (mGlobalLock) {
1527 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1528 if (r == null) {
1529 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
1530 }
1531 return r.getRequestedOrientation();
1532 }
1533 }
1534
1535 @Override
1536 public void setImmersive(IBinder token, boolean immersive) {
1537 synchronized (mGlobalLock) {
1538 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1539 if (r == null) {
1540 throw new IllegalArgumentException();
1541 }
1542 r.immersive = immersive;
1543
1544 // update associated state if we're frontmost
Andrii Kulian52d255c2018-07-13 11:32:19 -07001545 if (r.isResumedActivityOnDisplay()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001546 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, "Frontmost changed immersion: "+ r);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001547 applyUpdateLockStateLocked(r);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001548 }
1549 }
1550 }
1551
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001552 void applyUpdateLockStateLocked(ActivityRecord r) {
1553 // Modifications to the UpdateLock state are done on our handler, outside
1554 // the activity manager's locks. The new state is determined based on the
1555 // state *now* of the relevant activity record. The object is passed to
1556 // the handler solely for logging detail, not to be consulted/modified.
1557 final boolean nextState = r != null && r.immersive;
1558 mH.post(() -> {
1559 if (mUpdateLock.isHeld() != nextState) {
1560 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE,
1561 "Applying new update lock state '" + nextState + "' for " + r);
1562 if (nextState) {
1563 mUpdateLock.acquire();
1564 } else {
1565 mUpdateLock.release();
1566 }
1567 }
1568 });
1569 }
1570
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001571 @Override
1572 public boolean isImmersive(IBinder token) {
1573 synchronized (mGlobalLock) {
1574 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1575 if (r == null) {
1576 throw new IllegalArgumentException();
1577 }
1578 return r.immersive;
1579 }
1580 }
1581
1582 @Override
1583 public boolean isTopActivityImmersive() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001584 enforceNotIsolatedCaller("isTopActivityImmersive");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001585 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001586 final ActivityRecord r = getTopDisplayFocusedStack().topRunningActivityLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001587 return (r != null) ? r.immersive : false;
1588 }
1589 }
1590
1591 @Override
1592 public void overridePendingTransition(IBinder token, String packageName,
1593 int enterAnim, int exitAnim) {
1594 synchronized (mGlobalLock) {
1595 ActivityRecord self = ActivityRecord.isInStackLocked(token);
1596 if (self == null) {
1597 return;
1598 }
1599
1600 final long origId = Binder.clearCallingIdentity();
1601
1602 if (self.isState(
1603 ActivityStack.ActivityState.RESUMED, ActivityStack.ActivityState.PAUSING)) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001604 mWindowManager.overridePendingAppTransition(packageName,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001605 enterAnim, exitAnim, null);
1606 }
1607
1608 Binder.restoreCallingIdentity(origId);
1609 }
1610 }
1611
1612 @Override
1613 public int getFrontActivityScreenCompatMode() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001614 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001615 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001616 final ActivityRecord r = getTopDisplayFocusedStack().topRunningActivityLocked();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001617 if (r == null) {
1618 return ActivityManager.COMPAT_MODE_UNKNOWN;
1619 }
Wale Ogunwale53783742018-09-16 10:21:51 -07001620 return mCompatModePackages.computeCompatModeLocked(r.info.applicationInfo);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001621 }
1622 }
1623
1624 @Override
1625 public void setFrontActivityScreenCompatMode(int mode) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001626 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001627 "setFrontActivityScreenCompatMode");
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001628 ApplicationInfo ai;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001629 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001630 final ActivityRecord r = getTopDisplayFocusedStack().topRunningActivityLocked();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001631 if (r == null) {
1632 Slog.w(TAG, "setFrontActivityScreenCompatMode failed: no top activity");
1633 return;
1634 }
1635 ai = r.info.applicationInfo;
Wale Ogunwale53783742018-09-16 10:21:51 -07001636 mCompatModePackages.setPackageScreenCompatModeLocked(ai, mode);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001637 }
1638 }
1639
1640 @Override
1641 public int getLaunchedFromUid(IBinder activityToken) {
1642 ActivityRecord srec;
1643 synchronized (mGlobalLock) {
1644 srec = ActivityRecord.forTokenLocked(activityToken);
1645 }
1646 if (srec == null) {
1647 return -1;
1648 }
1649 return srec.launchedFromUid;
1650 }
1651
1652 @Override
1653 public String getLaunchedFromPackage(IBinder activityToken) {
1654 ActivityRecord srec;
1655 synchronized (mGlobalLock) {
1656 srec = ActivityRecord.forTokenLocked(activityToken);
1657 }
1658 if (srec == null) {
1659 return null;
1660 }
1661 return srec.launchedFromPackage;
1662 }
1663
1664 @Override
1665 public boolean convertFromTranslucent(IBinder token) {
1666 final long origId = Binder.clearCallingIdentity();
1667 try {
1668 synchronized (mGlobalLock) {
1669 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1670 if (r == null) {
1671 return false;
1672 }
1673 final boolean translucentChanged = r.changeWindowTranslucency(true);
1674 if (translucentChanged) {
1675 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
1676 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001677 mWindowManager.setAppFullscreen(token, true);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001678 return translucentChanged;
1679 }
1680 } finally {
1681 Binder.restoreCallingIdentity(origId);
1682 }
1683 }
1684
1685 @Override
1686 public boolean convertToTranslucent(IBinder token, Bundle options) {
1687 SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(options);
1688 final long origId = Binder.clearCallingIdentity();
1689 try {
1690 synchronized (mGlobalLock) {
1691 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
1692 if (r == null) {
1693 return false;
1694 }
1695 final TaskRecord task = r.getTask();
1696 int index = task.mActivities.lastIndexOf(r);
1697 if (index > 0) {
1698 ActivityRecord under = task.mActivities.get(index - 1);
1699 under.returningOptions = safeOptions != null ? safeOptions.getOptions(r) : null;
1700 }
1701 final boolean translucentChanged = r.changeWindowTranslucency(false);
1702 if (translucentChanged) {
1703 r.getStack().convertActivityToTranslucent(r);
1704 }
1705 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001706 mWindowManager.setAppFullscreen(token, false);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001707 return translucentChanged;
1708 }
1709 } finally {
1710 Binder.restoreCallingIdentity(origId);
1711 }
1712 }
1713
1714 @Override
1715 public void notifyActivityDrawn(IBinder token) {
1716 if (DEBUG_VISIBILITY) Slog.d(TAG_VISIBILITY, "notifyActivityDrawn: token=" + token);
1717 synchronized (mGlobalLock) {
1718 ActivityRecord r = mStackSupervisor.isInAnyStackLocked(token);
1719 if (r != null) {
1720 r.getStack().notifyActivityDrawnLocked(r);
1721 }
1722 }
1723 }
1724
1725 @Override
1726 public void reportActivityFullyDrawn(IBinder token, boolean restoredFromBundle) {
1727 synchronized (mGlobalLock) {
1728 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1729 if (r == null) {
1730 return;
1731 }
1732 r.reportFullyDrawnLocked(restoredFromBundle);
1733 }
1734 }
1735
1736 @Override
1737 public int getActivityDisplayId(IBinder activityToken) throws RemoteException {
1738 synchronized (mGlobalLock) {
1739 final ActivityStack stack = ActivityRecord.getStackLocked(activityToken);
1740 if (stack != null && stack.mDisplayId != INVALID_DISPLAY) {
1741 return stack.mDisplayId;
1742 }
1743 return DEFAULT_DISPLAY;
1744 }
1745 }
1746
1747 @Override
1748 public ActivityManager.StackInfo getFocusedStackInfo() throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001749 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001750 long ident = Binder.clearCallingIdentity();
1751 try {
1752 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07001753 ActivityStack focusedStack = getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001754 if (focusedStack != null) {
1755 return mStackSupervisor.getStackInfo(focusedStack.mStackId);
1756 }
1757 return null;
1758 }
1759 } finally {
1760 Binder.restoreCallingIdentity(ident);
1761 }
1762 }
1763
1764 @Override
1765 public void setFocusedStack(int stackId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001766 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001767 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedStack: stackId=" + stackId);
1768 final long callingId = Binder.clearCallingIdentity();
1769 try {
1770 synchronized (mGlobalLock) {
1771 final ActivityStack stack = mStackSupervisor.getStack(stackId);
1772 if (stack == null) {
1773 Slog.w(TAG, "setFocusedStack: No stack with id=" + stackId);
1774 return;
1775 }
1776 final ActivityRecord r = stack.topRunningActivityLocked();
Louis Chang19443452018-10-09 12:10:21 +08001777 if (r != null && r.moveFocusableActivityToTop("setFocusedStack")) {
Andrii Kulianab132ee2018-07-24 22:10:21 +08001778 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001779 }
1780 }
1781 } finally {
1782 Binder.restoreCallingIdentity(callingId);
1783 }
1784 }
1785
1786 @Override
1787 public void setFocusedTask(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001788 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedTask()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001789 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedTask: taskId=" + taskId);
1790 final long callingId = Binder.clearCallingIdentity();
1791 try {
1792 synchronized (mGlobalLock) {
1793 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
1794 if (task == null) {
1795 return;
1796 }
1797 final ActivityRecord r = task.topRunningActivityLocked();
Louis Chang19443452018-10-09 12:10:21 +08001798 if (r != null && r.moveFocusableActivityToTop("setFocusedTask")) {
Andrii Kulianab132ee2018-07-24 22:10:21 +08001799 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001800 }
1801 }
1802 } finally {
1803 Binder.restoreCallingIdentity(callingId);
1804 }
1805 }
1806
1807 @Override
1808 public boolean removeTask(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001809 enforceCallerIsRecentsOrHasPermission(REMOVE_TASKS, "removeTask()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001810 synchronized (mGlobalLock) {
1811 final long ident = Binder.clearCallingIdentity();
1812 try {
1813 return mStackSupervisor.removeTaskByIdLocked(taskId, true, REMOVE_FROM_RECENTS,
1814 "remove-task");
1815 } finally {
1816 Binder.restoreCallingIdentity(ident);
1817 }
1818 }
1819 }
1820
1821 @Override
Winson Chunge6439102018-07-30 15:48:01 -07001822 public void removeAllVisibleRecentTasks() {
1823 enforceCallerIsRecentsOrHasPermission(REMOVE_TASKS, "removeAllVisibleRecentTasks()");
1824 synchronized (mGlobalLock) {
1825 final long ident = Binder.clearCallingIdentity();
1826 try {
1827 getRecentTasks().removeAllVisibleTasks();
1828 } finally {
1829 Binder.restoreCallingIdentity(ident);
1830 }
1831 }
1832 }
1833
1834 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001835 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) {
1836 synchronized (mGlobalLock) {
1837 final ActivityRecord srec = ActivityRecord.forTokenLocked(token);
1838 if (srec != null) {
1839 return srec.getStack().shouldUpRecreateTaskLocked(srec, destAffinity);
1840 }
1841 }
1842 return false;
1843 }
1844
1845 @Override
1846 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode,
1847 Intent resultData) {
1848
1849 synchronized (mGlobalLock) {
1850 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
1851 if (r != null) {
1852 return r.getStack().navigateUpToLocked(r, destIntent, resultCode, resultData);
1853 }
1854 return false;
1855 }
1856 }
1857
1858 /**
1859 * Attempts to move a task backwards in z-order (the order of activities within the task is
1860 * unchanged).
1861 *
1862 * There are several possible results of this call:
1863 * - if the task is locked, then we will show the lock toast
1864 * - if there is a task behind the provided task, then that task is made visible and resumed as
1865 * this task is moved to the back
1866 * - otherwise, if there are no other tasks in the stack:
1867 * - if this task is in the pinned stack, then we remove the stack completely, which will
1868 * have the effect of moving the task to the top or bottom of the fullscreen stack
1869 * (depending on whether it is visible)
1870 * - otherwise, we simply return home and hide this task
1871 *
1872 * @param token A reference to the activity we wish to move
1873 * @param nonRoot If false then this only works if the activity is the root
1874 * of a task; if true it will work for any activity in a task.
1875 * @return Returns true if the move completed, false if not.
1876 */
1877 @Override
1878 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001879 enforceNotIsolatedCaller("moveActivityTaskToBack");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001880 synchronized (mGlobalLock) {
1881 final long origId = Binder.clearCallingIdentity();
1882 try {
1883 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot);
1884 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
1885 if (task != null) {
1886 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId);
1887 }
1888 } finally {
1889 Binder.restoreCallingIdentity(origId);
1890 }
1891 }
1892 return false;
1893 }
1894
1895 @Override
1896 public Rect getTaskBounds(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001897 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getTaskBounds()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001898 long ident = Binder.clearCallingIdentity();
1899 Rect rect = new Rect();
1900 try {
1901 synchronized (mGlobalLock) {
1902 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
1903 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
1904 if (task == null) {
1905 Slog.w(TAG, "getTaskBounds: taskId=" + taskId + " not found");
1906 return rect;
1907 }
1908 if (task.getStack() != null) {
1909 // Return the bounds from window manager since it will be adjusted for various
1910 // things like the presense of a docked stack for tasks that aren't resizeable.
1911 task.getWindowContainerBounds(rect);
1912 } else {
1913 // Task isn't in window manager yet since it isn't associated with a stack.
1914 // Return the persist value from activity manager
1915 if (!task.matchParentBounds()) {
1916 rect.set(task.getBounds());
1917 } else if (task.mLastNonFullscreenBounds != null) {
1918 rect.set(task.mLastNonFullscreenBounds);
1919 }
1920 }
1921 }
1922 } finally {
1923 Binder.restoreCallingIdentity(ident);
1924 }
1925 return rect;
1926 }
1927
1928 @Override
1929 public ActivityManager.TaskDescription getTaskDescription(int id) {
1930 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001931 enforceCallerIsRecentsOrHasPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001932 MANAGE_ACTIVITY_STACKS, "getTaskDescription()");
1933 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(id,
1934 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
1935 if (tr != null) {
1936 return tr.lastTaskDescription;
1937 }
1938 }
1939 return null;
1940 }
1941
1942 @Override
Wale Ogunwale65ebd952018-04-25 15:41:44 -07001943 public void setTaskWindowingMode(int taskId, int windowingMode, boolean toTop) {
1944 if (windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) {
1945 setTaskWindowingModeSplitScreenPrimary(taskId, SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT,
1946 toTop, ANIMATE, null /* initialBounds */, true /* showRecents */);
1947 return;
1948 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001949 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "setTaskWindowingMode()");
Wale Ogunwale65ebd952018-04-25 15:41:44 -07001950 synchronized (mGlobalLock) {
1951 final long ident = Binder.clearCallingIdentity();
1952 try {
1953 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
1954 if (task == null) {
1955 Slog.w(TAG, "setTaskWindowingMode: No task for id=" + taskId);
1956 return;
1957 }
1958
1959 if (DEBUG_STACK) Slog.d(TAG_STACK, "setTaskWindowingMode: moving task=" + taskId
1960 + " to windowingMode=" + windowingMode + " toTop=" + toTop);
1961
1962 if (!task.isActivityTypeStandardOrUndefined()) {
1963 throw new IllegalArgumentException("setTaskWindowingMode: Attempt to move"
1964 + " non-standard task " + taskId + " to windowing mode="
1965 + windowingMode);
1966 }
1967
1968 final ActivityStack stack = task.getStack();
1969 if (toTop) {
1970 stack.moveToFront("setTaskWindowingMode", task);
1971 }
1972 stack.setWindowingMode(windowingMode);
1973 } finally {
1974 Binder.restoreCallingIdentity(ident);
1975 }
1976 }
1977 }
1978
1979 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001980 public String getCallingPackage(IBinder token) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001981 synchronized (mGlobalLock) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001982 ActivityRecord r = getCallingRecordLocked(token);
1983 return r != null ? r.info.packageName : null;
1984 }
1985 }
1986
1987 @Override
1988 public ComponentName getCallingActivity(IBinder token) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07001989 synchronized (mGlobalLock) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07001990 ActivityRecord r = getCallingRecordLocked(token);
1991 return r != null ? r.intent.getComponent() : null;
1992 }
1993 }
1994
1995 private ActivityRecord getCallingRecordLocked(IBinder token) {
1996 ActivityRecord r = ActivityRecord.isInStackLocked(token);
1997 if (r == null) {
1998 return null;
1999 }
2000 return r.resultTo;
2001 }
2002
2003 @Override
2004 public void unhandledBack() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002005 mAmInternal.enforceCallingPermission(android.Manifest.permission.FORCE_BACK, "unhandledBack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002006
2007 synchronized (mGlobalLock) {
2008 final long origId = Binder.clearCallingIdentity();
2009 try {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07002010 getTopDisplayFocusedStack().unhandledBackLocked();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002011 } finally {
2012 Binder.restoreCallingIdentity(origId);
2013 }
2014 }
2015 }
2016
2017 /**
2018 * TODO: Add mController hook
2019 */
2020 @Override
2021 public void moveTaskToFront(int taskId, int flags, Bundle bOptions) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002022 mAmInternal.enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, "moveTaskToFront()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002023
2024 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToFront: moving taskId=" + taskId);
2025 synchronized (mGlobalLock) {
2026 moveTaskToFrontLocked(taskId, flags, SafeActivityOptions.fromBundle(bOptions),
2027 false /* fromRecents */);
2028 }
2029 }
2030
2031 void moveTaskToFrontLocked(int taskId, int flags, SafeActivityOptions options,
2032 boolean fromRecents) {
2033
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002034 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(),
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002035 Binder.getCallingUid(), -1, -1, "Task to front")) {
2036 SafeActivityOptions.abort(options);
2037 return;
2038 }
2039 final long origId = Binder.clearCallingIdentity();
2040 try {
2041 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2042 if (task == null) {
2043 Slog.d(TAG, "Could not find task for id: "+ taskId);
Winson Chungd0243682018-09-25 18:11:54 -07002044 SafeActivityOptions.abort(options);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002045 return;
2046 }
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002047 if (getLockTaskController().isLockTaskModeViolation(task)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002048 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode");
Winson Chungd0243682018-09-25 18:11:54 -07002049 SafeActivityOptions.abort(options);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002050 return;
2051 }
2052 ActivityOptions realOptions = options != null
2053 ? options.getOptions(mStackSupervisor)
2054 : null;
2055 mStackSupervisor.findTaskToMoveToFront(task, flags, realOptions, "moveTaskToFront",
2056 false /* forceNonResizable */);
2057
2058 final ActivityRecord topActivity = task.getTopActivity();
2059 if (topActivity != null) {
2060
2061 // We are reshowing a task, use a starting window to hide the initial draw delay
2062 // so the transition can start earlier.
2063 topActivity.showStartingWindow(null /* prev */, false /* newTask */,
2064 true /* taskSwitch */, fromRecents);
2065 }
2066 } finally {
2067 Binder.restoreCallingIdentity(origId);
2068 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002069 }
2070
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002071 boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid,
2072 int callingPid, int callingUid, String name) {
2073 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) {
2074 return true;
2075 }
2076
2077 if (getRecentTasks().isCallerRecents(sourceUid)) {
2078 return true;
2079 }
2080
2081 int perm = checkComponentPermission(STOP_APP_SWITCHES, sourcePid, sourceUid, -1, true);
2082 if (perm == PackageManager.PERMISSION_GRANTED) {
2083 return true;
2084 }
2085 if (checkAllowAppSwitchUid(sourceUid)) {
2086 return true;
2087 }
2088
2089 // If the actual IPC caller is different from the logical source, then
2090 // also see if they are allowed to control app switches.
2091 if (callingUid != -1 && callingUid != sourceUid) {
2092 perm = checkComponentPermission(STOP_APP_SWITCHES, callingPid, callingUid, -1, true);
2093 if (perm == PackageManager.PERMISSION_GRANTED) {
2094 return true;
2095 }
2096 if (checkAllowAppSwitchUid(callingUid)) {
2097 return true;
2098 }
2099 }
2100
2101 Slog.w(TAG, name + " request from " + sourceUid + " stopped");
2102 return false;
2103 }
2104
2105 private boolean checkAllowAppSwitchUid(int uid) {
2106 ArrayMap<String, Integer> types = mAllowAppSwitchUids.get(UserHandle.getUserId(uid));
2107 if (types != null) {
2108 for (int i = types.size() - 1; i >= 0; i--) {
2109 if (types.valueAt(i).intValue() == uid) {
2110 return true;
2111 }
2112 }
2113 }
2114 return false;
2115 }
2116
2117 @Override
2118 public void setActivityController(IActivityController controller, boolean imAMonkey) {
2119 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER,
2120 "setActivityController()");
2121 synchronized (mGlobalLock) {
2122 mController = controller;
2123 mControllerIsAMonkey = imAMonkey;
2124 Watchdog.getInstance().setActivityController(controller);
2125 }
2126 }
2127
2128 boolean isControllerAMonkey() {
2129 synchronized (mGlobalLock) {
2130 return mController != null && mControllerIsAMonkey;
2131 }
2132 }
2133
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002134 @Override
2135 public int getTaskForActivity(IBinder token, boolean onlyRoot) {
2136 synchronized (mGlobalLock) {
2137 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot);
2138 }
2139 }
2140
2141 @Override
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002142 public List<ActivityManager.RunningTaskInfo> getTasks(int maxNum) {
2143 return getFilteredTasks(maxNum, ACTIVITY_TYPE_UNDEFINED, WINDOWING_MODE_UNDEFINED);
2144 }
2145
2146 @Override
2147 public List<ActivityManager.RunningTaskInfo> getFilteredTasks(int maxNum,
2148 @WindowConfiguration.ActivityType int ignoreActivityType,
2149 @WindowConfiguration.WindowingMode int ignoreWindowingMode) {
2150 final int callingUid = Binder.getCallingUid();
2151 ArrayList<ActivityManager.RunningTaskInfo> list = new ArrayList<>();
2152
2153 synchronized (mGlobalLock) {
2154 if (DEBUG_ALL) Slog.v(TAG, "getTasks: max=" + maxNum);
2155
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002156 final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(),
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002157 callingUid);
2158 mStackSupervisor.getRunningTasks(maxNum, list, ignoreActivityType,
2159 ignoreWindowingMode, callingUid, allowed);
2160 }
2161
2162 return list;
2163 }
2164
2165 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002166 public final void finishSubActivity(IBinder token, String resultWho, int requestCode) {
2167 synchronized (mGlobalLock) {
2168 final long origId = Binder.clearCallingIdentity();
2169 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2170 if (r != null) {
2171 r.getStack().finishSubActivityLocked(r, resultWho, requestCode);
2172 }
2173 Binder.restoreCallingIdentity(origId);
2174 }
2175 }
2176
2177 @Override
2178 public boolean willActivityBeVisible(IBinder token) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002179 synchronized (mGlobalLock) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002180 ActivityStack stack = ActivityRecord.getStackLocked(token);
2181 if (stack != null) {
2182 return stack.willActivityBeVisibleLocked(token);
2183 }
2184 return false;
2185 }
2186 }
2187
2188 @Override
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002189 public void moveTaskToStack(int taskId, int stackId, boolean toTop) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002190 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToStack()");
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002191 synchronized (mGlobalLock) {
2192 final long ident = Binder.clearCallingIdentity();
2193 try {
2194 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2195 if (task == null) {
2196 Slog.w(TAG, "moveTaskToStack: No task for id=" + taskId);
2197 return;
2198 }
2199
2200 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToStack: moving task=" + taskId
2201 + " to stackId=" + stackId + " toTop=" + toTop);
2202
2203 final ActivityStack stack = mStackSupervisor.getStack(stackId);
2204 if (stack == null) {
2205 throw new IllegalStateException(
2206 "moveTaskToStack: No stack for stackId=" + stackId);
2207 }
2208 if (!stack.isActivityTypeStandardOrUndefined()) {
2209 throw new IllegalArgumentException("moveTaskToStack: Attempt to move task "
2210 + taskId + " to stack " + stackId);
2211 }
2212 if (stack.inSplitScreenPrimaryWindowingMode()) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002213 mWindowManager.setDockedStackCreateState(
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002214 SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT, null /* initialBounds */);
2215 }
2216 task.reparent(stack, toTop, REPARENT_KEEP_STACK_AT_FRONT, ANIMATE, !DEFER_RESUME,
2217 "moveTaskToStack");
2218 } finally {
2219 Binder.restoreCallingIdentity(ident);
2220 }
2221 }
2222 }
2223
2224 @Override
2225 public void resizeStack(int stackId, Rect destBounds, boolean allowResizeInDockedMode,
2226 boolean preserveWindows, boolean animate, int animationDuration) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002227 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()");
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002228
2229 final long ident = Binder.clearCallingIdentity();
2230 try {
2231 synchronized (mGlobalLock) {
2232 if (animate) {
2233 final PinnedActivityStack stack = mStackSupervisor.getStack(stackId);
2234 if (stack == null) {
2235 Slog.w(TAG, "resizeStack: stackId " + stackId + " not found.");
2236 return;
2237 }
2238 if (stack.getWindowingMode() != WINDOWING_MODE_PINNED) {
2239 throw new IllegalArgumentException("Stack: " + stackId
2240 + " doesn't support animated resize.");
2241 }
2242 stack.animateResizePinnedStack(null /* sourceHintBounds */, destBounds,
2243 animationDuration, false /* fromFullscreen */);
2244 } else {
2245 final ActivityStack stack = mStackSupervisor.getStack(stackId);
2246 if (stack == null) {
2247 Slog.w(TAG, "resizeStack: stackId " + stackId + " not found.");
2248 return;
2249 }
2250 mStackSupervisor.resizeStackLocked(stack, destBounds,
2251 null /* tempTaskBounds */, null /* tempTaskInsetBounds */,
2252 preserveWindows, allowResizeInDockedMode, !DEFER_RESUME);
2253 }
2254 }
2255 } finally {
2256 Binder.restoreCallingIdentity(ident);
2257 }
2258 }
2259
2260 /**
2261 * Moves the specified task to the primary-split-screen stack.
2262 *
2263 * @param taskId Id of task to move.
2264 * @param createMode The mode the primary split screen stack should be created in if it doesn't
2265 * exist already. See
2266 * {@link android.app.ActivityTaskManager#SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT}
2267 * and
2268 * {@link android.app.ActivityTaskManager#SPLIT_SCREEN_CREATE_MODE_BOTTOM_OR_RIGHT}
2269 * @param toTop If the task and stack should be moved to the top.
2270 * @param animate Whether we should play an animation for the moving the task.
2271 * @param initialBounds If the primary stack gets created, it will use these bounds for the
2272 * stack. Pass {@code null} to use default bounds.
2273 * @param showRecents If the recents activity should be shown on the other side of the task
2274 * going into split-screen mode.
2275 */
2276 @Override
2277 public boolean setTaskWindowingModeSplitScreenPrimary(int taskId, int createMode,
2278 boolean toTop, boolean animate, Rect initialBounds, boolean showRecents) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002279 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002280 "setTaskWindowingModeSplitScreenPrimary()");
2281 synchronized (mGlobalLock) {
2282 final long ident = Binder.clearCallingIdentity();
2283 try {
2284 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2285 if (task == null) {
2286 Slog.w(TAG, "setTaskWindowingModeSplitScreenPrimary: No task for id=" + taskId);
2287 return false;
2288 }
2289 if (DEBUG_STACK) Slog.d(TAG_STACK,
2290 "setTaskWindowingModeSplitScreenPrimary: moving task=" + taskId
2291 + " to createMode=" + createMode + " toTop=" + toTop);
2292 if (!task.isActivityTypeStandardOrUndefined()) {
2293 throw new IllegalArgumentException("setTaskWindowingMode: Attempt to move"
2294 + " non-standard task " + taskId + " to split-screen windowing mode");
2295 }
2296
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002297 mWindowManager.setDockedStackCreateState(createMode, initialBounds);
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002298 final int windowingMode = task.getWindowingMode();
2299 final ActivityStack stack = task.getStack();
2300 if (toTop) {
2301 stack.moveToFront("setTaskWindowingModeSplitScreenPrimary", task);
2302 }
2303 stack.setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, animate, showRecents,
2304 false /* enteringSplitScreenMode */, false /* deferEnsuringVisibility */);
2305 return windowingMode != task.getWindowingMode();
2306 } finally {
2307 Binder.restoreCallingIdentity(ident);
2308 }
2309 }
2310 }
2311
2312 /**
2313 * Removes stacks in the input windowing modes from the system if they are of activity type
2314 * ACTIVITY_TYPE_STANDARD or ACTIVITY_TYPE_UNDEFINED
2315 */
2316 @Override
2317 public void removeStacksInWindowingModes(int[] windowingModes) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002318 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002319 "removeStacksInWindowingModes()");
2320
2321 synchronized (mGlobalLock) {
2322 final long ident = Binder.clearCallingIdentity();
2323 try {
2324 mStackSupervisor.removeStacksInWindowingModes(windowingModes);
2325 } finally {
2326 Binder.restoreCallingIdentity(ident);
2327 }
2328 }
2329 }
2330
2331 @Override
2332 public void removeStacksWithActivityTypes(int[] activityTypes) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002333 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale65ebd952018-04-25 15:41:44 -07002334 "removeStacksWithActivityTypes()");
2335
2336 synchronized (mGlobalLock) {
2337 final long ident = Binder.clearCallingIdentity();
2338 try {
2339 mStackSupervisor.removeStacksWithActivityTypes(activityTypes);
2340 } finally {
2341 Binder.restoreCallingIdentity(ident);
2342 }
2343 }
2344 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002345
2346 @Override
2347 public ParceledListSlice<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags,
2348 int userId) {
2349 final int callingUid = Binder.getCallingUid();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002350 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, "getRecentTasks");
2351 final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(),
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002352 callingUid);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002353 final boolean detailed = checkGetTasksPermission(
2354 android.Manifest.permission.GET_DETAILED_TASKS, Binder.getCallingPid(),
2355 UserHandle.getAppId(callingUid))
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002356 == PackageManager.PERMISSION_GRANTED;
2357
2358 synchronized (mGlobalLock) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002359 return mRecentTasks.getRecentTasks(maxNum, flags, allowed, detailed, userId,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002360 callingUid);
2361 }
2362 }
2363
2364 @Override
2365 public List<ActivityManager.StackInfo> getAllStackInfos() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002366 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getAllStackInfos()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002367 long ident = Binder.clearCallingIdentity();
2368 try {
2369 synchronized (mGlobalLock) {
2370 return mStackSupervisor.getAllStackInfosLocked();
2371 }
2372 } finally {
2373 Binder.restoreCallingIdentity(ident);
2374 }
2375 }
2376
2377 @Override
2378 public ActivityManager.StackInfo getStackInfo(int windowingMode, int activityType) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002379 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002380 long ident = Binder.clearCallingIdentity();
2381 try {
2382 synchronized (mGlobalLock) {
2383 return mStackSupervisor.getStackInfo(windowingMode, activityType);
2384 }
2385 } finally {
2386 Binder.restoreCallingIdentity(ident);
2387 }
2388 }
2389
2390 @Override
2391 public void cancelRecentsAnimation(boolean restoreHomeStackPosition) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002392 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "cancelRecentsAnimation()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002393 final long callingUid = Binder.getCallingUid();
2394 final long origId = Binder.clearCallingIdentity();
2395 try {
2396 synchronized (mGlobalLock) {
2397 // Cancel the recents animation synchronously (do not hold the WM lock)
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002398 mWindowManager.cancelRecentsAnimationSynchronously(restoreHomeStackPosition
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002399 ? REORDER_MOVE_TO_ORIGINAL_POSITION
2400 : REORDER_KEEP_IN_PLACE, "cancelRecentsAnimation/uid=" + callingUid);
2401 }
2402 } finally {
2403 Binder.restoreCallingIdentity(origId);
2404 }
2405 }
2406
2407 @Override
2408 public void startLockTaskModeByToken(IBinder token) {
2409 synchronized (mGlobalLock) {
2410 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
2411 if (r == null) {
2412 return;
2413 }
2414 startLockTaskModeLocked(r.getTask(), false /* isSystemCaller */);
2415 }
2416 }
2417
2418 @Override
2419 public void startSystemLockTaskMode(int taskId) throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002420 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startSystemLockTaskMode");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002421 // This makes inner call to look as if it was initiated by system.
2422 long ident = Binder.clearCallingIdentity();
2423 try {
2424 synchronized (mGlobalLock) {
2425 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2426
2427 // When starting lock task mode the stack must be in front and focused
2428 task.getStack().moveToFront("startSystemLockTaskMode");
2429 startLockTaskModeLocked(task, true /* isSystemCaller */);
2430 }
2431 } finally {
2432 Binder.restoreCallingIdentity(ident);
2433 }
2434 }
2435
2436 @Override
2437 public void stopLockTaskModeByToken(IBinder token) {
2438 synchronized (mGlobalLock) {
2439 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
2440 if (r == null) {
2441 return;
2442 }
2443 stopLockTaskModeInternal(r.getTask(), false /* isSystemCaller */);
2444 }
2445 }
2446
2447 /**
2448 * This API should be called by SystemUI only when user perform certain action to dismiss
2449 * lock task mode. We should only dismiss pinned lock task mode in this case.
2450 */
2451 @Override
2452 public void stopSystemLockTaskMode() throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002453 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "stopSystemLockTaskMode");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002454 stopLockTaskModeInternal(null, true /* isSystemCaller */);
2455 }
2456
2457 private void startLockTaskModeLocked(@Nullable TaskRecord task, boolean isSystemCaller) {
2458 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "startLockTaskModeLocked: " + task);
2459 if (task == null || task.mLockTaskAuth == LOCK_TASK_AUTH_DONT_LOCK) {
2460 return;
2461 }
2462
Andrii Kulian5f750bc2018-07-17 08:57:23 -07002463 final ActivityStack stack = mStackSupervisor.getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002464 if (stack == null || task != stack.topTask()) {
2465 throw new IllegalArgumentException("Invalid task, not in foreground");
2466 }
2467
2468 // {@code isSystemCaller} is used to distinguish whether this request is initiated by the
2469 // system or a specific app.
2470 // * System-initiated requests will only start the pinned mode (screen pinning)
2471 // * App-initiated requests
2472 // - will put the device in fully locked mode (LockTask), if the app is whitelisted
2473 // - will start the pinned mode, otherwise
2474 final int callingUid = Binder.getCallingUid();
2475 long ident = Binder.clearCallingIdentity();
2476 try {
2477 // When a task is locked, dismiss the pinned stack if it exists
2478 mStackSupervisor.removeStacksInWindowingModes(WINDOWING_MODE_PINNED);
2479
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002480 getLockTaskController().startLockTaskMode(task, isSystemCaller, callingUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002481 } finally {
2482 Binder.restoreCallingIdentity(ident);
2483 }
2484 }
2485
2486 private void stopLockTaskModeInternal(@Nullable TaskRecord task, boolean isSystemCaller) {
2487 final int callingUid = Binder.getCallingUid();
2488 long ident = Binder.clearCallingIdentity();
2489 try {
2490 synchronized (mGlobalLock) {
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002491 getLockTaskController().stopLockTaskMode(task, isSystemCaller, callingUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002492 }
2493 // Launch in-call UI if a call is ongoing. This is necessary to allow stopping the lock
2494 // task and jumping straight into a call in the case of emergency call back.
2495 TelecomManager tm = (TelecomManager) mContext.getSystemService(Context.TELECOM_SERVICE);
2496 if (tm != null) {
2497 tm.showInCallScreen(false);
2498 }
2499 } finally {
2500 Binder.restoreCallingIdentity(ident);
2501 }
2502 }
2503
2504 @Override
2505 public boolean isInLockTaskMode() {
2506 return getLockTaskModeState() != LOCK_TASK_MODE_NONE;
2507 }
2508
2509 @Override
2510 public int getLockTaskModeState() {
2511 synchronized (mGlobalLock) {
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07002512 return getLockTaskController().getLockTaskModeState();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002513 }
2514 }
2515
2516 @Override
2517 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) {
2518 synchronized (mGlobalLock) {
2519 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2520 if (r != null) {
2521 r.setTaskDescription(td);
2522 final TaskRecord task = r.getTask();
2523 task.updateTaskDescription();
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002524 mTaskChangeNotificationController.notifyTaskDescriptionChanged(task.taskId, td);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002525 }
2526 }
2527 }
2528
2529 @Override
2530 public Bundle getActivityOptions(IBinder token) {
2531 final long origId = Binder.clearCallingIdentity();
2532 try {
2533 synchronized (mGlobalLock) {
2534 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
2535 if (r != null) {
2536 final ActivityOptions activityOptions = r.takeOptionsLocked();
2537 return activityOptions == null ? null : activityOptions.toBundle();
2538 }
2539 return null;
2540 }
2541 } finally {
2542 Binder.restoreCallingIdentity(origId);
2543 }
2544 }
2545
2546 @Override
2547 public List<IBinder> getAppTasks(String callingPackage) {
2548 int callingUid = Binder.getCallingUid();
2549 long ident = Binder.clearCallingIdentity();
2550 try {
2551 synchronized (mGlobalLock) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002552 return mRecentTasks.getAppTasksList(callingUid, callingPackage);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002553 }
2554 } finally {
2555 Binder.restoreCallingIdentity(ident);
2556 }
2557 }
2558
2559 @Override
2560 public void finishVoiceTask(IVoiceInteractionSession session) {
2561 synchronized (mGlobalLock) {
2562 final long origId = Binder.clearCallingIdentity();
2563 try {
2564 // TODO: VI Consider treating local voice interactions and voice tasks
2565 // differently here
2566 mStackSupervisor.finishVoiceTask(session);
2567 } finally {
2568 Binder.restoreCallingIdentity(origId);
2569 }
2570 }
2571
2572 }
2573
2574 @Override
2575 public boolean isTopOfTask(IBinder token) {
2576 synchronized (mGlobalLock) {
2577 ActivityRecord r = ActivityRecord.isInStackLocked(token);
Riddle Hsu66b74a82018-07-26 00:20:12 +08002578 return r != null && r.getTask().getTopActivity() == r;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002579 }
2580 }
2581
2582 @Override
2583 public void notifyLaunchTaskBehindComplete(IBinder token) {
2584 mStackSupervisor.scheduleLaunchTaskBehindComplete(token);
2585 }
2586
2587 @Override
2588 public void notifyEnterAnimationComplete(IBinder token) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002589 mH.post(() -> {
2590 synchronized (mGlobalLock) {
2591 ActivityRecord r = ActivityRecord.forTokenLocked(token);
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07002592 if (r != null && r.attachedToProcess()) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002593 try {
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07002594 r.app.getThread().scheduleEnterAnimationComplete(r.appToken);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002595 } catch (RemoteException e) {
2596 }
2597 }
2598 }
2599
2600 });
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002601 }
2602
2603 /** Called from an app when assist data is ready. */
2604 @Override
2605 public void reportAssistContextExtras(IBinder token, Bundle extras, AssistStructure structure,
2606 AssistContent content, Uri referrer) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002607 PendingAssistExtras pae = (PendingAssistExtras) token;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002608 synchronized (pae) {
2609 pae.result = extras;
2610 pae.structure = structure;
2611 pae.content = content;
2612 if (referrer != null) {
2613 pae.extras.putParcelable(Intent.EXTRA_REFERRER, referrer);
2614 }
2615 if (structure != null) {
2616 structure.setHomeActivity(pae.isHome);
2617 }
2618 pae.haveResult = true;
2619 pae.notifyAll();
2620 if (pae.intent == null && pae.receiver == null) {
2621 // Caller is just waiting for the result.
2622 return;
2623 }
2624 }
2625 // We are now ready to launch the assist activity.
2626 IAssistDataReceiver sendReceiver = null;
2627 Bundle sendBundle = null;
2628 synchronized (mGlobalLock) {
2629 buildAssistBundleLocked(pae, extras);
2630 boolean exists = mPendingAssistExtras.remove(pae);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002631 mUiHandler.removeCallbacks(pae);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002632 if (!exists) {
2633 // Timed out.
2634 return;
2635 }
2636
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002637 if ((sendReceiver = pae.receiver) != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002638 // Caller wants result sent back to them.
2639 sendBundle = new Bundle();
2640 sendBundle.putBundle(ASSIST_KEY_DATA, pae.extras);
2641 sendBundle.putParcelable(ASSIST_KEY_STRUCTURE, pae.structure);
2642 sendBundle.putParcelable(ASSIST_KEY_CONTENT, pae.content);
2643 sendBundle.putBundle(ASSIST_KEY_RECEIVER_EXTRAS, pae.receiverExtras);
2644 }
2645 }
2646 if (sendReceiver != null) {
2647 try {
2648 sendReceiver.onHandleAssistData(sendBundle);
2649 } catch (RemoteException e) {
2650 }
2651 return;
2652 }
2653
2654 final long ident = Binder.clearCallingIdentity();
2655 try {
2656 if (TextUtils.equals(pae.intent.getAction(),
2657 android.service.voice.VoiceInteractionService.SERVICE_INTERFACE)) {
2658 pae.intent.putExtras(pae.extras);
2659 mContext.startServiceAsUser(pae.intent, new UserHandle(pae.userHandle));
2660 } else {
2661 pae.intent.replaceExtras(pae.extras);
2662 pae.intent.setFlags(FLAG_ACTIVITY_NEW_TASK
2663 | Intent.FLAG_ACTIVITY_SINGLE_TOP
2664 | Intent.FLAG_ACTIVITY_CLEAR_TOP);
Wale Ogunwale31913b52018-10-13 08:29:31 -07002665 mInternal.closeSystemDialogs("assist");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002666
2667 try {
2668 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle));
2669 } catch (ActivityNotFoundException e) {
2670 Slog.w(TAG, "No activity to handle assist action.", e);
2671 }
2672 }
2673 } finally {
2674 Binder.restoreCallingIdentity(ident);
2675 }
2676 }
2677
2678 @Override
2679 public int addAppTask(IBinder activityToken, Intent intent,
2680 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException {
2681 final int callingUid = Binder.getCallingUid();
2682 final long callingIdent = Binder.clearCallingIdentity();
2683
2684 try {
2685 synchronized (mGlobalLock) {
2686 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
2687 if (r == null) {
2688 throw new IllegalArgumentException("Activity does not exist; token="
2689 + activityToken);
2690 }
2691 ComponentName comp = intent.getComponent();
2692 if (comp == null) {
2693 throw new IllegalArgumentException("Intent " + intent
2694 + " must specify explicit component");
2695 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002696 if (thumbnail.getWidth() != mThumbnailWidth
2697 || thumbnail.getHeight() != mThumbnailHeight) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002698 throw new IllegalArgumentException("Bad thumbnail size: got "
2699 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require "
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002700 + mThumbnailWidth + "x" + mThumbnailHeight);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002701 }
2702 if (intent.getSelector() != null) {
2703 intent.setSelector(null);
2704 }
2705 if (intent.getSourceBounds() != null) {
2706 intent.setSourceBounds(null);
2707 }
2708 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) {
2709 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) {
2710 // The caller has added this as an auto-remove task... that makes no
2711 // sense, so turn off auto-remove.
2712 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS);
2713 }
2714 }
2715 final ActivityInfo ainfo = AppGlobals.getPackageManager().getActivityInfo(comp,
2716 STOCK_PM_FLAGS, UserHandle.getUserId(callingUid));
2717 if (ainfo.applicationInfo.uid != callingUid) {
2718 throw new SecurityException(
2719 "Can't add task for another application: target uid="
2720 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid);
2721 }
2722
2723 final ActivityStack stack = r.getStack();
2724 final TaskRecord task = stack.createTaskRecord(
2725 mStackSupervisor.getNextTaskIdForUserLocked(r.userId), ainfo, intent,
2726 null /* voiceSession */, null /* voiceInteractor */, !ON_TOP);
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002727 if (!mRecentTasks.addToBottom(task)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002728 // The app has too many tasks already and we can't add any more
2729 stack.removeTask(task, "addAppTask", REMOVE_TASK_MODE_DESTROYING);
2730 return INVALID_TASK_ID;
2731 }
2732 task.lastTaskDescription.copyFrom(description);
2733
2734 // TODO: Send the thumbnail to WM to store it.
2735
2736 return task.taskId;
2737 }
2738 } finally {
2739 Binder.restoreCallingIdentity(callingIdent);
2740 }
2741 }
2742
2743 @Override
2744 public Point getAppTaskThumbnailSize() {
2745 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002746 return new Point(mThumbnailWidth, mThumbnailHeight);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002747 }
2748 }
2749
2750 @Override
2751 public void setTaskResizeable(int taskId, int resizeableMode) {
2752 synchronized (mGlobalLock) {
2753 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(
2754 taskId, MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
2755 if (task == null) {
2756 Slog.w(TAG, "setTaskResizeable: taskId=" + taskId + " not found");
2757 return;
2758 }
2759 task.setResizeMode(resizeableMode);
2760 }
2761 }
2762
2763 @Override
2764 public void resizeTask(int taskId, Rect bounds, int resizeMode) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002765 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeTask()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002766 long ident = Binder.clearCallingIdentity();
2767 try {
2768 synchronized (mGlobalLock) {
2769 TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
2770 if (task == null) {
2771 Slog.w(TAG, "resizeTask: taskId=" + taskId + " not found");
2772 return;
2773 }
2774 // Place the task in the right stack if it isn't there already based on
2775 // the requested bounds.
2776 // The stack transition logic is:
2777 // - a null bounds on a freeform task moves that task to fullscreen
2778 // - a non-null bounds on a non-freeform (fullscreen OR docked) task moves
2779 // that task to freeform
2780 // - otherwise the task is not moved
2781 ActivityStack stack = task.getStack();
2782 if (!task.getWindowConfiguration().canResizeTask()) {
2783 throw new IllegalArgumentException("resizeTask not allowed on task=" + task);
2784 }
2785 if (bounds == null && stack.getWindowingMode() == WINDOWING_MODE_FREEFORM) {
2786 stack = stack.getDisplay().getOrCreateStack(
2787 WINDOWING_MODE_FULLSCREEN, stack.getActivityType(), ON_TOP);
2788 } else if (bounds != null && stack.getWindowingMode() != WINDOWING_MODE_FREEFORM) {
2789 stack = stack.getDisplay().getOrCreateStack(
2790 WINDOWING_MODE_FREEFORM, stack.getActivityType(), ON_TOP);
2791 }
2792
2793 // Reparent the task to the right stack if necessary
2794 boolean preserveWindow = (resizeMode & RESIZE_MODE_PRESERVE_WINDOW) != 0;
2795 if (stack != task.getStack()) {
2796 // Defer resume until the task is resized below
2797 task.reparent(stack, ON_TOP, REPARENT_KEEP_STACK_AT_FRONT, ANIMATE,
2798 DEFER_RESUME, "resizeTask");
2799 preserveWindow = false;
2800 }
2801
2802 // After reparenting (which only resizes the task to the stack bounds), resize the
2803 // task to the actual bounds provided
2804 task.resize(bounds, resizeMode, preserveWindow, !DEFER_RESUME);
2805 }
2806 } finally {
2807 Binder.restoreCallingIdentity(ident);
2808 }
2809 }
2810
2811 @Override
2812 public boolean releaseActivityInstance(IBinder token) {
2813 synchronized (mGlobalLock) {
2814 final long origId = Binder.clearCallingIdentity();
2815 try {
2816 ActivityRecord r = ActivityRecord.isInStackLocked(token);
2817 if (r == null) {
2818 return false;
2819 }
2820 return r.getStack().safelyDestroyActivityLocked(r, "app-req");
2821 } finally {
2822 Binder.restoreCallingIdentity(origId);
2823 }
2824 }
2825 }
2826
2827 @Override
2828 public void releaseSomeActivities(IApplicationThread appInt) {
2829 synchronized (mGlobalLock) {
2830 final long origId = Binder.clearCallingIdentity();
2831 try {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07002832 final WindowProcessController app = getProcessController(appInt);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002833 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem");
2834 } finally {
2835 Binder.restoreCallingIdentity(origId);
2836 }
2837 }
2838 }
2839
2840 @Override
2841 public void setLockScreenShown(boolean keyguardShowing, boolean aodShowing,
2842 int secondaryDisplayShowing) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002843 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER)
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002844 != PackageManager.PERMISSION_GRANTED) {
2845 throw new SecurityException("Requires permission "
2846 + android.Manifest.permission.DEVICE_POWER);
2847 }
2848
2849 synchronized (mGlobalLock) {
2850 long ident = Binder.clearCallingIdentity();
2851 if (mKeyguardShown != keyguardShowing) {
2852 mKeyguardShown = keyguardShowing;
Wale Ogunwale342fbe92018-10-09 08:44:10 -07002853 final Message msg = PooledLambda.obtainMessage(
2854 ActivityManagerInternal::reportCurKeyguardUsageEvent, mAmInternal,
2855 keyguardShowing);
2856 mH.sendMessage(msg);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002857 }
2858 try {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002859 mKeyguardController.setKeyguardShown(keyguardShowing, aodShowing,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002860 secondaryDisplayShowing);
2861 } finally {
2862 Binder.restoreCallingIdentity(ident);
2863 }
2864 }
2865
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002866 mH.post(() -> {
2867 for (int i = mScreenObservers.size() - 1; i >= 0; i--) {
2868 mScreenObservers.get(i).onKeyguardStateChanged(keyguardShowing);
2869 }
2870 });
2871 }
2872
2873 void onScreenAwakeChanged(boolean isAwake) {
2874 mH.post(() -> {
2875 for (int i = mScreenObservers.size() - 1; i >= 0; i--) {
2876 mScreenObservers.get(i).onAwakeStateChanged(isAwake);
2877 }
2878 });
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002879 }
2880
2881 @Override
2882 public Bitmap getTaskDescriptionIcon(String filePath, int userId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002883 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
2884 userId, "getTaskDescriptionIcon");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002885
2886 final File passedIconFile = new File(filePath);
2887 final File legitIconFile = new File(TaskPersister.getUserImagesDir(userId),
2888 passedIconFile.getName());
2889 if (!legitIconFile.getPath().equals(filePath)
2890 || !filePath.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) {
2891 throw new IllegalArgumentException("Bad file path: " + filePath
2892 + " passed for userId " + userId);
2893 }
Wale Ogunwale16e505a2018-05-07 15:00:49 -07002894 return mRecentTasks.getTaskDescriptionIcon(filePath);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002895 }
2896
2897 @Override
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002898 public void startInPlaceAnimationOnFrontMostApplication(Bundle opts) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002899 final SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(opts);
2900 final ActivityOptions activityOptions = safeOptions != null
2901 ? safeOptions.getOptions(mStackSupervisor)
2902 : null;
2903 if (activityOptions == null
2904 || activityOptions.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE
2905 || activityOptions.getCustomInPlaceResId() == 0) {
2906 throw new IllegalArgumentException("Expected in-place ActivityOption " +
2907 "with valid animation");
2908 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002909 mWindowManager.prepareAppTransition(TRANSIT_TASK_IN_PLACE, false);
2910 mWindowManager.overridePendingAppTransitionInPlace(activityOptions.getPackageName(),
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002911 activityOptions.getCustomInPlaceResId());
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002912 mWindowManager.executeAppTransition();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002913 }
2914
2915 @Override
2916 public void removeStack(int stackId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002917 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "removeStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002918 synchronized (mGlobalLock) {
2919 final long ident = Binder.clearCallingIdentity();
2920 try {
2921 final ActivityStack stack = mStackSupervisor.getStack(stackId);
2922 if (stack == null) {
2923 Slog.w(TAG, "removeStack: No stack with id=" + stackId);
2924 return;
2925 }
2926 if (!stack.isActivityTypeStandardOrUndefined()) {
2927 throw new IllegalArgumentException(
2928 "Removing non-standard stack is not allowed.");
2929 }
2930 mStackSupervisor.removeStack(stack);
2931 } finally {
2932 Binder.restoreCallingIdentity(ident);
2933 }
2934 }
2935 }
2936
2937 @Override
2938 public void moveStackToDisplay(int stackId, int displayId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002939 mAmInternal.enforceCallingPermission(INTERNAL_SYSTEM_WINDOW, "moveStackToDisplay()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002940
2941 synchronized (mGlobalLock) {
2942 final long ident = Binder.clearCallingIdentity();
2943 try {
2944 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveStackToDisplay: moving stackId=" + stackId
2945 + " to displayId=" + displayId);
2946 mStackSupervisor.moveStackToDisplayLocked(stackId, displayId, ON_TOP);
2947 } finally {
2948 Binder.restoreCallingIdentity(ident);
2949 }
2950 }
2951 }
2952
2953 @Override
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002954 public void exitFreeformMode(IBinder token) {
2955 synchronized (mGlobalLock) {
2956 long ident = Binder.clearCallingIdentity();
2957 try {
2958 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
2959 if (r == null) {
2960 throw new IllegalArgumentException(
2961 "exitFreeformMode: No activity record matching token=" + token);
2962 }
2963
2964 final ActivityStack stack = r.getStack();
2965 if (stack == null || !stack.inFreeformWindowingMode()) {
2966 throw new IllegalStateException(
2967 "exitFreeformMode: You can only go fullscreen from freeform.");
2968 }
2969
2970 stack.setWindowingMode(WINDOWING_MODE_FULLSCREEN);
2971 } finally {
2972 Binder.restoreCallingIdentity(ident);
2973 }
2974 }
2975 }
2976
2977 /** Sets the task stack listener that gets callbacks when a task stack changes. */
2978 @Override
2979 public void registerTaskStackListener(ITaskStackListener listener) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002980 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002981 "registerTaskStackListener()");
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002982 mTaskChangeNotificationController.registerTaskStackListener(listener);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002983 }
2984
2985 /** Unregister a task stack listener so that it stops receiving callbacks. */
2986 @Override
2987 public void unregisterTaskStackListener(ITaskStackListener listener) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07002988 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002989 "unregisterTaskStackListener()");
Wale Ogunwaled0412b32018-05-08 09:25:50 -07002990 mTaskChangeNotificationController.unregisterTaskStackListener(listener);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002991 }
2992
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07002993 @Override
2994 public boolean requestAssistContextExtras(int requestType, IAssistDataReceiver receiver,
2995 Bundle receiverExtras, IBinder activityToken, boolean focused, boolean newSessionId) {
2996 return enqueueAssistContext(requestType, null, null, receiver, receiverExtras,
2997 activityToken, focused, newSessionId, UserHandle.getCallingUserId(), null,
2998 PENDING_ASSIST_EXTRAS_LONG_TIMEOUT, 0) != null;
2999 }
3000
3001 @Override
3002 public boolean requestAutofillData(IAssistDataReceiver receiver, Bundle receiverExtras,
3003 IBinder activityToken, int flags) {
3004 return enqueueAssistContext(ActivityManager.ASSIST_CONTEXT_AUTOFILL, null, null,
3005 receiver, receiverExtras, activityToken, true, true, UserHandle.getCallingUserId(),
3006 null, PENDING_AUTOFILL_ASSIST_STRUCTURE_TIMEOUT, flags) != null;
3007 }
3008
3009 @Override
3010 public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle,
3011 Bundle args) {
3012 return enqueueAssistContext(requestType, intent, hint, null, null, null,
3013 true /* focused */, true /* newSessionId */, userHandle, args,
3014 PENDING_ASSIST_EXTRAS_TIMEOUT, 0) != null;
3015 }
3016
3017 @Override
3018 public Bundle getAssistContextExtras(int requestType) {
3019 PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, null,
3020 null, null, true /* focused */, true /* newSessionId */,
3021 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_TIMEOUT, 0);
3022 if (pae == null) {
3023 return null;
3024 }
3025 synchronized (pae) {
3026 while (!pae.haveResult) {
3027 try {
3028 pae.wait();
3029 } catch (InterruptedException e) {
3030 }
3031 }
3032 }
3033 synchronized (mGlobalLock) {
3034 buildAssistBundleLocked(pae, pae.result);
3035 mPendingAssistExtras.remove(pae);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003036 mUiHandler.removeCallbacks(pae);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003037 }
3038 return pae.extras;
3039 }
3040
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003041 /**
3042 * Binder IPC calls go through the public entry point.
3043 * This can be called with or without the global lock held.
3044 */
3045 private static int checkCallingPermission(String permission) {
3046 return checkPermission(
3047 permission, Binder.getCallingPid(), UserHandle.getAppId(Binder.getCallingUid()));
3048 }
3049
3050 /** This can be called with or without the global lock held. */
Wale Ogunwale214f3482018-10-04 11:00:47 -07003051 private void enforceCallerIsRecentsOrHasPermission(String permission, String func) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003052 if (!getRecentTasks().isCallerRecents(Binder.getCallingUid())) {
3053 mAmInternal.enforceCallingPermission(permission, func);
3054 }
3055 }
3056
3057 @VisibleForTesting
3058 int checkGetTasksPermission(String permission, int pid, int uid) {
3059 return checkPermission(permission, pid, uid);
3060 }
3061
3062 static int checkPermission(String permission, int pid, int uid) {
3063 if (permission == null) {
3064 return PackageManager.PERMISSION_DENIED;
3065 }
3066 return checkComponentPermission(permission, pid, uid, -1, true);
3067 }
3068
Wale Ogunwale214f3482018-10-04 11:00:47 -07003069 public static int checkComponentPermission(String permission, int pid, int uid,
3070 int owningUid, boolean exported) {
3071 return ActivityManagerService.checkComponentPermission(
3072 permission, pid, uid, owningUid, exported);
3073 }
3074
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003075 boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) {
3076 if (getRecentTasks().isCallerRecents(callingUid)) {
3077 // Always allow the recents component to get tasks
3078 return true;
3079 }
3080
3081 boolean allowed = checkGetTasksPermission(android.Manifest.permission.REAL_GET_TASKS,
3082 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED;
3083 if (!allowed) {
3084 if (checkGetTasksPermission(android.Manifest.permission.GET_TASKS,
3085 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) {
3086 // Temporary compatibility: some existing apps on the system image may
3087 // still be requesting the old permission and not switched to the new
3088 // one; if so, we'll still allow them full access. This means we need
3089 // to see if they are holding the old permission and are a system app.
3090 try {
3091 if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) {
3092 allowed = true;
3093 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid
3094 + " is using old GET_TASKS but privileged; allowing");
3095 }
3096 } catch (RemoteException e) {
3097 }
3098 }
3099 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid
3100 + " does not hold REAL_GET_TASKS; limiting output");
3101 }
3102 return allowed;
3103 }
3104
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003105 private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint,
3106 IAssistDataReceiver receiver, Bundle receiverExtras, IBinder activityToken,
3107 boolean focused, boolean newSessionId, int userHandle, Bundle args, long timeout,
3108 int flags) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003109 mAmInternal.enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003110 "enqueueAssistContext()");
3111
3112 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003113 ActivityRecord activity = getTopDisplayFocusedStack().getTopActivity();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003114 if (activity == null) {
3115 Slog.w(TAG, "getAssistContextExtras failed: no top activity");
3116 return null;
3117 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003118 if (!activity.attachedToProcess()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003119 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity);
3120 return null;
3121 }
3122 if (focused) {
3123 if (activityToken != null) {
3124 ActivityRecord caller = ActivityRecord.forTokenLocked(activityToken);
3125 if (activity != caller) {
3126 Slog.w(TAG, "enqueueAssistContext failed: caller " + caller
3127 + " is not current top " + activity);
3128 return null;
3129 }
3130 }
3131 } else {
3132 activity = ActivityRecord.forTokenLocked(activityToken);
3133 if (activity == null) {
3134 Slog.w(TAG, "enqueueAssistContext failed: activity for token=" + activityToken
3135 + " couldn't be found");
3136 return null;
3137 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003138 if (!activity.attachedToProcess()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003139 Slog.w(TAG, "enqueueAssistContext failed: no process for " + activity);
3140 return null;
3141 }
3142 }
3143
3144 PendingAssistExtras pae;
3145 Bundle extras = new Bundle();
3146 if (args != null) {
3147 extras.putAll(args);
3148 }
3149 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName);
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003150 extras.putInt(Intent.EXTRA_ASSIST_UID, activity.app.mUid);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003151
3152 pae = new PendingAssistExtras(activity, extras, intent, hint, receiver, receiverExtras,
3153 userHandle);
3154 pae.isHome = activity.isActivityTypeHome();
3155
3156 // Increment the sessionId if necessary
3157 if (newSessionId) {
3158 mViSessionId++;
3159 }
3160 try {
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07003161 activity.app.getThread().requestAssistContextExtras(activity.appToken, pae,
3162 requestType, mViSessionId, flags);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003163 mPendingAssistExtras.add(pae);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003164 mUiHandler.postDelayed(pae, timeout);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003165 } catch (RemoteException e) {
3166 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity);
3167 return null;
3168 }
3169 return pae;
3170 }
3171 }
3172
3173 private void buildAssistBundleLocked(PendingAssistExtras pae, Bundle result) {
3174 if (result != null) {
3175 pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, result);
3176 }
3177 if (pae.hint != null) {
3178 pae.extras.putBoolean(pae.hint, true);
3179 }
3180 }
3181
3182 private void pendingAssistExtrasTimedOut(PendingAssistExtras pae) {
3183 IAssistDataReceiver receiver;
3184 synchronized (mGlobalLock) {
3185 mPendingAssistExtras.remove(pae);
3186 receiver = pae.receiver;
3187 }
3188 if (receiver != null) {
3189 // Caller wants result sent back to them.
3190 Bundle sendBundle = new Bundle();
3191 // At least return the receiver extras
3192 sendBundle.putBundle(ASSIST_KEY_RECEIVER_EXTRAS, pae.receiverExtras);
3193 try {
3194 pae.receiver.onHandleAssistData(sendBundle);
3195 } catch (RemoteException e) {
3196 }
3197 }
3198 }
3199
3200 public class PendingAssistExtras extends Binder implements Runnable {
3201 public final ActivityRecord activity;
3202 public boolean isHome;
3203 public final Bundle extras;
3204 public final Intent intent;
3205 public final String hint;
3206 public final IAssistDataReceiver receiver;
3207 public final int userHandle;
3208 public boolean haveResult = false;
3209 public Bundle result = null;
3210 public AssistStructure structure = null;
3211 public AssistContent content = null;
3212 public Bundle receiverExtras;
3213
3214 public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent,
3215 String _hint, IAssistDataReceiver _receiver, Bundle _receiverExtras,
3216 int _userHandle) {
3217 activity = _activity;
3218 extras = _extras;
3219 intent = _intent;
3220 hint = _hint;
3221 receiver = _receiver;
3222 receiverExtras = _receiverExtras;
3223 userHandle = _userHandle;
3224 }
3225
3226 @Override
3227 public void run() {
3228 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity);
3229 synchronized (this) {
3230 haveResult = true;
3231 notifyAll();
3232 }
3233 pendingAssistExtrasTimedOut(this);
3234 }
3235 }
3236
3237 @Override
3238 public boolean isAssistDataAllowedOnCurrentActivity() {
3239 int userId;
3240 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003241 final ActivityStack focusedStack = getTopDisplayFocusedStack();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003242 if (focusedStack == null || focusedStack.isActivityTypeAssistant()) {
3243 return false;
3244 }
3245
3246 final ActivityRecord activity = focusedStack.getTopActivity();
3247 if (activity == null) {
3248 return false;
3249 }
3250 userId = activity.userId;
3251 }
3252 return !DevicePolicyCache.getInstance().getScreenCaptureDisabled(userId);
3253 }
3254
3255 @Override
3256 public boolean showAssistFromActivity(IBinder token, Bundle args) {
3257 long ident = Binder.clearCallingIdentity();
3258 try {
3259 synchronized (mGlobalLock) {
3260 ActivityRecord caller = ActivityRecord.forTokenLocked(token);
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003261 ActivityRecord top = getTopDisplayFocusedStack().getTopActivity();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003262 if (top != caller) {
3263 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller
3264 + " is not current top " + top);
3265 return false;
3266 }
3267 if (!top.nowVisible) {
3268 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller
3269 + " is not visible");
3270 return false;
3271 }
3272 }
3273 return mAssistUtils.showSessionForActiveService(args, SHOW_SOURCE_APPLICATION, null,
3274 token);
3275 } finally {
3276 Binder.restoreCallingIdentity(ident);
3277 }
3278 }
3279
3280 @Override
3281 public boolean isRootVoiceInteraction(IBinder token) {
3282 synchronized (mGlobalLock) {
3283 ActivityRecord r = ActivityRecord.isInStackLocked(token);
3284 if (r == null) {
3285 return false;
3286 }
3287 return r.rootVoiceInteraction;
3288 }
3289 }
3290
Wale Ogunwalef6733932018-06-27 05:14:34 -07003291 private void onLocalVoiceInteractionStartedLocked(IBinder activity,
3292 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
3293 ActivityRecord activityToCallback = ActivityRecord.forTokenLocked(activity);
3294 if (activityToCallback == null) return;
3295 activityToCallback.setVoiceSessionLocked(voiceSession);
3296
3297 // Inform the activity
3298 try {
3299 activityToCallback.app.getThread().scheduleLocalVoiceInteractionStarted(activity,
3300 voiceInteractor);
3301 long token = Binder.clearCallingIdentity();
3302 try {
3303 startRunningVoiceLocked(voiceSession, activityToCallback.appInfo.uid);
3304 } finally {
3305 Binder.restoreCallingIdentity(token);
3306 }
3307 // TODO: VI Should we cache the activity so that it's easier to find later
3308 // rather than scan through all the stacks and activities?
3309 } catch (RemoteException re) {
3310 activityToCallback.clearVoiceSessionLocked();
3311 // TODO: VI Should this terminate the voice session?
3312 }
3313 }
3314
3315 private void startRunningVoiceLocked(IVoiceInteractionSession session, int targetUid) {
3316 Slog.d(TAG, "<<< startRunningVoiceLocked()");
3317 mVoiceWakeLock.setWorkSource(new WorkSource(targetUid));
3318 if (mRunningVoice == null || mRunningVoice.asBinder() != session.asBinder()) {
3319 boolean wasRunningVoice = mRunningVoice != null;
3320 mRunningVoice = session;
3321 if (!wasRunningVoice) {
3322 mVoiceWakeLock.acquire();
3323 updateSleepIfNeededLocked();
3324 }
3325 }
3326 }
3327
3328 void finishRunningVoiceLocked() {
3329 if (mRunningVoice != null) {
3330 mRunningVoice = null;
3331 mVoiceWakeLock.release();
3332 updateSleepIfNeededLocked();
3333 }
3334 }
3335
3336 @Override
3337 public void setVoiceKeepAwake(IVoiceInteractionSession session, boolean keepAwake) {
3338 synchronized (mGlobalLock) {
3339 if (mRunningVoice != null && mRunningVoice.asBinder() == session.asBinder()) {
3340 if (keepAwake) {
3341 mVoiceWakeLock.acquire();
3342 } else {
3343 mVoiceWakeLock.release();
3344 }
3345 }
3346 }
3347 }
3348
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003349 @Override
3350 public ComponentName getActivityClassForToken(IBinder token) {
3351 synchronized (mGlobalLock) {
3352 ActivityRecord r = ActivityRecord.isInStackLocked(token);
3353 if (r == null) {
3354 return null;
3355 }
3356 return r.intent.getComponent();
3357 }
3358 }
3359
3360 @Override
3361 public String getPackageForToken(IBinder token) {
3362 synchronized (mGlobalLock) {
3363 ActivityRecord r = ActivityRecord.isInStackLocked(token);
3364 if (r == null) {
3365 return null;
3366 }
3367 return r.packageName;
3368 }
3369 }
3370
3371 @Override
3372 public void showLockTaskEscapeMessage(IBinder token) {
3373 synchronized (mGlobalLock) {
3374 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
3375 if (r == null) {
3376 return;
3377 }
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07003378 getLockTaskController().showLockTaskToast();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003379 }
3380 }
3381
3382 @Override
3383 public void keyguardGoingAway(int flags) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003384 enforceNotIsolatedCaller("keyguardGoingAway");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003385 final long token = Binder.clearCallingIdentity();
3386 try {
3387 synchronized (mGlobalLock) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003388 mKeyguardController.keyguardGoingAway(flags);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003389 }
3390 } finally {
3391 Binder.restoreCallingIdentity(token);
3392 }
3393 }
3394
3395 /**
3396 * Try to place task to provided position. The final position might be different depending on
3397 * current user and stacks state. The task will be moved to target stack if it's currently in
3398 * different stack.
3399 */
3400 @Override
3401 public void positionTaskInStack(int taskId, int stackId, int position) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003402 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "positionTaskInStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003403 synchronized (mGlobalLock) {
3404 long ident = Binder.clearCallingIdentity();
3405 try {
3406 if (DEBUG_STACK) Slog.d(TAG_STACK, "positionTaskInStack: positioning task="
3407 + taskId + " in stackId=" + stackId + " at position=" + position);
3408 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
3409 if (task == null) {
3410 throw new IllegalArgumentException("positionTaskInStack: no task for id="
3411 + taskId);
3412 }
3413
3414 final ActivityStack stack = mStackSupervisor.getStack(stackId);
3415
3416 if (stack == null) {
3417 throw new IllegalArgumentException("positionTaskInStack: no stack for id="
3418 + stackId);
3419 }
3420 if (!stack.isActivityTypeStandardOrUndefined()) {
3421 throw new IllegalArgumentException("positionTaskInStack: Attempt to change"
3422 + " the position of task " + taskId + " in/to non-standard stack");
3423 }
3424
3425 // TODO: Have the callers of this API call a separate reparent method if that is
3426 // what they intended to do vs. having this method also do reparenting.
3427 if (task.getStack() == stack) {
3428 // Change position in current stack.
3429 stack.positionChildAt(task, position);
3430 } else {
3431 // Reparent to new stack.
3432 task.reparent(stack, position, REPARENT_LEAVE_STACK_IN_PLACE, !ANIMATE,
3433 !DEFER_RESUME, "positionTaskInStack");
3434 }
3435 } finally {
3436 Binder.restoreCallingIdentity(ident);
3437 }
3438 }
3439 }
3440
3441 @Override
3442 public void reportSizeConfigurations(IBinder token, int[] horizontalSizeConfiguration,
3443 int[] verticalSizeConfigurations, int[] smallestSizeConfigurations) {
3444 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Report configuration: " + token + " "
3445 + horizontalSizeConfiguration + " " + verticalSizeConfigurations);
3446 synchronized (mGlobalLock) {
3447 ActivityRecord record = ActivityRecord.isInStackLocked(token);
3448 if (record == null) {
3449 throw new IllegalArgumentException("reportSizeConfigurations: ActivityRecord not "
3450 + "found for: " + token);
3451 }
3452 record.setSizeConfigurations(horizontalSizeConfiguration,
3453 verticalSizeConfigurations, smallestSizeConfigurations);
3454 }
3455 }
3456
3457 /**
3458 * Dismisses split-screen multi-window mode.
3459 * @param toTop If true the current primary split-screen stack will be placed or left on top.
3460 */
3461 @Override
3462 public void dismissSplitScreenMode(boolean toTop) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003463 enforceCallerIsRecentsOrHasPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003464 MANAGE_ACTIVITY_STACKS, "dismissSplitScreenMode()");
3465 final long ident = Binder.clearCallingIdentity();
3466 try {
3467 synchronized (mGlobalLock) {
3468 final ActivityStack stack =
3469 mStackSupervisor.getDefaultDisplay().getSplitScreenPrimaryStack();
3470 if (stack == null) {
3471 Slog.w(TAG, "dismissSplitScreenMode: primary split-screen stack not found.");
3472 return;
3473 }
3474
3475 if (toTop) {
3476 // Caller wants the current split-screen primary stack to be the top stack after
3477 // it goes fullscreen, so move it to the front.
3478 stack.moveToFront("dismissSplitScreenMode");
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003479 } else if (mStackSupervisor.isTopDisplayFocusedStack(stack)) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003480 // In this case the current split-screen primary stack shouldn't be the top
3481 // stack after it goes fullscreen, but it current has focus, so we move the
3482 // focus to the top-most split-screen secondary stack next to it.
3483 final ActivityStack otherStack = stack.getDisplay().getTopStackInWindowingMode(
3484 WINDOWING_MODE_SPLIT_SCREEN_SECONDARY);
3485 if (otherStack != null) {
3486 otherStack.moveToFront("dismissSplitScreenMode_other");
3487 }
3488 }
3489
Evan Rosky10475742018-09-05 19:02:48 -07003490 stack.setWindowingMode(WINDOWING_MODE_UNDEFINED);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003491 }
3492 } finally {
3493 Binder.restoreCallingIdentity(ident);
3494 }
3495 }
3496
3497 /**
3498 * Dismisses Pip
3499 * @param animate True if the dismissal should be animated.
3500 * @param animationDuration The duration of the resize animation in milliseconds or -1 if the
3501 * default animation duration should be used.
3502 */
3503 @Override
3504 public void dismissPip(boolean animate, int animationDuration) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003505 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "dismissPip()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003506 final long ident = Binder.clearCallingIdentity();
3507 try {
3508 synchronized (mGlobalLock) {
3509 final PinnedActivityStack stack =
3510 mStackSupervisor.getDefaultDisplay().getPinnedStack();
3511 if (stack == null) {
3512 Slog.w(TAG, "dismissPip: pinned stack not found.");
3513 return;
3514 }
3515 if (stack.getWindowingMode() != WINDOWING_MODE_PINNED) {
3516 throw new IllegalArgumentException("Stack: " + stack
3517 + " doesn't support animated resize.");
3518 }
3519 if (animate) {
3520 stack.animateResizePinnedStack(null /* sourceHintBounds */,
3521 null /* destBounds */, animationDuration, false /* fromFullscreen */);
3522 } else {
3523 mStackSupervisor.moveTasksToFullscreenStackLocked(stack, true /* onTop */);
3524 }
3525 }
3526 } finally {
3527 Binder.restoreCallingIdentity(ident);
3528 }
3529 }
3530
3531 @Override
3532 public void suppressResizeConfigChanges(boolean suppress) throws RemoteException {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003533 mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "suppressResizeConfigChanges()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003534 synchronized (mGlobalLock) {
3535 mSuppressResizeConfigChanges = suppress;
3536 }
3537 }
3538
3539 /**
3540 * NOTE: For the pinned stack, this method is usually called after the bounds animation has
3541 * animated the stack to the fullscreen, but can also be called if we are relaunching an
3542 * activity and clearing the task at the same time.
3543 */
3544 @Override
3545 // TODO: API should just be about changing windowing modes...
3546 public void moveTasksToFullscreenStack(int fromStackId, boolean onTop) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003547 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003548 "moveTasksToFullscreenStack()");
3549 synchronized (mGlobalLock) {
3550 final long origId = Binder.clearCallingIdentity();
3551 try {
3552 final ActivityStack stack = mStackSupervisor.getStack(fromStackId);
3553 if (stack != null){
3554 if (!stack.isActivityTypeStandardOrUndefined()) {
3555 throw new IllegalArgumentException(
3556 "You can't move tasks from non-standard stacks.");
3557 }
3558 mStackSupervisor.moveTasksToFullscreenStackLocked(stack, onTop);
3559 }
3560 } finally {
3561 Binder.restoreCallingIdentity(origId);
3562 }
3563 }
3564 }
3565
3566 /**
3567 * Moves the top activity in the input stackId to the pinned stack.
3568 *
3569 * @param stackId Id of stack to move the top activity to pinned stack.
3570 * @param bounds Bounds to use for pinned stack.
3571 *
3572 * @return True if the top activity of the input stack was successfully moved to the pinned
3573 * stack.
3574 */
3575 @Override
3576 public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003577 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003578 "moveTopActivityToPinnedStack()");
3579 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003580 if (!mSupportsPictureInPicture) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003581 throw new IllegalStateException("moveTopActivityToPinnedStack:"
3582 + "Device doesn't support picture-in-picture mode");
3583 }
3584
3585 long ident = Binder.clearCallingIdentity();
3586 try {
3587 return mStackSupervisor.moveTopStackActivityToPinnedStackLocked(stackId, bounds);
3588 } finally {
3589 Binder.restoreCallingIdentity(ident);
3590 }
3591 }
3592 }
3593
3594 @Override
3595 public boolean isInMultiWindowMode(IBinder token) {
3596 final long origId = Binder.clearCallingIdentity();
3597 try {
3598 synchronized (mGlobalLock) {
3599 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
3600 if (r == null) {
3601 return false;
3602 }
3603 // An activity is consider to be in multi-window mode if its task isn't fullscreen.
3604 return r.inMultiWindowMode();
3605 }
3606 } finally {
3607 Binder.restoreCallingIdentity(origId);
3608 }
3609 }
3610
3611 @Override
3612 public boolean isInPictureInPictureMode(IBinder token) {
3613 final long origId = Binder.clearCallingIdentity();
3614 try {
3615 synchronized (mGlobalLock) {
3616 return isInPictureInPictureMode(ActivityRecord.forTokenLocked(token));
3617 }
3618 } finally {
3619 Binder.restoreCallingIdentity(origId);
3620 }
3621 }
3622
3623 private boolean isInPictureInPictureMode(ActivityRecord r) {
3624 if (r == null || r.getStack() == null || !r.inPinnedWindowingMode()
3625 || r.getStack().isInStackLocked(r) == null) {
3626 return false;
3627 }
3628
3629 // If we are animating to fullscreen then we have already dispatched the PIP mode
3630 // changed, so we should reflect that check here as well.
3631 final PinnedActivityStack stack = r.getStack();
3632 final PinnedStackWindowController windowController = stack.getWindowContainerController();
3633 return !windowController.isAnimatingBoundsToFullscreen();
3634 }
3635
3636 @Override
3637 public boolean enterPictureInPictureMode(IBinder token, final PictureInPictureParams params) {
3638 final long origId = Binder.clearCallingIdentity();
3639 try {
3640 synchronized (mGlobalLock) {
3641 final ActivityRecord r = ensureValidPictureInPictureActivityParamsLocked(
3642 "enterPictureInPictureMode", token, params);
3643
3644 // If the activity is already in picture in picture mode, then just return early
3645 if (isInPictureInPictureMode(r)) {
3646 return true;
3647 }
3648
3649 // Activity supports picture-in-picture, now check that we can enter PiP at this
3650 // point, if it is
3651 if (!r.checkEnterPictureInPictureState("enterPictureInPictureMode",
3652 false /* beforeStopping */)) {
3653 return false;
3654 }
3655
3656 final Runnable enterPipRunnable = () -> {
Wale Ogunwalef276a6f2018-06-15 08:26:07 -07003657 synchronized (mGlobalLock) {
3658 // Only update the saved args from the args that are set
3659 r.pictureInPictureArgs.copyOnlySet(params);
3660 final float aspectRatio = r.pictureInPictureArgs.getAspectRatio();
3661 final List<RemoteAction> actions = r.pictureInPictureArgs.getActions();
3662 // Adjust the source bounds by the insets for the transition down
3663 final Rect sourceBounds = new Rect(
3664 r.pictureInPictureArgs.getSourceRectHint());
3665 mStackSupervisor.moveActivityToPinnedStackLocked(
3666 r, sourceBounds, aspectRatio, "enterPictureInPictureMode");
3667 final PinnedActivityStack stack = r.getStack();
3668 stack.setPictureInPictureAspectRatio(aspectRatio);
3669 stack.setPictureInPictureActions(actions);
3670 MetricsLoggerWrapper.logPictureInPictureEnter(mContext, r.appInfo.uid,
3671 r.shortComponentName, r.supportsEnterPipOnTaskSwitch);
3672 logPictureInPictureArgs(params);
3673 }
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003674 };
3675
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003676 if (isKeyguardLocked()) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003677 // If the keyguard is showing or occluded, then try and dismiss it before
3678 // entering picture-in-picture (this will prompt the user to authenticate if the
3679 // device is currently locked).
3680 dismissKeyguard(token, new KeyguardDismissCallback() {
3681 @Override
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003682 public void onDismissSucceeded() {
3683 mH.post(enterPipRunnable);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003684 }
3685 }, null /* message */);
3686 } else {
3687 // Enter picture in picture immediately otherwise
3688 enterPipRunnable.run();
3689 }
3690 return true;
3691 }
3692 } finally {
3693 Binder.restoreCallingIdentity(origId);
3694 }
3695 }
3696
3697 @Override
3698 public void setPictureInPictureParams(IBinder token, final PictureInPictureParams params) {
3699 final long origId = Binder.clearCallingIdentity();
3700 try {
3701 synchronized (mGlobalLock) {
3702 final ActivityRecord r = ensureValidPictureInPictureActivityParamsLocked(
3703 "setPictureInPictureParams", token, params);
3704
3705 // Only update the saved args from the args that are set
3706 r.pictureInPictureArgs.copyOnlySet(params);
3707 if (r.inPinnedWindowingMode()) {
3708 // If the activity is already in picture-in-picture, update the pinned stack now
3709 // if it is not already expanding to fullscreen. Otherwise, the arguments will
3710 // be used the next time the activity enters PiP
3711 final PinnedActivityStack stack = r.getStack();
3712 if (!stack.isAnimatingBoundsToFullscreen()) {
3713 stack.setPictureInPictureAspectRatio(
3714 r.pictureInPictureArgs.getAspectRatio());
3715 stack.setPictureInPictureActions(r.pictureInPictureArgs.getActions());
3716 }
3717 }
3718 logPictureInPictureArgs(params);
3719 }
3720 } finally {
3721 Binder.restoreCallingIdentity(origId);
3722 }
3723 }
3724
3725 @Override
3726 public int getMaxNumPictureInPictureActions(IBinder token) {
3727 // Currently, this is a static constant, but later, we may change this to be dependent on
3728 // the context of the activity
3729 return 3;
3730 }
3731
3732 private void logPictureInPictureArgs(PictureInPictureParams params) {
3733 if (params.hasSetActions()) {
3734 MetricsLogger.histogram(mContext, "tron_varz_picture_in_picture_actions_count",
3735 params.getActions().size());
3736 }
3737 if (params.hasSetAspectRatio()) {
3738 LogMaker lm = new LogMaker(MetricsEvent.ACTION_PICTURE_IN_PICTURE_ASPECT_RATIO_CHANGED);
3739 lm.addTaggedData(MetricsEvent.PICTURE_IN_PICTURE_ASPECT_RATIO, params.getAspectRatio());
3740 MetricsLogger.action(lm);
3741 }
3742 }
3743
3744 /**
3745 * Checks the state of the system and the activity associated with the given {@param token} to
3746 * verify that picture-in-picture is supported for that activity.
3747 *
3748 * @return the activity record for the given {@param token} if all the checks pass.
3749 */
3750 private ActivityRecord ensureValidPictureInPictureActivityParamsLocked(String caller,
3751 IBinder token, PictureInPictureParams params) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003752 if (!mSupportsPictureInPicture) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003753 throw new IllegalStateException(caller
3754 + ": Device doesn't support picture-in-picture mode.");
3755 }
3756
3757 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
3758 if (r == null) {
3759 throw new IllegalStateException(caller
3760 + ": Can't find activity for token=" + token);
3761 }
3762
3763 if (!r.supportsPictureInPicture()) {
3764 throw new IllegalStateException(caller
3765 + ": Current activity does not support picture-in-picture.");
3766 }
3767
3768 if (params.hasSetAspectRatio()
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003769 && !mWindowManager.isValidPictureInPictureAspectRatio(r.getStack().mDisplayId,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003770 params.getAspectRatio())) {
3771 final float minAspectRatio = mContext.getResources().getFloat(
3772 com.android.internal.R.dimen.config_pictureInPictureMinAspectRatio);
3773 final float maxAspectRatio = mContext.getResources().getFloat(
3774 com.android.internal.R.dimen.config_pictureInPictureMaxAspectRatio);
3775 throw new IllegalArgumentException(String.format(caller
3776 + ": Aspect ratio is too extreme (must be between %f and %f).",
3777 minAspectRatio, maxAspectRatio));
3778 }
3779
3780 // Truncate the number of actions if necessary
3781 params.truncateActions(getMaxNumPictureInPictureActions(token));
3782
3783 return r;
3784 }
3785
3786 @Override
3787 public IBinder getUriPermissionOwnerForActivity(IBinder activityToken) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003788 enforceNotIsolatedCaller("getUriPermissionOwnerForActivity");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003789 synchronized (mGlobalLock) {
3790 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
3791 if (r == null) {
3792 throw new IllegalArgumentException("Activity does not exist; token="
3793 + activityToken);
3794 }
Wale Ogunwale6d50dcc2018-07-21 23:00:40 -07003795 return r.getUriPermissionsLocked().getExternalToken();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003796 }
3797 }
3798
3799 @Override
3800 public void resizeDockedStack(Rect dockedBounds, Rect tempDockedTaskBounds,
3801 Rect tempDockedTaskInsetBounds,
3802 Rect tempOtherTaskBounds, Rect tempOtherTaskInsetBounds) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003803 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizeDockedStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003804 long ident = Binder.clearCallingIdentity();
3805 try {
3806 synchronized (mGlobalLock) {
3807 mStackSupervisor.resizeDockedStackLocked(dockedBounds, tempDockedTaskBounds,
3808 tempDockedTaskInsetBounds, tempOtherTaskBounds, tempOtherTaskInsetBounds,
3809 PRESERVE_WINDOWS);
3810 }
3811 } finally {
3812 Binder.restoreCallingIdentity(ident);
3813 }
3814 }
3815
3816 @Override
3817 public void setSplitScreenResizing(boolean resizing) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003818 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "setSplitScreenResizing()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003819 final long ident = Binder.clearCallingIdentity();
3820 try {
3821 synchronized (mGlobalLock) {
3822 mStackSupervisor.setSplitScreenResizing(resizing);
3823 }
3824 } finally {
3825 Binder.restoreCallingIdentity(ident);
3826 }
3827 }
3828
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003829 /**
3830 * Check that we have the features required for VR-related API calls, and throw an exception if
3831 * not.
3832 */
3833 void enforceSystemHasVrFeature() {
3834 if (!mContext.getPackageManager().hasSystemFeature(
3835 PackageManager.FEATURE_VR_MODE_HIGH_PERFORMANCE)) {
3836 throw new UnsupportedOperationException("VR mode not supported on this device!");
3837 }
3838 }
3839
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003840 @Override
3841 public int setVrMode(IBinder token, boolean enabled, ComponentName packageName) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003842 enforceSystemHasVrFeature();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003843
3844 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class);
3845
3846 ActivityRecord r;
3847 synchronized (mGlobalLock) {
3848 r = ActivityRecord.isInStackLocked(token);
3849 }
3850
3851 if (r == null) {
3852 throw new IllegalArgumentException();
3853 }
3854
3855 int err;
3856 if ((err = vrService.hasVrPackage(packageName, r.userId)) !=
3857 VrManagerInternal.NO_ERROR) {
3858 return err;
3859 }
3860
3861 // Clear the binder calling uid since this path may call moveToTask().
3862 final long callingId = Binder.clearCallingIdentity();
3863 try {
3864 synchronized (mGlobalLock) {
3865 r.requestedVrComponent = (enabled) ? packageName : null;
3866
3867 // Update associated state if this activity is currently focused
Andrii Kulian52d255c2018-07-13 11:32:19 -07003868 if (r.isResumedActivityOnDisplay()) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003869 applyUpdateVrModeLocked(r);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003870 }
3871 return 0;
3872 }
3873 } finally {
3874 Binder.restoreCallingIdentity(callingId);
3875 }
3876 }
3877
3878 @Override
3879 public void startLocalVoiceInteraction(IBinder callingActivity, Bundle options) {
3880 Slog.i(TAG, "Activity tried to startLocalVoiceInteraction");
3881 synchronized (mGlobalLock) {
Andrii Kulian5f750bc2018-07-17 08:57:23 -07003882 ActivityRecord activity = getTopDisplayFocusedStack().getTopActivity();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003883 if (ActivityRecord.forTokenLocked(callingActivity) != activity) {
3884 throw new SecurityException("Only focused activity can call startVoiceInteraction");
3885 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07003886 if (mRunningVoice != null || activity.getTask().voiceSession != null
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003887 || activity.voiceSession != null) {
3888 Slog.w(TAG, "Already in a voice interaction, cannot start new voice interaction");
3889 return;
3890 }
3891 if (activity.pendingVoiceInteractionStart) {
3892 Slog.w(TAG, "Pending start of voice interaction already.");
3893 return;
3894 }
3895 activity.pendingVoiceInteractionStart = true;
3896 }
3897 LocalServices.getService(VoiceInteractionManagerInternal.class)
3898 .startLocalVoiceInteraction(callingActivity, options);
3899 }
3900
3901 @Override
3902 public void stopLocalVoiceInteraction(IBinder callingActivity) {
3903 LocalServices.getService(VoiceInteractionManagerInternal.class)
3904 .stopLocalVoiceInteraction(callingActivity);
3905 }
3906
3907 @Override
3908 public boolean supportsLocalVoiceInteraction() {
3909 return LocalServices.getService(VoiceInteractionManagerInternal.class)
3910 .supportsLocalVoiceInteraction();
3911 }
3912
3913 /** Notifies all listeners when the pinned stack animation starts. */
3914 @Override
3915 public void notifyPinnedStackAnimationStarted() {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003916 mTaskChangeNotificationController.notifyPinnedStackAnimationStarted();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003917 }
3918
3919 /** Notifies all listeners when the pinned stack animation ends. */
3920 @Override
3921 public void notifyPinnedStackAnimationEnded() {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07003922 mTaskChangeNotificationController.notifyPinnedStackAnimationEnded();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003923 }
3924
3925 @Override
3926 public void resizePinnedStack(Rect pinnedBounds, Rect tempPinnedTaskBounds) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003927 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizePinnedStack()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003928 final long ident = Binder.clearCallingIdentity();
3929 try {
3930 synchronized (mGlobalLock) {
3931 mStackSupervisor.resizePinnedStackLocked(pinnedBounds, tempPinnedTaskBounds);
3932 }
3933 } finally {
3934 Binder.restoreCallingIdentity(ident);
3935 }
3936 }
3937
3938 @Override
3939 public boolean updateDisplayOverrideConfiguration(Configuration values, int displayId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003940 mAmInternal.enforceCallingPermission(CHANGE_CONFIGURATION, "updateDisplayOverrideConfiguration()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003941
3942 synchronized (mGlobalLock) {
3943 // Check if display is initialized in AM.
3944 if (!mStackSupervisor.isDisplayAdded(displayId)) {
3945 // Call might come when display is not yet added or has already been removed.
3946 if (DEBUG_CONFIGURATION) {
3947 Slog.w(TAG, "Trying to update display configuration for non-existing displayId="
3948 + displayId);
3949 }
3950 return false;
3951 }
3952
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003953 if (values == null && mWindowManager != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003954 // sentinel: fetch the current configuration from the window manager
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003955 values = mWindowManager.computeNewConfiguration(displayId);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003956 }
3957
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003958 if (mWindowManager != null) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07003959 final Message msg = PooledLambda.obtainMessage(
3960 ActivityManagerInternal::updateOomLevelsForDisplay, mAmInternal, displayId);
3961 mH.sendMessage(msg);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003962 }
3963
3964 final long origId = Binder.clearCallingIdentity();
3965 try {
3966 if (values != null) {
3967 Settings.System.clearConfiguration(values);
3968 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003969 updateDisplayOverrideConfigurationLocked(values, null /* starting */,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003970 false /* deferResume */, displayId, mTmpUpdateConfigurationResult);
3971 return mTmpUpdateConfigurationResult.changes != 0;
3972 } finally {
3973 Binder.restoreCallingIdentity(origId);
3974 }
3975 }
3976 }
3977
3978 @Override
3979 public boolean updateConfiguration(Configuration values) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003980 mAmInternal.enforceCallingPermission(CHANGE_CONFIGURATION, "updateConfiguration()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003981
3982 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003983 if (values == null && mWindowManager != null) {
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003984 // sentinel: fetch the current configuration from the window manager
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003985 values = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003986 }
3987
Wale Ogunwalea6191b42018-05-09 07:41:32 -07003988 if (mWindowManager != null) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07003989 final Message msg = PooledLambda.obtainMessage(
3990 ActivityManagerInternal::updateOomLevelsForDisplay, mAmInternal,
3991 DEFAULT_DISPLAY);
3992 mH.sendMessage(msg);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07003993 }
3994
3995 final long origId = Binder.clearCallingIdentity();
3996 try {
3997 if (values != null) {
3998 Settings.System.clearConfiguration(values);
3999 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004000 updateConfigurationLocked(values, null, false, false /* persistent */,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004001 UserHandle.USER_NULL, false /* deferResume */,
4002 mTmpUpdateConfigurationResult);
4003 return mTmpUpdateConfigurationResult.changes != 0;
4004 } finally {
4005 Binder.restoreCallingIdentity(origId);
4006 }
4007 }
4008 }
4009
4010 @Override
4011 public void dismissKeyguard(IBinder token, IKeyguardDismissCallback callback,
4012 CharSequence message) {
4013 if (message != null) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004014 mAmInternal.enforceCallingPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004015 Manifest.permission.SHOW_KEYGUARD_MESSAGE, "dismissKeyguard()");
4016 }
4017 final long callingId = Binder.clearCallingIdentity();
4018 try {
4019 synchronized (mGlobalLock) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004020 mKeyguardController.dismissKeyguard(token, callback, message);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004021 }
4022 } finally {
4023 Binder.restoreCallingIdentity(callingId);
4024 }
4025 }
4026
4027 @Override
4028 public void cancelTaskWindowTransition(int taskId) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004029 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004030 "cancelTaskWindowTransition()");
4031 final long ident = Binder.clearCallingIdentity();
4032 try {
4033 synchronized (mGlobalLock) {
4034 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId,
4035 MATCH_TASK_IN_STACKS_ONLY);
4036 if (task == null) {
4037 Slog.w(TAG, "cancelTaskWindowTransition: taskId=" + taskId + " not found");
4038 return;
4039 }
4040 task.cancelWindowTransition();
4041 }
4042 } finally {
4043 Binder.restoreCallingIdentity(ident);
4044 }
4045 }
4046
4047 @Override
4048 public ActivityManager.TaskSnapshot getTaskSnapshot(int taskId, boolean reducedResolution) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004049 enforceCallerIsRecentsOrHasPermission(READ_FRAME_BUFFER, "getTaskSnapshot()");
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004050 final long ident = Binder.clearCallingIdentity();
4051 try {
4052 final TaskRecord task;
4053 synchronized (mGlobalLock) {
4054 task = mStackSupervisor.anyTaskForIdLocked(taskId,
4055 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS);
4056 if (task == null) {
4057 Slog.w(TAG, "getTaskSnapshot: taskId=" + taskId + " not found");
4058 return null;
4059 }
4060 }
4061 // Don't call this while holding the lock as this operation might hit the disk.
4062 return task.getSnapshot(reducedResolution);
4063 } finally {
4064 Binder.restoreCallingIdentity(ident);
4065 }
4066 }
4067
4068 @Override
4069 public void setDisablePreviewScreenshots(IBinder token, boolean disable) {
4070 synchronized (mGlobalLock) {
4071 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4072 if (r == null) {
4073 Slog.w(TAG, "setDisablePreviewScreenshots: Unable to find activity for token="
4074 + token);
4075 return;
4076 }
4077 final long origId = Binder.clearCallingIdentity();
4078 try {
4079 r.setDisablePreviewScreenshots(disable);
4080 } finally {
4081 Binder.restoreCallingIdentity(origId);
4082 }
4083 }
4084 }
4085
4086 /** Return the user id of the last resumed activity. */
4087 @Override
4088 public @UserIdInt
4089 int getLastResumedActivityUserId() {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004090 mAmInternal.enforceCallingPermission(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004091 Manifest.permission.INTERACT_ACROSS_USERS_FULL, "getLastResumedActivityUserId()");
4092 synchronized (mGlobalLock) {
Wale Ogunwalef6733932018-06-27 05:14:34 -07004093 if (mLastResumedActivity == null) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004094 return getCurrentUserId();
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004095 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07004096 return mLastResumedActivity.userId;
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004097 }
4098 }
4099
4100 @Override
4101 public void updateLockTaskFeatures(int userId, int flags) {
4102 final int callingUid = Binder.getCallingUid();
4103 if (callingUid != 0 && callingUid != SYSTEM_UID) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004104 mAmInternal.enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004105 "updateLockTaskFeatures()");
4106 }
4107 synchronized (mGlobalLock) {
4108 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Allowing features " + userId + ":0x" +
4109 Integer.toHexString(flags));
Wale Ogunwaled95c06b2018-05-08 10:35:38 -07004110 getLockTaskController().updateLockTaskFeatures(userId, flags);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004111 }
4112 }
4113
4114 @Override
4115 public void setShowWhenLocked(IBinder token, boolean showWhenLocked) {
4116 synchronized (mGlobalLock) {
4117 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4118 if (r == null) {
4119 return;
4120 }
4121 final long origId = Binder.clearCallingIdentity();
4122 try {
4123 r.setShowWhenLocked(showWhenLocked);
4124 } finally {
4125 Binder.restoreCallingIdentity(origId);
4126 }
4127 }
4128 }
4129
4130 @Override
4131 public void setTurnScreenOn(IBinder token, boolean turnScreenOn) {
4132 synchronized (mGlobalLock) {
4133 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4134 if (r == null) {
4135 return;
4136 }
4137 final long origId = Binder.clearCallingIdentity();
4138 try {
4139 r.setTurnScreenOn(turnScreenOn);
4140 } finally {
4141 Binder.restoreCallingIdentity(origId);
4142 }
4143 }
4144 }
4145
4146 @Override
4147 public void registerRemoteAnimations(IBinder token, RemoteAnimationDefinition definition) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004148 mAmInternal.enforceCallingPermission(CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004149 "registerRemoteAnimations");
4150 definition.setCallingPid(Binder.getCallingPid());
4151 synchronized (mGlobalLock) {
4152 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
4153 if (r == null) {
4154 return;
4155 }
4156 final long origId = Binder.clearCallingIdentity();
4157 try {
4158 r.registerRemoteAnimations(definition);
4159 } finally {
4160 Binder.restoreCallingIdentity(origId);
4161 }
4162 }
4163 }
4164
4165 @Override
4166 public void registerRemoteAnimationForNextActivityStart(String packageName,
4167 RemoteAnimationAdapter adapter) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004168 mAmInternal.enforceCallingPermission(CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS,
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004169 "registerRemoteAnimationForNextActivityStart");
4170 adapter.setCallingPid(Binder.getCallingPid());
4171 synchronized (mGlobalLock) {
4172 final long origId = Binder.clearCallingIdentity();
4173 try {
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07004174 getActivityStartController().registerRemoteAnimationForNextActivityStart(
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004175 packageName, adapter);
4176 } finally {
4177 Binder.restoreCallingIdentity(origId);
4178 }
4179 }
4180 }
4181
4182 /** @see android.app.ActivityManager#alwaysShowUnsupportedCompileSdkWarning */
4183 @Override
4184 public void alwaysShowUnsupportedCompileSdkWarning(ComponentName activity) {
4185 synchronized (mGlobalLock) {
4186 final long origId = Binder.clearCallingIdentity();
4187 try {
Wale Ogunwale008163e2018-07-23 23:11:08 -07004188 mAppWarnings.alwaysShowUnsupportedCompileSdkWarning(activity);
Wale Ogunwale04d9cb52018-04-30 13:55:07 -07004189 } finally {
4190 Binder.restoreCallingIdentity(origId);
4191 }
4192 }
4193 }
Wale Ogunwale6767eae2018-05-03 15:52:51 -07004194
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004195 @Override
4196 public void setVrThread(int tid) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004197 enforceSystemHasVrFeature();
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004198 synchronized (mGlobalLock) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004199 final int pid = Binder.getCallingPid();
4200 final WindowProcessController wpc = mPidMap.get(pid);
4201 mVrController.setVrThreadLocked(tid, pid, wpc);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004202 }
4203 }
4204
4205 @Override
4206 public void setPersistentVrThread(int tid) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004207 if (checkCallingPermission(Manifest.permission.RESTRICTED_VR_ACCESS)
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004208 != PERMISSION_GRANTED) {
4209 final String msg = "Permission Denial: setPersistentVrThread() from pid="
4210 + Binder.getCallingPid()
4211 + ", uid=" + Binder.getCallingUid()
4212 + " requires " + Manifest.permission.RESTRICTED_VR_ACCESS;
4213 Slog.w(TAG, msg);
4214 throw new SecurityException(msg);
4215 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004216 enforceSystemHasVrFeature();
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004217 synchronized (mGlobalLock) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004218 final int pid = Binder.getCallingPid();
4219 final WindowProcessController proc = mPidMap.get(pid);
4220 mVrController.setPersistentVrThreadLocked(tid, pid, proc);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004221 }
4222 }
4223
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004224 @Override
4225 public void stopAppSwitches() {
4226 enforceCallerIsRecentsOrHasPermission(STOP_APP_SWITCHES, "stopAppSwitches");
4227 synchronized (mGlobalLock) {
4228 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() + APP_SWITCH_DELAY_TIME;
4229 mDidAppSwitch = false;
4230 getActivityStartController().schedulePendingActivityLaunches(APP_SWITCH_DELAY_TIME);
4231 }
4232 }
4233
4234 @Override
4235 public void resumeAppSwitches() {
4236 enforceCallerIsRecentsOrHasPermission(STOP_APP_SWITCHES, "resumeAppSwitches");
4237 synchronized (mGlobalLock) {
4238 // Note that we don't execute any pending app switches... we will
4239 // let those wait until either the timeout, or the next start
4240 // activity request.
4241 mAppSwitchesAllowedTime = 0;
4242 }
4243 }
4244
4245 void onStartActivitySetDidAppSwitch() {
4246 if (mDidAppSwitch) {
4247 // This is the second allowed switch since we stopped switches, so now just generally
4248 // allow switches. Use case:
4249 // - user presses home (switches disabled, switch to home, mDidAppSwitch now true);
4250 // - user taps a home icon (coming from home so allowed, we hit here and now allow
4251 // anyone to switch again).
4252 mAppSwitchesAllowedTime = 0;
4253 } else {
4254 mDidAppSwitch = true;
4255 }
4256 }
4257
4258 /** @return whether the system should disable UI modes incompatible with VR mode. */
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004259 boolean shouldDisableNonVrUiLocked() {
4260 return mVrController.shouldDisableNonVrUiLocked();
4261 }
4262
Wale Ogunwale53783742018-09-16 10:21:51 -07004263 private void applyUpdateVrModeLocked(ActivityRecord r) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004264 // VR apps are expected to run in a main display. If an app is turning on VR for
4265 // itself, but lives in a dynamic stack, then make sure that it is moved to the main
4266 // fullscreen stack before enabling VR Mode.
4267 // TODO: The goal of this code is to keep the VR app on the main display. When the
4268 // stack implementation changes in the future, keep in mind that the use of the fullscreen
4269 // stack is a means to move the activity to the main display and a moveActivityToDisplay()
4270 // option would be a better choice here.
4271 if (r.requestedVrComponent != null && r.getDisplayId() != DEFAULT_DISPLAY) {
4272 Slog.i(TAG, "Moving " + r.shortComponentName + " from stack " + r.getStackId()
4273 + " to main stack for VR");
4274 final ActivityStack stack = mStackSupervisor.getDefaultDisplay().getOrCreateStack(
4275 WINDOWING_MODE_FULLSCREEN, r.getActivityType(), true /* toTop */);
4276 moveTaskToStack(r.getTask().taskId, stack.mStackId, true /* toTop */);
4277 }
4278 mH.post(() -> {
4279 if (!mVrController.onVrModeChanged(r)) {
4280 return;
4281 }
4282 synchronized (mGlobalLock) {
4283 final boolean disableNonVrUi = mVrController.shouldDisableNonVrUiLocked();
4284 mWindowManager.disableNonVrUi(disableNonVrUi);
4285 if (disableNonVrUi) {
4286 // If we are in a VR mode where Picture-in-Picture mode is unsupported,
4287 // then remove the pinned stack.
4288 mStackSupervisor.removeStacksInWindowingModes(WINDOWING_MODE_PINNED);
4289 }
4290 }
4291 });
4292 }
4293
Wale Ogunwale53783742018-09-16 10:21:51 -07004294 @Override
4295 public int getPackageScreenCompatMode(String packageName) {
4296 enforceNotIsolatedCaller("getPackageScreenCompatMode");
4297 synchronized (mGlobalLock) {
4298 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName);
4299 }
4300 }
4301
4302 @Override
4303 public void setPackageScreenCompatMode(String packageName, int mode) {
4304 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4305 "setPackageScreenCompatMode");
4306 synchronized (mGlobalLock) {
4307 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode);
4308 }
4309 }
4310
4311 @Override
4312 public boolean getPackageAskScreenCompat(String packageName) {
4313 enforceNotIsolatedCaller("getPackageAskScreenCompat");
4314 synchronized (mGlobalLock) {
4315 return mCompatModePackages.getPackageAskCompatModeLocked(packageName);
4316 }
4317 }
4318
4319 @Override
4320 public void setPackageAskScreenCompat(String packageName, boolean ask) {
4321 mAmInternal.enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4322 "setPackageAskScreenCompat");
4323 synchronized (mGlobalLock) {
4324 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask);
4325 }
4326 }
4327
Andrii Kulian5f750bc2018-07-17 08:57:23 -07004328 ActivityStack getTopDisplayFocusedStack() {
4329 return mStackSupervisor.getTopDisplayFocusedStack();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004330 }
4331
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004332 /** Pokes the task persister. */
4333 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) {
4334 mRecentTasks.notifyTaskPersisterLocked(task, flush);
4335 }
4336
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07004337 void onTopProcChangedLocked(WindowProcessController proc) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004338 mVrController.onTopProcChangedLocked(proc);
4339 }
4340
4341 boolean isKeyguardLocked() {
4342 return mKeyguardController.isKeyguardLocked();
4343 }
4344
4345 boolean isNextTransitionForward() {
4346 int transit = mWindowManager.getPendingAppTransition();
4347 return transit == TRANSIT_ACTIVITY_OPEN
4348 || transit == TRANSIT_TASK_OPEN
4349 || transit == TRANSIT_TASK_TO_FRONT;
4350 }
4351
Wale Ogunwale31913b52018-10-13 08:29:31 -07004352 void dumpLastANRLocked(PrintWriter pw) {
4353 pw.println("ACTIVITY MANAGER LAST ANR (dumpsys activity lastanr)");
4354 if (mLastANRState == null) {
4355 pw.println(" <no ANR has occurred since boot>");
4356 } else {
4357 pw.println(mLastANRState);
4358 }
4359 }
4360
4361 void dumpLastANRTracesLocked(PrintWriter pw) {
4362 pw.println("ACTIVITY MANAGER LAST ANR TRACES (dumpsys activity lastanr-traces)");
4363
4364 final File[] files = new File(ANR_TRACE_DIR).listFiles();
4365 if (ArrayUtils.isEmpty(files)) {
4366 pw.println(" <no ANR has occurred since boot>");
4367 return;
4368 }
4369 // Find the latest file.
4370 File latest = null;
4371 for (File f : files) {
4372 if ((latest == null) || (latest.lastModified() < f.lastModified())) {
4373 latest = f;
Wale Ogunwalef6733932018-06-27 05:14:34 -07004374 }
Wale Ogunwale31913b52018-10-13 08:29:31 -07004375 }
4376 pw.print("File: ");
4377 pw.print(latest.getName());
4378 pw.println();
4379 try (BufferedReader in = new BufferedReader(new FileReader(latest))) {
4380 String line;
4381 while ((line = in.readLine()) != null) {
4382 pw.println(line);
4383 }
4384 } catch (IOException e) {
4385 pw.print("Unable to read: ");
4386 pw.print(e);
4387 pw.println();
4388 }
4389 }
4390
4391 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args,
4392 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) {
4393 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage,
4394 "ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)");
4395 }
4396
4397 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args,
4398 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage, String header) {
4399 pw.println(header);
4400
4401 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient,
4402 dumpPackage);
4403 boolean needSep = printedAnything;
4404
4405 boolean printed = ActivityStackSupervisor.printThisActivity(pw,
4406 mStackSupervisor.getTopResumedActivity(), dumpPackage, needSep,
4407 " ResumedActivity: ");
4408 if (printed) {
4409 printedAnything = true;
4410 needSep = false;
4411 }
4412
4413 if (dumpPackage == null) {
4414 if (needSep) {
4415 pw.println();
4416 }
4417 printedAnything = true;
4418 mStackSupervisor.dump(pw, " ");
4419 }
4420
4421 if (!printedAnything) {
4422 pw.println(" (nothing)");
4423 }
4424 }
4425
4426 void dumpActivityContainersLocked(PrintWriter pw) {
4427 pw.println("ACTIVITY MANAGER STARTER (dumpsys activity containers)");
4428 mStackSupervisor.dumpChildrenNames(pw, " ");
4429 pw.println(" ");
4430 }
4431
4432 void dumpActivityStarterLocked(PrintWriter pw, String dumpPackage) {
4433 pw.println("ACTIVITY MANAGER STARTER (dumpsys activity starter)");
4434 getActivityStartController().dump(pw, "", dumpPackage);
4435 }
4436
4437 /**
4438 * There are three things that cmd can be:
4439 * - a flattened component name that matches an existing activity
4440 * - the cmd arg isn't the flattened component name of an existing activity:
4441 * dump all activity whose component contains the cmd as a substring
4442 * - A hex number of the ActivityRecord object instance.
4443 *
4444 * @param dumpVisibleStacksOnly dump activity with {@param name} only if in a visible stack
4445 * @param dumpFocusedStackOnly dump activity with {@param name} only if in the focused stack
4446 */
4447 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args,
4448 int opti, boolean dumpAll, boolean dumpVisibleStacksOnly, boolean dumpFocusedStackOnly) {
4449 ArrayList<ActivityRecord> activities;
4450
4451 synchronized (mGlobalLock) {
4452 activities = mStackSupervisor.getDumpActivitiesLocked(name, dumpVisibleStacksOnly,
4453 dumpFocusedStackOnly);
4454 }
4455
4456 if (activities.size() <= 0) {
4457 return false;
4458 }
4459
4460 String[] newArgs = new String[args.length - opti];
4461 System.arraycopy(args, opti, newArgs, 0, args.length - opti);
4462
4463 TaskRecord lastTask = null;
4464 boolean needSep = false;
4465 for (int i = activities.size() - 1; i >= 0; i--) {
4466 ActivityRecord r = activities.get(i);
4467 if (needSep) {
4468 pw.println();
4469 }
4470 needSep = true;
4471 synchronized (mGlobalLock) {
4472 final TaskRecord task = r.getTask();
4473 if (lastTask != task) {
4474 lastTask = task;
4475 pw.print("TASK "); pw.print(lastTask.affinity);
4476 pw.print(" id="); pw.print(lastTask.taskId);
4477 pw.print(" userId="); pw.println(lastTask.userId);
4478 if (dumpAll) {
4479 lastTask.dump(pw, " ");
4480 }
4481 }
4482 }
4483 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll);
4484 }
4485 return true;
4486 }
4487
4488 /**
4489 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if
4490 * there is a thread associated with the activity.
4491 */
4492 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw,
4493 final ActivityRecord r, String[] args, boolean dumpAll) {
4494 String innerPrefix = prefix + " ";
4495 synchronized (mGlobalLock) {
4496 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName);
4497 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r)));
4498 pw.print(" pid=");
4499 if (r.hasProcess()) pw.println(r.app.getPid());
4500 else pw.println("(not running)");
4501 if (dumpAll) {
4502 r.dump(pw, innerPrefix);
4503 }
4504 }
4505 if (r.attachedToProcess()) {
4506 // flush anything that is already in the PrintWriter since the thread is going
4507 // to write to the file descriptor directly
4508 pw.flush();
4509 try {
4510 TransferPipe tp = new TransferPipe();
4511 try {
4512 r.app.getThread().dumpActivity(tp.getWriteFd(),
4513 r.appToken, innerPrefix, args);
4514 tp.go(fd);
4515 } finally {
4516 tp.kill();
4517 }
4518 } catch (IOException e) {
4519 pw.println(innerPrefix + "Failure while dumping the activity: " + e);
4520 } catch (RemoteException e) {
4521 pw.println(innerPrefix + "Got a RemoteException while dumping the activity");
4522 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07004523 }
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004524 }
4525
Wale Ogunwalef6733932018-06-27 05:14:34 -07004526 void writeSleepStateToProto(ProtoOutputStream proto) {
4527 for (ActivityTaskManagerInternal.SleepToken st : mStackSupervisor.mSleepTokens) {
4528 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SLEEP_TOKENS,
4529 st.toString());
4530 }
4531
4532 if (mRunningVoice != null) {
4533 final long vrToken = proto.start(
4534 ActivityManagerServiceDumpProcessesProto.RUNNING_VOICE);
4535 proto.write(ActivityManagerServiceDumpProcessesProto.Voice.SESSION,
4536 mRunningVoice.toString());
4537 mVoiceWakeLock.writeToProto(
4538 proto, ActivityManagerServiceDumpProcessesProto.Voice.WAKELOCK);
4539 proto.end(vrToken);
4540 }
4541
4542 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SLEEPING, mSleeping);
4543 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SHUTTING_DOWN,
4544 mShuttingDown);
4545 mVrController.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.VR_CONTROLLER);
Wale Ogunwaled0412b32018-05-08 09:25:50 -07004546 }
4547
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004548 int getCurrentUserId() {
4549 return mAmInternal.getCurrentUserId();
4550 }
4551
4552 private void enforceNotIsolatedCaller(String caller) {
4553 if (UserHandle.isIsolated(Binder.getCallingUid())) {
4554 throw new SecurityException("Isolated process not allowed to call " + caller);
4555 }
4556 }
4557
Wale Ogunwalef6733932018-06-27 05:14:34 -07004558 public Configuration getConfiguration() {
4559 Configuration ci;
4560 synchronized(mGlobalLock) {
Yunfan Chen75157d72018-07-27 14:47:21 +09004561 ci = new Configuration(getGlobalConfigurationForCallingPid());
Wale Ogunwalef6733932018-06-27 05:14:34 -07004562 ci.userSetLocale = false;
4563 }
4564 return ci;
4565 }
4566
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004567 /**
4568 * Current global configuration information. Contains general settings for the entire system,
4569 * also corresponds to the merged configuration of the default display.
4570 */
4571 Configuration getGlobalConfiguration() {
4572 return mStackSupervisor.getConfiguration();
4573 }
4574
4575 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4576 boolean initLocale) {
4577 return updateConfigurationLocked(values, starting, initLocale, false /* deferResume */);
4578 }
4579
4580 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4581 boolean initLocale, boolean deferResume) {
4582 // pass UserHandle.USER_NULL as userId because we don't persist configuration for any user
4583 return updateConfigurationLocked(values, starting, initLocale, false /* persistent */,
4584 UserHandle.USER_NULL, deferResume);
4585 }
4586
4587 void updatePersistentConfiguration(Configuration values, @UserIdInt int userId) {
4588 final long origId = Binder.clearCallingIdentity();
4589 try {
4590 synchronized (mGlobalLock) {
4591 updateConfigurationLocked(values, null, false, true, userId,
4592 false /* deferResume */);
4593 }
4594 } finally {
4595 Binder.restoreCallingIdentity(origId);
4596 }
4597 }
4598
4599 void updateUserConfiguration() {
4600 synchronized (mGlobalLock) {
4601 final Configuration configuration = new Configuration(getGlobalConfiguration());
4602 final int currentUserId = mAmInternal.getCurrentUserId();
4603 Settings.System.adjustConfigurationForUser(mContext.getContentResolver(), configuration,
4604 currentUserId, Settings.System.canWrite(mContext));
4605 updateConfigurationLocked(configuration, null /* starting */, false /* initLocale */,
4606 false /* persistent */, currentUserId, false /* deferResume */);
4607 }
4608 }
4609
4610 private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4611 boolean initLocale, boolean persistent, int userId, boolean deferResume) {
4612 return updateConfigurationLocked(values, starting, initLocale, persistent, userId,
4613 deferResume, null /* result */);
4614 }
4615
4616 /**
4617 * Do either or both things: (1) change the current configuration, and (2)
4618 * make sure the given activity is running with the (now) current
4619 * configuration. Returns true if the activity has been left running, or
4620 * false if <var>starting</var> is being destroyed to match the new
4621 * configuration.
4622 *
4623 * @param userId is only used when persistent parameter is set to true to persist configuration
4624 * for that particular user
4625 */
4626 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
4627 boolean initLocale, boolean persistent, int userId, boolean deferResume,
4628 ActivityTaskManagerService.UpdateConfigurationResult result) {
4629 int changes = 0;
4630 boolean kept = true;
4631
4632 if (mWindowManager != null) {
4633 mWindowManager.deferSurfaceLayout();
4634 }
4635 try {
4636 if (values != null) {
4637 changes = updateGlobalConfigurationLocked(values, initLocale, persistent, userId,
4638 deferResume);
4639 }
4640
4641 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes);
4642 } finally {
4643 if (mWindowManager != null) {
4644 mWindowManager.continueSurfaceLayout();
4645 }
4646 }
4647
4648 if (result != null) {
4649 result.changes = changes;
4650 result.activityRelaunched = !kept;
4651 }
4652 return kept;
4653 }
4654
4655 /**
4656 * Returns true if this configuration change is interesting enough to send an
4657 * {@link Intent#ACTION_SPLIT_CONFIGURATION_CHANGED} broadcast.
4658 */
4659 private static boolean isSplitConfigurationChange(int configDiff) {
4660 return (configDiff & (ActivityInfo.CONFIG_LOCALE | ActivityInfo.CONFIG_DENSITY)) != 0;
4661 }
4662
4663 /** Update default (global) configuration and notify listeners about changes. */
4664 private int updateGlobalConfigurationLocked(@NonNull Configuration values, boolean initLocale,
4665 boolean persistent, int userId, boolean deferResume) {
4666 mTempConfig.setTo(getGlobalConfiguration());
4667 final int changes = mTempConfig.updateFrom(values);
4668 if (changes == 0) {
4669 // Since calling to Activity.setRequestedOrientation leads to freezing the window with
4670 // setting WindowManagerService.mWaitingForConfig to true, it is important that we call
4671 // performDisplayOverrideConfigUpdate in order to send the new display configuration
4672 // (even if there are no actual changes) to unfreeze the window.
4673 performDisplayOverrideConfigUpdate(values, deferResume, DEFAULT_DISPLAY);
4674 return 0;
4675 }
4676
4677 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) Slog.i(TAG_CONFIGURATION,
4678 "Updating global configuration to: " + values);
4679
4680 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes);
4681 StatsLog.write(StatsLog.RESOURCE_CONFIGURATION_CHANGED,
4682 values.colorMode,
4683 values.densityDpi,
4684 values.fontScale,
4685 values.hardKeyboardHidden,
4686 values.keyboard,
4687 values.keyboardHidden,
4688 values.mcc,
4689 values.mnc,
4690 values.navigation,
4691 values.navigationHidden,
4692 values.orientation,
4693 values.screenHeightDp,
4694 values.screenLayout,
4695 values.screenWidthDp,
4696 values.smallestScreenWidthDp,
4697 values.touchscreen,
4698 values.uiMode);
4699
4700
4701 if (!initLocale && !values.getLocales().isEmpty() && values.userSetLocale) {
4702 final LocaleList locales = values.getLocales();
4703 int bestLocaleIndex = 0;
4704 if (locales.size() > 1) {
4705 if (mSupportedSystemLocales == null) {
4706 mSupportedSystemLocales = Resources.getSystem().getAssets().getLocales();
4707 }
4708 bestLocaleIndex = Math.max(0, locales.getFirstMatchIndex(mSupportedSystemLocales));
4709 }
4710 SystemProperties.set("persist.sys.locale",
4711 locales.get(bestLocaleIndex).toLanguageTag());
4712 LocaleList.setDefault(locales, bestLocaleIndex);
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004713
4714 final Message m = PooledLambda.obtainMessage(
4715 ActivityTaskManagerService::sendLocaleToMountDaemonMsg, this,
4716 locales.get(bestLocaleIndex));
4717 mH.sendMessage(m);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004718 }
4719
Yunfan Chen75157d72018-07-27 14:47:21 +09004720 mTempConfig.seq = increaseConfigurationSeqLocked();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004721
4722 // Update stored global config and notify everyone about the change.
4723 mStackSupervisor.onConfigurationChanged(mTempConfig);
4724
4725 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + mTempConfig);
4726 // TODO(multi-display): Update UsageEvents#Event to include displayId.
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004727 mUsageStatsInternal.reportConfigurationChange(mTempConfig, mAmInternal.getCurrentUserId());
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004728
4729 // TODO: If our config changes, should we auto dismiss any currently showing dialogs?
Wale Ogunwalef6733932018-06-27 05:14:34 -07004730 updateShouldShowDialogsLocked(mTempConfig);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004731
4732 AttributeCache ac = AttributeCache.instance();
4733 if (ac != null) {
4734 ac.updateConfiguration(mTempConfig);
4735 }
4736
4737 // Make sure all resources in our process are updated right now, so that anyone who is going
4738 // to retrieve resource values after we return will be sure to get the new ones. This is
4739 // especially important during boot, where the first config change needs to guarantee all
4740 // resources have that config before following boot code is executed.
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004741 mSystemThread.applyConfigurationToResources(mTempConfig);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004742
4743 // We need another copy of global config because we're scheduling some calls instead of
4744 // running them in place. We need to be sure that object we send will be handled unchanged.
4745 final Configuration configCopy = new Configuration(mTempConfig);
4746 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) {
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004747 final Message msg = PooledLambda.obtainMessage(
4748 ActivityTaskManagerService::sendPutConfigurationForUserMsg,
4749 this, userId, configCopy);
4750 mH.sendMessage(msg);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004751 }
4752
Yunfan Chen34fcc7a2018-10-11 16:26:09 -07004753 for (int i = mPidMap.size() - 1; i >= 0; i--) {
4754 WindowProcessController app = mPidMap.get(mPidMap.keyAt(i));
4755 if (DEBUG_CONFIGURATION) {
4756 Slog.v(TAG_CONFIGURATION, "Update process config of "
4757 + app.mName + " to new config " + configCopy);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004758 }
Yunfan Chen34fcc7a2018-10-11 16:26:09 -07004759 app.onConfigurationChanged(configCopy);
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004760 }
4761
4762 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED);
4763 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_REPLACE_PENDING
4764 | Intent.FLAG_RECEIVER_FOREGROUND
4765 | Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS);
4766 mAm.broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null,
4767 OP_NONE, null, false, false, MY_PID, SYSTEM_UID,
4768 UserHandle.USER_ALL);
4769 if ((changes & ActivityInfo.CONFIG_LOCALE) != 0) {
4770 intent = new Intent(Intent.ACTION_LOCALE_CHANGED);
4771 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND
4772 | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND
4773 | Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS);
4774 if (initLocale || !mAm.mProcessesReady) {
4775 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
4776 }
4777 mAm.broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null,
4778 OP_NONE, null, false, false, MY_PID, SYSTEM_UID,
4779 UserHandle.USER_ALL);
4780 }
4781
4782 // Send a broadcast to PackageInstallers if the configuration change is interesting
4783 // for the purposes of installing additional splits.
4784 if (!initLocale && isSplitConfigurationChange(changes)) {
4785 intent = new Intent(Intent.ACTION_SPLIT_CONFIGURATION_CHANGED);
4786 intent.addFlags(Intent.FLAG_RECEIVER_REPLACE_PENDING
4787 | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND);
4788
4789 // Typically only app stores will have this permission.
4790 String[] permissions = new String[] { android.Manifest.permission.INSTALL_PACKAGES };
4791 mAm.broadcastIntentLocked(null, null, intent, null, null, 0, null, null, permissions,
4792 OP_NONE, null, false, false, MY_PID, SYSTEM_UID, UserHandle.USER_ALL);
4793 }
4794
4795 // Override configuration of the default display duplicates global config, so we need to
4796 // update it also. This will also notify WindowManager about changes.
4797 performDisplayOverrideConfigUpdate(mStackSupervisor.getConfiguration(), deferResume,
4798 DEFAULT_DISPLAY);
4799
4800 return changes;
4801 }
4802
4803 boolean updateDisplayOverrideConfigurationLocked(Configuration values, ActivityRecord starting,
4804 boolean deferResume, int displayId) {
4805 return updateDisplayOverrideConfigurationLocked(values, starting, deferResume /* deferResume */,
4806 displayId, null /* result */);
4807 }
4808
4809 /**
4810 * Updates override configuration specific for the selected display. If no config is provided,
4811 * new one will be computed in WM based on current display info.
4812 */
4813 boolean updateDisplayOverrideConfigurationLocked(Configuration values,
4814 ActivityRecord starting, boolean deferResume, int displayId,
4815 ActivityTaskManagerService.UpdateConfigurationResult result) {
4816 int changes = 0;
4817 boolean kept = true;
4818
4819 if (mWindowManager != null) {
4820 mWindowManager.deferSurfaceLayout();
4821 }
4822 try {
4823 if (values != null) {
4824 if (displayId == DEFAULT_DISPLAY) {
4825 // Override configuration of the default display duplicates global config, so
4826 // we're calling global config update instead for default display. It will also
4827 // apply the correct override config.
4828 changes = updateGlobalConfigurationLocked(values, false /* initLocale */,
4829 false /* persistent */, UserHandle.USER_NULL /* userId */, deferResume);
4830 } else {
4831 changes = performDisplayOverrideConfigUpdate(values, deferResume, displayId);
4832 }
4833 }
4834
4835 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes);
4836 } finally {
4837 if (mWindowManager != null) {
4838 mWindowManager.continueSurfaceLayout();
4839 }
4840 }
4841
4842 if (result != null) {
4843 result.changes = changes;
4844 result.activityRelaunched = !kept;
4845 }
4846 return kept;
4847 }
4848
4849 private int performDisplayOverrideConfigUpdate(Configuration values, boolean deferResume,
4850 int displayId) {
4851 mTempConfig.setTo(mStackSupervisor.getDisplayOverrideConfiguration(displayId));
4852 final int changes = mTempConfig.updateFrom(values);
4853 if (changes != 0) {
4854 Slog.i(TAG, "Override config changes=" + Integer.toHexString(changes) + " "
4855 + mTempConfig + " for displayId=" + displayId);
4856 mStackSupervisor.setDisplayOverrideConfiguration(mTempConfig, displayId);
4857
4858 final boolean isDensityChange = (changes & ActivityInfo.CONFIG_DENSITY) != 0;
4859 if (isDensityChange && displayId == DEFAULT_DISPLAY) {
Wale Ogunwale008163e2018-07-23 23:11:08 -07004860 mAppWarnings.onDensityChanged();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07004861
4862 mAm.killAllBackgroundProcessesExcept(N,
4863 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE);
4864 }
4865 }
4866
4867 // Update the configuration with WM first and check if any of the stacks need to be resized
4868 // due to the configuration change. If so, resize the stacks now and do any relaunches if
4869 // necessary. This way we don't need to relaunch again afterwards in
4870 // ensureActivityConfiguration().
4871 if (mWindowManager != null) {
4872 final int[] resizedStacks =
4873 mWindowManager.setNewDisplayOverrideConfiguration(mTempConfig, displayId);
4874 if (resizedStacks != null) {
4875 for (int stackId : resizedStacks) {
4876 resizeStackWithBoundsFromWindowManager(stackId, deferResume);
4877 }
4878 }
4879 }
4880
4881 return changes;
4882 }
4883
Wale Ogunwalef6733932018-06-27 05:14:34 -07004884 private void updateEventDispatchingLocked(boolean booted) {
4885 mWindowManager.setEventDispatching(booted && !mShuttingDown);
4886 }
4887
Wale Ogunwale342fbe92018-10-09 08:44:10 -07004888 private void sendPutConfigurationForUserMsg(int userId, Configuration config) {
4889 final ContentResolver resolver = mContext.getContentResolver();
4890 Settings.System.putConfigurationForUser(resolver, config, userId);
4891 }
4892
4893 private void sendLocaleToMountDaemonMsg(Locale l) {
4894 try {
4895 IBinder service = ServiceManager.getService("mount");
4896 IStorageManager storageManager = IStorageManager.Stub.asInterface(service);
4897 Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI");
4898 storageManager.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag());
4899 } catch (RemoteException e) {
4900 Log.e(TAG, "Error storing locale for decryption UI", e);
4901 }
4902 }
4903
4904 boolean isActivityStartsLoggingEnabled() {
4905 return mAmInternal.isActivityStartsLoggingEnabled();
4906 }
4907
Wale Ogunwalef6733932018-06-27 05:14:34 -07004908 void enableScreenAfterBoot(boolean booted) {
4909 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN,
4910 SystemClock.uptimeMillis());
4911 mWindowManager.enableScreenAfterBoot();
4912
4913 synchronized (mGlobalLock) {
4914 updateEventDispatchingLocked(booted);
4915 }
4916 }
4917
4918 boolean canShowErrorDialogs() {
4919 return mShowDialogs && !mSleeping && !mShuttingDown
4920 && !mKeyguardController.isKeyguardOrAodShowing(DEFAULT_DISPLAY)
4921 && !hasUserRestriction(UserManager.DISALLOW_SYSTEM_ERROR_DIALOGS,
Wale Ogunwale86b74462018-07-02 08:42:43 -07004922 mAmInternal.getCurrentUserId())
Wale Ogunwalef6733932018-06-27 05:14:34 -07004923 && !(UserManager.isDeviceInDemoMode(mContext)
Wale Ogunwale86b74462018-07-02 08:42:43 -07004924 && mAmInternal.getCurrentUser().isDemo());
Wale Ogunwalef6733932018-06-27 05:14:34 -07004925 }
4926
Wale Ogunwale906f9c62018-07-23 11:23:44 -07004927 static long getInputDispatchingTimeoutLocked(ActivityRecord r) {
4928 if (r == null || !r.hasProcess()) {
4929 return KEY_DISPATCHING_TIMEOUT_MS;
4930 }
4931 return getInputDispatchingTimeoutLocked(r.app);
4932 }
4933
4934 private static long getInputDispatchingTimeoutLocked(WindowProcessController r) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07004935 return r != null ? r.getInputDispatchingTimeout() : KEY_DISPATCHING_TIMEOUT_MS;
Wale Ogunwale906f9c62018-07-23 11:23:44 -07004936 }
4937
Wale Ogunwalef6733932018-06-27 05:14:34 -07004938 /**
4939 * Decide based on the configuration whether we should show the ANR,
4940 * crash, etc dialogs. The idea is that if there is no affordance to
4941 * press the on-screen buttons, or the user experience would be more
4942 * greatly impacted than the crash itself, we shouldn't show the dialog.
4943 *
4944 * A thought: SystemUI might also want to get told about this, the Power
4945 * dialog / global actions also might want different behaviors.
4946 */
4947 private void updateShouldShowDialogsLocked(Configuration config) {
4948 final boolean inputMethodExists = !(config.keyboard == Configuration.KEYBOARD_NOKEYS
4949 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH
4950 && config.navigation == Configuration.NAVIGATION_NONAV);
4951 int modeType = config.uiMode & Configuration.UI_MODE_TYPE_MASK;
4952 final boolean uiModeSupportsDialogs = (modeType != Configuration.UI_MODE_TYPE_CAR
4953 && !(modeType == Configuration.UI_MODE_TYPE_WATCH && Build.IS_USER)
4954 && modeType != Configuration.UI_MODE_TYPE_TELEVISION
4955 && modeType != Configuration.UI_MODE_TYPE_VR_HEADSET);
4956 final boolean hideDialogsSet = Settings.Global.getInt(mContext.getContentResolver(),
4957 HIDE_ERROR_DIALOGS, 0) != 0;
4958 mShowDialogs = inputMethodExists && uiModeSupportsDialogs && !hideDialogsSet;
4959 }
4960
4961 private void updateFontScaleIfNeeded(@UserIdInt int userId) {
4962 final float scaleFactor = Settings.System.getFloatForUser(mContext.getContentResolver(),
4963 FONT_SCALE, 1.0f, userId);
4964
4965 synchronized (this) {
4966 if (getGlobalConfiguration().fontScale == scaleFactor) {
4967 return;
4968 }
4969
4970 final Configuration configuration
4971 = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY);
4972 configuration.fontScale = scaleFactor;
4973 updatePersistentConfiguration(configuration, userId);
4974 }
4975 }
4976
4977 // Actually is sleeping or shutting down or whatever else in the future
4978 // is an inactive state.
4979 boolean isSleepingOrShuttingDownLocked() {
4980 return isSleepingLocked() || mShuttingDown;
4981 }
4982
4983 boolean isSleepingLocked() {
4984 return mSleeping;
4985 }
4986
Riddle Hsu16567132018-08-16 21:37:47 +08004987 /** Update AMS states when an activity is resumed. */
Wale Ogunwalef6733932018-06-27 05:14:34 -07004988 void setResumedActivityUncheckLocked(ActivityRecord r, String reason) {
4989 final TaskRecord task = r.getTask();
4990 if (task.isActivityTypeStandard()) {
4991 if (mCurAppTimeTracker != r.appTimeTracker) {
4992 // We are switching app tracking. Complete the current one.
4993 if (mCurAppTimeTracker != null) {
4994 mCurAppTimeTracker.stop();
4995 mH.obtainMessage(
4996 REPORT_TIME_TRACKER_MSG, mCurAppTimeTracker).sendToTarget();
4997 mStackSupervisor.clearOtherAppTimeTrackers(r.appTimeTracker);
4998 mCurAppTimeTracker = null;
4999 }
5000 if (r.appTimeTracker != null) {
5001 mCurAppTimeTracker = r.appTimeTracker;
5002 startTimeTrackingFocusedActivityLocked();
5003 }
5004 } else {
5005 startTimeTrackingFocusedActivityLocked();
5006 }
5007 } else {
5008 r.appTimeTracker = null;
5009 }
5010 // TODO: VI Maybe r.task.voiceInteractor || r.voiceInteractor != null
5011 // TODO: Probably not, because we don't want to resume voice on switching
5012 // back to this activity
5013 if (task.voiceInteractor != null) {
5014 startRunningVoiceLocked(task.voiceSession, r.info.applicationInfo.uid);
5015 } else {
5016 finishRunningVoiceLocked();
5017
5018 if (mLastResumedActivity != null) {
5019 final IVoiceInteractionSession session;
5020
5021 final TaskRecord lastResumedActivityTask = mLastResumedActivity.getTask();
5022 if (lastResumedActivityTask != null
5023 && lastResumedActivityTask.voiceSession != null) {
5024 session = lastResumedActivityTask.voiceSession;
5025 } else {
5026 session = mLastResumedActivity.voiceSession;
5027 }
5028
5029 if (session != null) {
5030 // We had been in a voice interaction session, but now focused has
5031 // move to something different. Just finish the session, we can't
5032 // return to it and retain the proper state and synchronization with
5033 // the voice interaction service.
5034 finishVoiceTask(session);
5035 }
5036 }
5037 }
5038
5039 if (mLastResumedActivity != null && r.userId != mLastResumedActivity.userId) {
5040 mAmInternal.sendForegroundProfileChanged(r.userId);
5041 }
5042 updateResumedAppTrace(r);
5043 mLastResumedActivity = r;
5044
Tiger Huang1e5b10a2018-07-30 20:19:51 +08005045 r.getDisplay().setFocusedApp(r, true);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005046
5047 applyUpdateLockStateLocked(r);
5048 applyUpdateVrModeLocked(r);
5049
5050 EventLogTags.writeAmSetResumedActivity(
5051 r == null ? -1 : r.userId,
5052 r == null ? "NULL" : r.shortComponentName,
5053 reason);
5054 }
5055
5056 ActivityTaskManagerInternal.SleepToken acquireSleepToken(String tag, int displayId) {
5057 synchronized (mGlobalLock) {
5058 final ActivityTaskManagerInternal.SleepToken token = mStackSupervisor.createSleepTokenLocked(tag, displayId);
5059 updateSleepIfNeededLocked();
5060 return token;
5061 }
5062 }
5063
5064 void updateSleepIfNeededLocked() {
5065 final boolean shouldSleep = !mStackSupervisor.hasAwakeDisplay();
5066 final boolean wasSleeping = mSleeping;
5067 boolean updateOomAdj = false;
5068
5069 if (!shouldSleep) {
5070 // If wasSleeping is true, we need to wake up activity manager state from when
5071 // we started sleeping. In either case, we need to apply the sleep tokens, which
5072 // will wake up stacks or put them to sleep as appropriate.
5073 if (wasSleeping) {
5074 mSleeping = false;
Chenjie Yubd1a28f2018-07-17 14:55:19 -07005075 StatsLog.write(StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED,
5076 StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED__STATE__AWAKE);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005077 startTimeTrackingFocusedActivityLocked();
5078 mTopProcessState = ActivityManager.PROCESS_STATE_TOP;
5079 mStackSupervisor.comeOutOfSleepIfNeededLocked();
5080 }
5081 mStackSupervisor.applySleepTokensLocked(true /* applyToStacks */);
5082 if (wasSleeping) {
5083 updateOomAdj = true;
5084 }
5085 } else if (!mSleeping && shouldSleep) {
5086 mSleeping = true;
Chenjie Yubd1a28f2018-07-17 14:55:19 -07005087 StatsLog.write(StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED,
5088 StatsLog.ACTIVITY_MANAGER_SLEEP_STATE_CHANGED__STATE__ASLEEP);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005089 if (mCurAppTimeTracker != null) {
5090 mCurAppTimeTracker.stop();
5091 }
5092 mTopProcessState = ActivityManager.PROCESS_STATE_TOP_SLEEPING;
5093 mStackSupervisor.goingToSleepLocked();
5094 updateResumedAppTrace(null /* resumed */);
5095 updateOomAdj = true;
5096 }
5097 if (updateOomAdj) {
5098 mH.post(mAmInternal::updateOomAdj);
5099 }
5100 }
5101
5102 void updateOomAdj() {
5103 mH.post(mAmInternal::updateOomAdj);
5104 }
5105
Wale Ogunwale53783742018-09-16 10:21:51 -07005106 void updateCpuStats() {
5107 mH.post(mAmInternal::updateCpuStats);
5108 }
5109
5110 void updateUsageStats(ActivityRecord component, boolean resumed) {
5111 final Message m = PooledLambda.obtainMessage(ActivityManagerInternal::updateUsageStats,
5112 mAmInternal, component.realActivity, component.app.mUid, component.userId, resumed);
5113 mH.sendMessage(m);
5114 }
5115
5116 void setBooting(boolean booting) {
5117 mAmInternal.setBooting(booting);
5118 }
5119
5120 boolean isBooting() {
5121 return mAmInternal.isBooting();
5122 }
5123
5124 void setBooted(boolean booted) {
5125 mAmInternal.setBooted(booted);
5126 }
5127
5128 boolean isBooted() {
5129 return mAmInternal.isBooted();
5130 }
5131
5132 void postFinishBooting(boolean finishBooting, boolean enableScreen) {
5133 mH.post(() -> {
5134 if (finishBooting) {
5135 mAmInternal.finishBooting();
5136 }
5137 if (enableScreen) {
5138 mInternal.enableScreenAfterBoot(isBooted());
5139 }
5140 });
5141 }
5142
5143 void setHeavyWeightProcess(ActivityRecord root) {
5144 mHeavyWeightProcess = root.app;
5145 final Message m = PooledLambda.obtainMessage(
5146 ActivityTaskManagerService::postHeavyWeightProcessNotification, this,
5147 root.app, root.intent, root.userId);
5148 mH.sendMessage(m);
5149 }
5150
5151 void clearHeavyWeightProcessIfEquals(WindowProcessController proc) {
5152 if (mHeavyWeightProcess == null || mHeavyWeightProcess != proc) {
5153 return;
5154 }
5155
5156 mHeavyWeightProcess = null;
5157 final Message m = PooledLambda.obtainMessage(
5158 ActivityTaskManagerService::cancelHeavyWeightProcessNotification, this,
5159 proc.mUserId);
5160 mH.sendMessage(m);
5161 }
5162
5163 private void cancelHeavyWeightProcessNotification(int userId) {
5164 final INotificationManager inm = NotificationManager.getService();
5165 if (inm == null) {
5166 return;
5167 }
5168 try {
5169 inm.cancelNotificationWithTag("android", null,
5170 SystemMessage.NOTE_HEAVY_WEIGHT_NOTIFICATION, userId);
5171 } catch (RuntimeException e) {
5172 Slog.w(TAG, "Error canceling notification for service", e);
5173 } catch (RemoteException e) {
5174 }
5175
5176 }
5177
5178 private void postHeavyWeightProcessNotification(
5179 WindowProcessController proc, Intent intent, int userId) {
5180 if (proc == null) {
5181 return;
5182 }
5183
5184 final INotificationManager inm = NotificationManager.getService();
5185 if (inm == null) {
5186 return;
5187 }
5188
5189 try {
5190 Context context = mContext.createPackageContext(proc.mInfo.packageName, 0);
5191 String text = mContext.getString(R.string.heavy_weight_notification,
5192 context.getApplicationInfo().loadLabel(context.getPackageManager()));
5193 Notification notification =
5194 new Notification.Builder(context,
5195 SystemNotificationChannels.HEAVY_WEIGHT_APP)
5196 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb)
5197 .setWhen(0)
5198 .setOngoing(true)
5199 .setTicker(text)
5200 .setColor(mContext.getColor(
5201 com.android.internal.R.color.system_notification_accent_color))
5202 .setContentTitle(text)
5203 .setContentText(
5204 mContext.getText(R.string.heavy_weight_notification_detail))
5205 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0,
5206 intent, PendingIntent.FLAG_CANCEL_CURRENT, null,
5207 new UserHandle(userId)))
5208 .build();
5209 try {
5210 inm.enqueueNotificationWithTag("android", "android", null,
5211 SystemMessage.NOTE_HEAVY_WEIGHT_NOTIFICATION, notification, userId);
5212 } catch (RuntimeException e) {
5213 Slog.w(TAG, "Error showing notification for heavy-weight app", e);
5214 } catch (RemoteException e) {
5215 }
5216 } catch (PackageManager.NameNotFoundException e) {
5217 Slog.w(TAG, "Unable to create context for heavy notification", e);
5218 }
5219
5220 }
5221
Wale Ogunwaleee6eca12018-09-19 20:37:53 -07005222 IIntentSender getIntentSenderLocked(int type, String packageName, int callingUid, int userId,
5223 IBinder token, String resultWho, int requestCode, Intent[] intents,
5224 String[] resolvedTypes, int flags, Bundle bOptions) {
5225
5226 ActivityRecord activity = null;
5227 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) {
5228 activity = ActivityRecord.isInStackLocked(token);
5229 if (activity == null) {
5230 Slog.w(TAG, "Failed createPendingResult: activity " + token + " not in any stack");
5231 return null;
5232 }
5233 if (activity.finishing) {
5234 Slog.w(TAG, "Failed createPendingResult: activity " + activity + " is finishing");
5235 return null;
5236 }
5237 }
5238
5239 final PendingIntentRecord rec = mPendingIntentController.getIntentSender(type, packageName,
5240 callingUid, userId, token, resultWho, requestCode, intents, resolvedTypes, flags,
5241 bOptions);
5242 final boolean noCreate = (flags & PendingIntent.FLAG_NO_CREATE) != 0;
5243 if (noCreate) {
5244 return rec;
5245 }
5246 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) {
5247 if (activity.pendingResults == null) {
5248 activity.pendingResults = new HashSet<>();
5249 }
5250 activity.pendingResults.add(rec.ref);
5251 }
5252 return rec;
5253 }
5254
Andrii Kulian52d255c2018-07-13 11:32:19 -07005255 // TODO(b/111541062): Update app time tracking to make it aware of multiple resumed activities
Wale Ogunwalef6733932018-06-27 05:14:34 -07005256 private void startTimeTrackingFocusedActivityLocked() {
Andrii Kulian52d255c2018-07-13 11:32:19 -07005257 final ActivityRecord resumedActivity = mStackSupervisor.getTopResumedActivity();
Wale Ogunwalef6733932018-06-27 05:14:34 -07005258 if (!mSleeping && mCurAppTimeTracker != null && resumedActivity != null) {
5259 mCurAppTimeTracker.start(resumedActivity.packageName);
5260 }
5261 }
5262
5263 private void updateResumedAppTrace(@Nullable ActivityRecord resumed) {
5264 if (mTracedResumedActivity != null) {
5265 Trace.asyncTraceEnd(TRACE_TAG_ACTIVITY_MANAGER,
5266 constructResumedTraceName(mTracedResumedActivity.packageName), 0);
5267 }
5268 if (resumed != null) {
5269 Trace.asyncTraceBegin(TRACE_TAG_ACTIVITY_MANAGER,
5270 constructResumedTraceName(resumed.packageName), 0);
5271 }
5272 mTracedResumedActivity = resumed;
5273 }
5274
5275 private String constructResumedTraceName(String packageName) {
5276 return "focused app: " + packageName;
5277 }
5278
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005279 /** Helper method that requests bounds from WM and applies them to stack. */
5280 private void resizeStackWithBoundsFromWindowManager(int stackId, boolean deferResume) {
5281 final Rect newStackBounds = new Rect();
5282 final ActivityStack stack = mStackSupervisor.getStack(stackId);
5283
5284 // TODO(b/71548119): Revert CL introducing below once cause of mismatch is found.
5285 if (stack == null) {
5286 final StringWriter writer = new StringWriter();
5287 final PrintWriter printWriter = new PrintWriter(writer);
5288 mStackSupervisor.dumpDisplays(printWriter);
5289 printWriter.flush();
5290
5291 Log.wtf(TAG, "stack not found:" + stackId + " displays:" + writer);
5292 }
5293
5294 stack.getBoundsForNewConfiguration(newStackBounds);
5295 mStackSupervisor.resizeStackLocked(
5296 stack, !newStackBounds.isEmpty() ? newStackBounds : null /* bounds */,
5297 null /* tempTaskBounds */, null /* tempTaskInsetBounds */,
5298 false /* preserveWindows */, false /* allowResizeInDockedMode */, deferResume);
5299 }
5300
5301 /** Applies latest configuration and/or visibility updates if needed. */
5302 private boolean ensureConfigAndVisibilityAfterUpdate(ActivityRecord starting, int changes) {
5303 boolean kept = true;
Andrii Kulian5f750bc2018-07-17 08:57:23 -07005304 final ActivityStack mainStack = mStackSupervisor.getTopDisplayFocusedStack();
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005305 // mainStack is null during startup.
5306 if (mainStack != null) {
5307 if (changes != 0 && starting == null) {
5308 // If the configuration changed, and the caller is not already
5309 // in the process of starting an activity, then find the top
5310 // activity to check if its configuration needs to change.
5311 starting = mainStack.topRunningActivityLocked();
5312 }
5313
5314 if (starting != null) {
5315 kept = starting.ensureActivityConfiguration(changes,
5316 false /* preserveWindow */);
5317 // And we need to make sure at this point that all other activities
5318 // are made visible with the correct configuration.
5319 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes,
5320 !PRESERVE_WINDOWS);
5321 }
5322 }
5323
5324 return kept;
5325 }
5326
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005327 void scheduleAppGcsLocked() {
5328 mH.post(() -> mAmInternal.scheduleAppGcs());
5329 }
5330
Wale Ogunwale53783742018-09-16 10:21:51 -07005331 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) {
5332 return mCompatModePackages.compatibilityInfoForPackageLocked(ai);
5333 }
5334
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005335 /**
5336 * Returns the PackageManager. Used by classes hosted by {@link ActivityTaskManagerService}. The
5337 * PackageManager could be unavailable at construction time and therefore needs to be accessed
5338 * on demand.
5339 */
5340 IPackageManager getPackageManager() {
5341 return AppGlobals.getPackageManager();
5342 }
5343
5344 PackageManagerInternal getPackageManagerInternalLocked() {
5345 if (mPmInternal == null) {
5346 mPmInternal = LocalServices.getService(PackageManagerInternal.class);
5347 }
5348 return mPmInternal;
5349 }
5350
Wale Ogunwale008163e2018-07-23 23:11:08 -07005351 AppWarnings getAppWarningsLocked() {
5352 return mAppWarnings;
5353 }
5354
Wale Ogunwale214f3482018-10-04 11:00:47 -07005355 Intent getHomeIntent() {
5356 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
5357 intent.setComponent(mTopComponent);
5358 intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING);
5359 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
5360 intent.addCategory(Intent.CATEGORY_HOME);
5361 }
5362 return intent;
5363 }
5364
5365 /**
5366 * This starts home activity on displays that can have system decorations and only if the
5367 * home activity can have multiple instances.
5368 */
5369 boolean startHomeActivityLocked(int userId, String reason, int displayId) {
5370 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL && mTopAction == null) {
5371 // We are running in factory test mode, but unable to find the factory test app, so just
5372 // sit around displaying the error message and don't try to start anything.
5373 return false;
5374 }
5375
5376 final Intent intent = getHomeIntent();
5377 ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId);
5378 if (aInfo != null) {
5379 intent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name));
5380 // Don't do this if the home app is currently being instrumented.
5381 aInfo = new ActivityInfo(aInfo);
5382 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId);
5383 WindowProcessController app =
5384 getProcessController(aInfo.processName, aInfo.applicationInfo.uid);
5385 if (app == null || !app.isInstrumenting()) {
5386 intent.setFlags(intent.getFlags() | FLAG_ACTIVITY_NEW_TASK);
5387 final int resolvedUserId = UserHandle.getUserId(aInfo.applicationInfo.uid);
5388 // For ANR debugging to verify if the user activity is the one that actually
5389 // launched.
5390 final String myReason = reason + ":" + userId + ":" + resolvedUserId;
5391 getActivityStartController().startHomeActivity(intent, aInfo, myReason, displayId);
5392 }
5393 } else {
5394 Slog.wtf(TAG, "No home screen found for " + intent, new Throwable());
5395 }
5396
5397 return true;
5398 }
5399
5400 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) {
5401 ActivityInfo ai = null;
5402 final ComponentName comp = intent.getComponent();
5403 try {
5404 if (comp != null) {
5405 // Factory test.
5406 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId);
5407 } else {
5408 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent(
5409 intent,
5410 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
5411 flags, userId);
5412
5413 if (info != null) {
5414 ai = info.activityInfo;
5415 }
5416 }
5417 } catch (RemoteException e) {
5418 // ignore
5419 }
5420
5421 return ai;
5422 }
5423
5424 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) {
5425 if (info == null) return null;
5426 ApplicationInfo newInfo = new ApplicationInfo(info);
5427 newInfo.initForUser(userId);
5428 return newInfo;
5429 }
5430
5431 private WindowProcessController getProcessController(String processName, int uid) {
5432 if (uid == SYSTEM_UID) {
5433 // The system gets to run in any process. If there are multiple processes with the same
5434 // uid, just pick the first (this should never happen).
5435 final SparseArray<WindowProcessController> procs =
5436 mProcessNames.getMap().get(processName);
5437 if (procs == null) return null;
5438 final int procCount = procs.size();
5439 for (int i = 0; i < procCount; i++) {
5440 final int procUid = procs.keyAt(i);
5441 if (UserHandle.isApp(procUid) || !UserHandle.isSameUser(procUid, uid)) {
5442 // Don't use an app process or different user process for system component.
5443 continue;
5444 }
5445 return procs.valueAt(i);
5446 }
5447 }
5448
5449 return mProcessNames.get(processName, uid);
5450 }
5451
Wale Ogunwale342fbe92018-10-09 08:44:10 -07005452 WindowProcessController getProcessController(IApplicationThread thread) {
5453 if (thread == null) {
5454 return null;
5455 }
5456
5457 final IBinder threadBinder = thread.asBinder();
5458 final ArrayMap<String, SparseArray<WindowProcessController>> pmap = mProcessNames.getMap();
5459 for (int i = pmap.size()-1; i >= 0; i--) {
5460 final SparseArray<WindowProcessController> procs = pmap.valueAt(i);
5461 for (int j = procs.size() - 1; j >= 0; j--) {
5462 final WindowProcessController proc = procs.valueAt(j);
5463 if (proc.hasThread() && proc.getThread().asBinder() == threadBinder) {
5464 return proc;
5465 }
5466 }
5467 }
5468
5469 return null;
5470 }
5471
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07005472 void logAppTooSlow(WindowProcessController app, long startTime, String msg) {
5473 if (true || Build.IS_USER) {
5474 return;
5475 }
5476
5477 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads();
5478 StrictMode.allowThreadDiskWrites();
5479 try {
5480 File tracesDir = new File("/data/anr");
5481 File tracesFile = null;
5482 try {
5483 tracesFile = File.createTempFile("app_slow", null, tracesDir);
5484
5485 StringBuilder sb = new StringBuilder();
5486 Time tobj = new Time();
5487 tobj.set(System.currentTimeMillis());
5488 sb.append(tobj.format("%Y-%m-%d %H:%M:%S"));
5489 sb.append(": ");
5490 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb);
5491 sb.append(" since ");
5492 sb.append(msg);
5493 FileOutputStream fos = new FileOutputStream(tracesFile);
5494 fos.write(sb.toString().getBytes());
5495 if (app == null) {
5496 fos.write("\n*** No application process!".getBytes());
5497 }
5498 fos.close();
5499 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw-
5500 } catch (IOException e) {
5501 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesFile, e);
5502 return;
5503 }
5504
5505 if (app != null && app.getPid() > 0) {
5506 ArrayList<Integer> firstPids = new ArrayList<Integer>();
5507 firstPids.add(app.getPid());
5508 dumpStackTraces(tracesFile.getAbsolutePath(), firstPids, null, null);
5509 }
5510
5511 File lastTracesFile = null;
5512 File curTracesFile = null;
5513 for (int i=9; i>=0; i--) {
5514 String name = String.format(Locale.US, "slow%02d.txt", i);
5515 curTracesFile = new File(tracesDir, name);
5516 if (curTracesFile.exists()) {
5517 if (lastTracesFile != null) {
5518 curTracesFile.renameTo(lastTracesFile);
5519 } else {
5520 curTracesFile.delete();
5521 }
5522 }
5523 lastTracesFile = curTracesFile;
5524 }
5525 tracesFile.renameTo(curTracesFile);
5526 } finally {
5527 StrictMode.setThreadPolicy(oldPolicy);
5528 }
5529 }
5530
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005531 final class H extends Handler {
Wale Ogunwalef6733932018-06-27 05:14:34 -07005532 static final int REPORT_TIME_TRACKER_MSG = 1;
Wale Ogunwale98875612018-10-12 07:53:02 -07005533 static final int FIRST_ACTIVITY_STACK_MSG = 100;
5534 static final int FIRST_SUPERVISOR_STACK_MSG = 200;
Wale Ogunwalef6733932018-06-27 05:14:34 -07005535
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005536 public H(Looper looper) {
5537 super(looper, null, true);
5538 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07005539
5540 @Override
5541 public void handleMessage(Message msg) {
5542 switch (msg.what) {
5543 case REPORT_TIME_TRACKER_MSG: {
5544 AppTimeTracker tracker = (AppTimeTracker) msg.obj;
5545 tracker.deliverResult(mContext);
5546 } break;
5547 }
5548 }
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005549 }
5550
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005551 final class UiHandler extends Handler {
Wale Ogunwalef6733932018-06-27 05:14:34 -07005552 static final int DISMISS_DIALOG_UI_MSG = 1;
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005553
5554 public UiHandler() {
5555 super(com.android.server.UiThread.get().getLooper(), null, true);
5556 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07005557
5558 @Override
5559 public void handleMessage(Message msg) {
5560 switch (msg.what) {
5561 case DISMISS_DIALOG_UI_MSG: {
5562 final Dialog d = (Dialog) msg.obj;
5563 d.dismiss();
5564 break;
5565 }
5566 }
5567 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005568 }
5569
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005570 final class LocalService extends ActivityTaskManagerInternal {
5571 @Override
5572 public SleepToken acquireSleepToken(String tag, int displayId) {
5573 Preconditions.checkNotNull(tag);
Wale Ogunwalef6733932018-06-27 05:14:34 -07005574 return ActivityTaskManagerService.this.acquireSleepToken(tag, displayId);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005575 }
5576
5577 @Override
5578 public ComponentName getHomeActivityForUser(int userId) {
5579 synchronized (mGlobalLock) {
Louis Changbd48dca2018-08-29 17:44:34 +08005580 ActivityRecord homeActivity =
5581 mStackSupervisor.getDefaultDisplayHomeActivityForUser(userId);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005582 return homeActivity == null ? null : homeActivity.realActivity;
5583 }
5584 }
5585
5586 @Override
5587 public void onLocalVoiceInteractionStarted(IBinder activity,
5588 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
5589 synchronized (mGlobalLock) {
Wale Ogunwalef6733932018-06-27 05:14:34 -07005590 onLocalVoiceInteractionStartedLocked(activity, voiceSession, voiceInteractor);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005591 }
5592 }
5593
5594 @Override
5595 public void notifyAppTransitionStarting(SparseIntArray reasons, long timestamp) {
5596 synchronized (mGlobalLock) {
5597 mStackSupervisor.getActivityMetricsLogger().notifyTransitionStarting(
5598 reasons, timestamp);
5599 }
5600 }
5601
5602 @Override
5603 public void notifyAppTransitionFinished() {
5604 synchronized (mGlobalLock) {
5605 mStackSupervisor.notifyAppTransitionDone();
5606 }
5607 }
5608
5609 @Override
5610 public void notifyAppTransitionCancelled() {
5611 synchronized (mGlobalLock) {
5612 mStackSupervisor.notifyAppTransitionDone();
5613 }
5614 }
5615
5616 @Override
5617 public List<IBinder> getTopVisibleActivities() {
5618 synchronized (mGlobalLock) {
5619 return mStackSupervisor.getTopVisibleActivities();
5620 }
5621 }
5622
5623 @Override
5624 public void notifyDockedStackMinimizedChanged(boolean minimized) {
5625 synchronized (mGlobalLock) {
5626 mStackSupervisor.setDockedStackMinimized(minimized);
5627 }
5628 }
5629
5630 @Override
5631 public int startActivitiesAsPackage(String packageName, int userId, Intent[] intents,
5632 Bundle bOptions) {
5633 Preconditions.checkNotNull(intents, "intents");
5634 final String[] resolvedTypes = new String[intents.length];
5635
5636 // UID of the package on user userId.
5637 // "= 0" is needed because otherwise catch(RemoteException) would make it look like
5638 // packageUid may not be initialized.
5639 int packageUid = 0;
5640 final long ident = Binder.clearCallingIdentity();
5641
5642 try {
5643 for (int i = 0; i < intents.length; i++) {
5644 resolvedTypes[i] =
5645 intents[i].resolveTypeIfNeeded(mContext.getContentResolver());
5646 }
5647
5648 packageUid = AppGlobals.getPackageManager().getPackageUid(
5649 packageName, PackageManager.MATCH_DEBUG_TRIAGED_MISSING, userId);
5650 } catch (RemoteException e) {
5651 // Shouldn't happen.
5652 } finally {
5653 Binder.restoreCallingIdentity(ident);
5654 }
5655
5656 synchronized (mGlobalLock) {
Wale Ogunwale5fa8a8c2018-05-08 13:43:21 -07005657 return getActivityStartController().startActivitiesInPackage(
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005658 packageUid, packageName,
5659 intents, resolvedTypes, null /* resultTo */,
5660 SafeActivityOptions.fromBundle(bOptions), userId,
Michal Karpinski201bc0c2018-07-20 15:32:00 +01005661 false /* validateIncomingUser */, null /* originatingPendingIntent */);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005662 }
5663 }
5664
5665 @Override
Wale Ogunwaleee6eca12018-09-19 20:37:53 -07005666 public int startActivitiesInPackage(int uid, String callingPackage, Intent[] intents,
5667 String[] resolvedTypes, IBinder resultTo, SafeActivityOptions options, int userId,
5668 boolean validateIncomingUser, PendingIntentRecord originatingPendingIntent) {
5669 synchronized (mGlobalLock) {
5670 return getActivityStartController().startActivitiesInPackage(uid, callingPackage,
5671 intents, resolvedTypes, resultTo, options, userId, validateIncomingUser,
5672 originatingPendingIntent);
5673 }
5674 }
5675
5676 @Override
5677 public int startActivityInPackage(int uid, int realCallingPid, int realCallingUid,
5678 String callingPackage, Intent intent, String resolvedType, IBinder resultTo,
5679 String resultWho, int requestCode, int startFlags, SafeActivityOptions options,
5680 int userId, TaskRecord inTask, String reason, boolean validateIncomingUser,
5681 PendingIntentRecord originatingPendingIntent) {
5682 synchronized (mGlobalLock) {
5683 return getActivityStartController().startActivityInPackage(uid, realCallingPid,
5684 realCallingUid, callingPackage, intent, resolvedType, resultTo, resultWho,
5685 requestCode, startFlags, options, userId, inTask, reason,
5686 validateIncomingUser, originatingPendingIntent);
5687 }
5688 }
5689
5690 @Override
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005691 public int startActivityAsUser(IApplicationThread caller, String callerPacakge,
5692 Intent intent, Bundle options, int userId) {
5693 return ActivityTaskManagerService.this.startActivityAsUser(
5694 caller, callerPacakge, intent,
5695 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
5696 null, null, 0, Intent.FLAG_ACTIVITY_NEW_TASK, null, options, userId,
5697 false /*validateIncomingUser*/);
5698 }
5699
5700 @Override
5701 public void notifyKeyguardFlagsChanged(@Nullable Runnable callback) {
5702 synchronized (mGlobalLock) {
5703
5704 // We might change the visibilities here, so prepare an empty app transition which
5705 // might be overridden later if we actually change visibilities.
5706 final boolean wasTransitionSet =
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005707 mWindowManager.getPendingAppTransition() != TRANSIT_NONE;
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005708 if (!wasTransitionSet) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005709 mWindowManager.prepareAppTransition(TRANSIT_NONE,
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005710 false /* alwaysKeepCurrent */);
5711 }
5712 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
5713
5714 // If there was a transition set already we don't want to interfere with it as we
5715 // might be starting it too early.
5716 if (!wasTransitionSet) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005717 mWindowManager.executeAppTransition();
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005718 }
5719 }
5720 if (callback != null) {
5721 callback.run();
5722 }
5723 }
5724
5725 @Override
5726 public void notifyKeyguardTrustedChanged() {
5727 synchronized (mGlobalLock) {
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005728 if (mKeyguardController.isKeyguardShowing(DEFAULT_DISPLAY)) {
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005729 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
5730 }
5731 }
5732 }
5733
5734 /**
5735 * Called after virtual display Id is updated by
5736 * {@link com.android.server.vr.Vr2dDisplay} with a specific
5737 * {@param vrVr2dDisplayId}.
5738 */
5739 @Override
5740 public void setVr2dDisplayId(int vr2dDisplayId) {
5741 if (DEBUG_STACK) Slog.d(TAG, "setVr2dDisplayId called for: " + vr2dDisplayId);
5742 synchronized (mGlobalLock) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005743 mVr2dDisplayId = vr2dDisplayId;
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005744 }
5745 }
5746
5747 @Override
5748 public void setFocusedActivity(IBinder token) {
5749 synchronized (mGlobalLock) {
5750 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
5751 if (r == null) {
5752 throw new IllegalArgumentException(
5753 "setFocusedActivity: No activity record matching token=" + token);
5754 }
Louis Chang19443452018-10-09 12:10:21 +08005755 if (r.moveFocusableActivityToTop("setFocusedActivity")) {
Andrii Kulianab132ee2018-07-24 22:10:21 +08005756 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005757 }
5758 }
5759 }
5760
5761 @Override
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005762 public void registerScreenObserver(ScreenObserver observer) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005763 mScreenObservers.add(observer);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005764 }
5765
5766 @Override
5767 public boolean isCallerRecents(int callingUid) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07005768 return getRecentTasks().isCallerRecents(callingUid);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005769 }
5770
5771 @Override
5772 public boolean isRecentsComponentHomeActivity(int userId) {
Wale Ogunwale16e505a2018-05-07 15:00:49 -07005773 return getRecentTasks().isRecentsComponentHomeActivity(userId);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005774 }
5775
5776 @Override
5777 public void cancelRecentsAnimation(boolean restoreHomeStackPosition) {
5778 ActivityTaskManagerService.this.cancelRecentsAnimation(restoreHomeStackPosition);
5779 }
5780
5781 @Override
5782 public void enforceCallerIsRecentsOrHasPermission(String permission, String func) {
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005783 ActivityTaskManagerService.this.enforceCallerIsRecentsOrHasPermission(permission, func);
Wale Ogunwale6767eae2018-05-03 15:52:51 -07005784 }
Wale Ogunwaled0412b32018-05-08 09:25:50 -07005785
5786 @Override
5787 public void notifyActiveVoiceInteractionServiceChanged(ComponentName component) {
5788 synchronized (mGlobalLock) {
5789 mActiveVoiceInteractionServiceComponent = component;
5790 }
5791 }
Wale Ogunwalea6191b42018-05-09 07:41:32 -07005792
5793 @Override
5794 public void setAllowAppSwitches(@NonNull String type, int uid, int userId) {
5795 if (!mAmInternal.isUserRunning(userId, ActivityManager.FLAG_OR_STOPPED)) {
5796 return;
5797 }
5798 synchronized (mGlobalLock) {
5799 ArrayMap<String, Integer> types = mAllowAppSwitchUids.get(userId);
5800 if (types == null) {
5801 if (uid < 0) {
5802 return;
5803 }
5804 types = new ArrayMap<>();
5805 mAllowAppSwitchUids.put(userId, types);
5806 }
5807 if (uid < 0) {
5808 types.remove(type);
5809 } else {
5810 types.put(type, uid);
5811 }
5812 }
5813 }
5814
5815 @Override
5816 public void onUserStopped(int userId) {
5817 synchronized (mGlobalLock) {
5818 getRecentTasks().unloadUserDataFromMemoryLocked(userId);
5819 mAllowAppSwitchUids.remove(userId);
5820 }
5821 }
5822
5823 @Override
5824 public boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) {
5825 synchronized (mGlobalLock) {
5826 return ActivityTaskManagerService.this.isGetTasksAllowed(
5827 caller, callingPid, callingUid);
5828 }
5829 }
Wale Ogunwale9e4f3e02018-05-17 09:35:39 -07005830
5831 @Override
5832 public void onProcessAdded(WindowProcessController proc) {
5833 synchronized (mGlobalLock) {
5834 mProcessNames.put(proc.mName, proc.mUid, proc);
5835 }
5836 }
5837
5838 @Override
5839 public void onProcessRemoved(String name, int uid) {
5840 synchronized (mGlobalLock) {
5841 mProcessNames.remove(name, uid);
5842 }
5843 }
5844
5845 @Override
5846 public void onCleanUpApplicationRecord(WindowProcessController proc) {
5847 synchronized (mGlobalLock) {
5848 if (proc == mHomeProcess) {
5849 mHomeProcess = null;
5850 }
5851 if (proc == mPreviousProcess) {
5852 mPreviousProcess = null;
5853 }
5854 }
5855 }
Wale Ogunwalef6733932018-06-27 05:14:34 -07005856
5857 @Override
5858 public int getTopProcessState() {
5859 synchronized (mGlobalLock) {
5860 return mTopProcessState;
5861 }
5862 }
5863
5864 @Override
Wale Ogunwale53783742018-09-16 10:21:51 -07005865 public boolean isHeavyWeightProcess(WindowProcessController proc) {
5866 synchronized (mGlobalLock) {
5867 return proc == mHeavyWeightProcess;
5868 }
5869 }
5870
5871 @Override
5872 public void clearHeavyWeightProcessIfEquals(WindowProcessController proc) {
5873 synchronized (mGlobalLock) {
5874 ActivityTaskManagerService.this.clearHeavyWeightProcessIfEquals(proc);
5875 }
5876 }
5877
5878 @Override
5879 public void finishHeavyWeightApp() {
5880 synchronized (mGlobalLock) {
5881 ActivityTaskManagerService.this.clearHeavyWeightProcessIfEquals(
5882 mHeavyWeightProcess);
5883 }
5884 }
5885
5886 @Override
Wale Ogunwalef6733932018-06-27 05:14:34 -07005887 public boolean isSleeping() {
5888 synchronized (mGlobalLock) {
5889 return isSleepingLocked();
5890 }
5891 }
5892
5893 @Override
5894 public boolean isShuttingDown() {
5895 synchronized (mGlobalLock) {
5896 return mShuttingDown;
5897 }
5898 }
5899
5900 @Override
5901 public boolean shuttingDown(boolean booted, int timeout) {
5902 synchronized (mGlobalLock) {
5903 mShuttingDown = true;
5904 mStackSupervisor.prepareForShutdownLocked();
5905 updateEventDispatchingLocked(booted);
5906 return mStackSupervisor.shutdownLocked(timeout);
5907 }
5908 }
5909
5910 @Override
5911 public void enableScreenAfterBoot(boolean booted) {
5912 synchronized (mGlobalLock) {
5913 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN,
5914 SystemClock.uptimeMillis());
5915 mWindowManager.enableScreenAfterBoot();
5916 updateEventDispatchingLocked(booted);
5917 }
5918 }
5919
5920 @Override
5921 public boolean showStrictModeViolationDialog() {
5922 synchronized (mGlobalLock) {
5923 return mShowDialogs && !mSleeping && !mShuttingDown;
5924 }
5925 }
5926
5927 @Override
5928 public void showSystemReadyErrorDialogsIfNeeded() {
5929 synchronized (mGlobalLock) {
5930 try {
5931 if (AppGlobals.getPackageManager().hasSystemUidErrors()) {
5932 Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your"
5933 + " data partition or your device will be unstable.");
5934 mUiHandler.post(() -> {
5935 if (mShowDialogs) {
5936 AlertDialog d = new BaseErrorDialog(mUiContext);
5937 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
5938 d.setCancelable(false);
5939 d.setTitle(mUiContext.getText(R.string.android_system_label));
5940 d.setMessage(mUiContext.getText(R.string.system_error_wipe_data));
5941 d.setButton(DialogInterface.BUTTON_POSITIVE,
5942 mUiContext.getText(R.string.ok),
5943 mUiHandler.obtainMessage(DISMISS_DIALOG_UI_MSG, d));
5944 d.show();
5945 }
5946 });
5947 }
5948 } catch (RemoteException e) {
5949 }
5950
5951 if (!Build.isBuildConsistent()) {
5952 Slog.e(TAG, "Build fingerprint is not consistent, warning user");
5953 mUiHandler.post(() -> {
5954 if (mShowDialogs) {
5955 AlertDialog d = new BaseErrorDialog(mUiContext);
5956 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
5957 d.setCancelable(false);
5958 d.setTitle(mUiContext.getText(R.string.android_system_label));
5959 d.setMessage(mUiContext.getText(R.string.system_error_manufacturer));
5960 d.setButton(DialogInterface.BUTTON_POSITIVE,
5961 mUiContext.getText(R.string.ok),
5962 mUiHandler.obtainMessage(DISMISS_DIALOG_UI_MSG, d));
5963 d.show();
5964 }
5965 });
5966 }
5967 }
5968 }
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005969
5970 @Override
Wale Ogunwale906f9c62018-07-23 11:23:44 -07005971 public void onProcessMapped(int pid, WindowProcessController proc) {
5972 synchronized (mGlobalLock) {
5973 mPidMap.put(pid, proc);
5974 }
5975 }
5976
5977 @Override
5978 public void onProcessUnMapped(int pid) {
5979 synchronized (mGlobalLock) {
5980 mPidMap.remove(pid);
5981 }
5982 }
Wale Ogunwale008163e2018-07-23 23:11:08 -07005983
5984 @Override
5985 public void onPackageDataCleared(String name) {
5986 synchronized (mGlobalLock) {
Wale Ogunwale53783742018-09-16 10:21:51 -07005987 mCompatModePackages.handlePackageDataClearedLocked(name);
Wale Ogunwale008163e2018-07-23 23:11:08 -07005988 mAppWarnings.onPackageDataCleared(name);
5989 }
5990 }
5991
5992 @Override
5993 public void onPackageUninstalled(String name) {
5994 synchronized (mGlobalLock) {
5995 mAppWarnings.onPackageUninstalled(name);
Wale Ogunwale53783742018-09-16 10:21:51 -07005996 mCompatModePackages.handlePackageUninstalledLocked(name);
Wale Ogunwale008163e2018-07-23 23:11:08 -07005997 }
5998 }
Wale Ogunwale53783742018-09-16 10:21:51 -07005999
6000 @Override
6001 public void onPackageAdded(String name, boolean replacing) {
6002 synchronized (mGlobalLock) {
6003 mCompatModePackages.handlePackageAddedLocked(name, replacing);
6004 }
6005 }
6006
6007 @Override
Wale Ogunwale31913b52018-10-13 08:29:31 -07006008 public void onPackageReplaced(ApplicationInfo aInfo) {
6009 synchronized (mGlobalLock) {
6010 mStackSupervisor.updateActivityApplicationInfoLocked(aInfo);
6011 }
6012 }
6013
6014 @Override
Wale Ogunwale53783742018-09-16 10:21:51 -07006015 public CompatibilityInfo compatibilityInfoForPackage(ApplicationInfo ai) {
6016 synchronized (mGlobalLock) {
6017 return compatibilityInfoForPackageLocked(ai);
6018 }
6019 }
6020
Yunfan Chen75157d72018-07-27 14:47:21 +09006021 /**
6022 * Set the corresponding display information for the process global configuration. To be
6023 * called when we need to show IME on a different display.
6024 *
6025 * @param pid The process id associated with the IME window.
6026 * @param displayId The ID of the display showing the IME.
6027 */
6028 @Override
6029 public void onImeWindowSetOnDisplay(int pid, int displayId) {
6030 if (pid == MY_PID || pid < 0) {
6031 if (DEBUG_CONFIGURATION) {
6032 Slog.w(TAG,
6033 "Trying to update display configuration for system/invalid process.");
6034 }
6035 return;
6036 }
6037 mH.post(() -> {
6038 synchronized (mGlobalLock) {
6039 // Check if display is initialized in AM.
6040 if (!mStackSupervisor.isDisplayAdded(displayId)) {
6041 // Call come when display is not yet added or has already been removed.
6042 if (DEBUG_CONFIGURATION) {
6043 Slog.w(TAG, "Trying to update display configuration for non-existing "
6044 + "displayId=" + displayId);
6045 }
6046 return;
6047 }
6048 final WindowProcessController imeProcess = mPidMap.get(pid);
6049 if (imeProcess == null) {
6050 if (DEBUG_CONFIGURATION) {
6051 Slog.w(TAG, "Trying to update display configuration for invalid pid: "
6052 + pid);
6053 }
6054 return;
6055 }
6056 // Fetch the current override configuration of the display and set it to the
6057 // process global configuration.
6058 imeProcess.onConfigurationChanged(
6059 mStackSupervisor.getDisplayOverrideConfiguration(displayId));
6060 }
6061 });
6062 }
Wale Ogunwaleee6eca12018-09-19 20:37:53 -07006063
6064 @Override
6065 public void sendActivityResult(int callingUid, IBinder activityToken, String resultWho,
6066 int requestCode, int resultCode, Intent data) {
6067 synchronized (mGlobalLock) {
6068 final ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
6069 if (r != null && r.getStack() != null) {
6070 r.getStack().sendActivityResultLocked(callingUid, r, resultWho, requestCode,
6071 resultCode, data);
6072 }
6073 }
6074 }
6075
6076 @Override
6077 public void clearPendingResultForActivity(IBinder activityToken,
6078 WeakReference<PendingIntentRecord> pir) {
6079 synchronized (mGlobalLock) {
6080 final ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
6081 if (r != null && r.pendingResults != null) {
6082 r.pendingResults.remove(pir);
6083 }
6084 }
6085 }
6086
6087 @Override
6088 public IIntentSender getIntentSender(int type, String packageName,
6089 int callingUid, int userId, IBinder token, String resultWho,
6090 int requestCode, Intent[] intents, String[] resolvedTypes, int flags,
6091 Bundle bOptions) {
6092 synchronized (mGlobalLock) {
6093 return getIntentSenderLocked(type, packageName, callingUid, userId, token,
6094 resultWho, requestCode, intents, resolvedTypes, flags, bOptions);
6095 }
6096 }
Wale Ogunwalec4e63a42018-10-02 13:19:54 -07006097
6098 @Override
6099 public ActivityServiceConnectionsHolder getServiceConnectionsHolder(IBinder token) {
6100 synchronized (mGlobalLock) {
6101 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
6102 if (r == null) {
6103 return null;
6104 }
6105 if (r.mServiceConnectionsHolder == null) {
6106 r.mServiceConnectionsHolder = new ActivityServiceConnectionsHolder(
6107 ActivityTaskManagerService.this, r);
6108 }
6109
6110 return r.mServiceConnectionsHolder;
6111 }
6112 }
Wale Ogunwale214f3482018-10-04 11:00:47 -07006113
6114 @Override
6115 public Intent getHomeIntent() {
6116 synchronized (mGlobalLock) {
6117 return ActivityTaskManagerService.this.getHomeIntent();
6118 }
6119 }
6120
6121 @Override
6122 public boolean startHomeActivity(int userId, String reason) {
6123 synchronized (mGlobalLock) {
6124 return startHomeActivityLocked(userId, reason, DEFAULT_DISPLAY);
6125 }
6126 }
6127
6128 @Override
6129 public boolean isFactoryTestProcess(WindowProcessController wpc) {
6130 synchronized (mGlobalLock) {
6131 if (mFactoryTest == FACTORY_TEST_OFF) {
6132 return false;
6133 }
6134 if (mFactoryTest == FACTORY_TEST_LOW_LEVEL && mTopComponent != null
6135 && wpc.mName.equals(mTopComponent.getPackageName())) {
6136 return true;
6137 }
6138 return mFactoryTest == FACTORY_TEST_HIGH_LEVEL
6139 && (wpc.mInfo.flags & FLAG_FACTORY_TEST) != 0;
6140 }
6141 }
6142
6143 @Override
6144 public void updateTopComponentForFactoryTest() {
6145 synchronized (mGlobalLock) {
6146 if (mFactoryTest != FACTORY_TEST_LOW_LEVEL) {
6147 return;
6148 }
6149 final ResolveInfo ri = mContext.getPackageManager()
6150 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), STOCK_PM_FLAGS);
6151 final CharSequence errorMsg;
6152 if (ri != null) {
6153 final ActivityInfo ai = ri.activityInfo;
6154 final ApplicationInfo app = ai.applicationInfo;
6155 if ((app.flags & ApplicationInfo.FLAG_SYSTEM) != 0) {
6156 mTopAction = Intent.ACTION_FACTORY_TEST;
6157 mTopData = null;
6158 mTopComponent = new ComponentName(app.packageName, ai.name);
6159 errorMsg = null;
6160 } else {
6161 errorMsg = mContext.getResources().getText(
6162 com.android.internal.R.string.factorytest_not_system);
6163 }
6164 } else {
6165 errorMsg = mContext.getResources().getText(
6166 com.android.internal.R.string.factorytest_no_action);
6167 }
6168 if (errorMsg == null) {
6169 return;
6170 }
6171
6172 mTopAction = null;
6173 mTopData = null;
6174 mTopComponent = null;
6175 mUiHandler.post(() -> {
6176 Dialog d = new FactoryErrorDialog(mUiContext, errorMsg);
6177 d.show();
Wale Ogunwale342fbe92018-10-09 08:44:10 -07006178 mAmInternal.ensureBootCompleted();
Wale Ogunwale214f3482018-10-04 11:00:47 -07006179 });
6180 }
6181 }
Wale Ogunwale31913b52018-10-13 08:29:31 -07006182
6183 @Override
6184 public void handleAppDied(WindowProcessController wpc, boolean restarting,
6185 Runnable finishInstrumentationCallback) {
6186 synchronized (mGlobalLock) {
6187 // Remove this application's activities from active lists.
6188 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(wpc);
6189
6190 wpc.clearRecentTasks();
6191 wpc.clearActivities();
6192
6193 if (wpc.isInstrumenting()) {
6194 finishInstrumentationCallback.run();
6195 }
6196
6197 mWindowManager.deferSurfaceLayout();
6198 try {
6199 if (!restarting && hasVisibleActivities
6200 && !mStackSupervisor.resumeFocusedStacksTopActivitiesLocked()) {
6201 // If there was nothing to resume, and we are not already restarting this
6202 // process, but there is a visible activity that is hosted by the process...
6203 // then make sure all visible activities are running, taking care of
6204 // restarting this process.
6205 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
6206 }
6207 } finally {
6208 mWindowManager.continueSurfaceLayout();
6209 }
6210 }
6211 }
6212
6213 @Override
6214 public void closeSystemDialogs(String reason) {
6215 enforceNotIsolatedCaller("closeSystemDialogs");
6216
6217 final int pid = Binder.getCallingPid();
6218 final int uid = Binder.getCallingUid();
6219 final long origId = Binder.clearCallingIdentity();
6220 try {
6221 synchronized (mGlobalLock) {
6222 // Only allow this from foreground processes, so that background
6223 // applications can't abuse it to prevent system UI from being shown.
6224 if (uid >= FIRST_APPLICATION_UID) {
6225 final WindowProcessController proc = mPidMap.get(pid);
6226 if (!proc.isPerceptible()) {
6227 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason
6228 + " from background process " + proc);
6229 return;
6230 }
6231 }
6232 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
6233 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY
6234 | Intent.FLAG_RECEIVER_FOREGROUND);
6235 if (reason != null) {
6236 intent.putExtra("reason", reason);
6237 }
6238 mWindowManager.closeSystemDialogs(reason);
6239
6240 mStackSupervisor.closeSystemDialogsLocked();
6241
6242 mAm.broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null,
6243 OP_NONE, null, false, false,
6244 -1, SYSTEM_UID, UserHandle.USER_ALL);
6245 }
6246 } finally {
6247 Binder.restoreCallingIdentity(origId);
6248 }
6249 }
6250
6251 @Override
6252 public void cleanupDisabledPackageComponents(
6253 String packageName, Set<String> disabledClasses, int userId, boolean booted) {
6254 synchronized (mGlobalLock) {
6255 // Clean-up disabled activities.
6256 if (mStackSupervisor.finishDisabledPackageActivitiesLocked(
6257 packageName, disabledClasses, true, false, userId) && booted) {
6258 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
6259 mStackSupervisor.scheduleIdleLocked();
6260 }
6261
6262 // Clean-up disabled tasks
6263 getRecentTasks().cleanupDisabledPackageTasksLocked(
6264 packageName, disabledClasses, userId);
6265 }
6266 }
6267
6268 @Override
6269 public boolean onForceStopPackage(String packageName, boolean doit, boolean evenPersistent,
6270 int userId) {
6271 synchronized (mGlobalLock) {
6272
6273 boolean didSomething =
6274 getActivityStartController().clearPendingActivityLaunches(packageName);
6275 didSomething |= mStackSupervisor.finishDisabledPackageActivitiesLocked(packageName,
6276 null, doit, evenPersistent, userId);
6277 return didSomething;
6278 }
6279 }
6280
6281 @Override
6282 public void resumeTopActivities(boolean scheduleIdle) {
6283 synchronized (mGlobalLock) {
6284 mStackSupervisor.resumeFocusedStacksTopActivitiesLocked();
6285 if (scheduleIdle) {
6286 mStackSupervisor.scheduleIdleLocked();
6287 }
6288 }
6289 }
6290
6291 @Override
6292 public void preBindApplication(WindowProcessController wpc) {
6293 synchronized (mGlobalLock) {
6294 mStackSupervisor.getActivityMetricsLogger().notifyBindApplication(wpc.mInfo);
6295 }
6296 }
6297
6298 @Override
6299 public boolean attachApplication(WindowProcessController wpc) throws RemoteException {
6300 synchronized (mGlobalLock) {
6301 return mStackSupervisor.attachApplicationLocked(wpc);
6302 }
6303 }
6304
6305 @Override
6306 public void notifyLockedProfile(@UserIdInt int userId, int currentUserId) {
6307 try {
6308 if (!AppGlobals.getPackageManager().isUidPrivileged(Binder.getCallingUid())) {
6309 throw new SecurityException("Only privileged app can call notifyLockedProfile");
6310 }
6311 } catch (RemoteException ex) {
6312 throw new SecurityException("Fail to check is caller a privileged app", ex);
6313 }
6314
6315 synchronized (mGlobalLock) {
6316 final long ident = Binder.clearCallingIdentity();
6317 try {
6318 if (mAmInternal.shouldConfirmCredentials(userId)) {
6319 if (mKeyguardController.isKeyguardLocked()) {
6320 // Showing launcher to avoid user entering credential twice.
6321 startHomeActivity(currentUserId, "notifyLockedProfile");
6322 }
6323 mStackSupervisor.lockAllProfileTasks(userId);
6324 }
6325 } finally {
6326 Binder.restoreCallingIdentity(ident);
6327 }
6328 }
6329 }
6330
6331 @Override
6332 public void startConfirmDeviceCredentialIntent(Intent intent, Bundle options) {
6333 mAmInternal.enforceCallingPermission(
6334 MANAGE_ACTIVITY_STACKS, "startConfirmDeviceCredentialIntent");
6335
6336 synchronized (mGlobalLock) {
6337 final long ident = Binder.clearCallingIdentity();
6338 try {
6339 intent.addFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS |
6340 FLAG_ACTIVITY_TASK_ON_HOME);
6341 ActivityOptions activityOptions = options != null
6342 ? new ActivityOptions(options) : ActivityOptions.makeBasic();
6343 activityOptions.setLaunchTaskId(
6344 mStackSupervisor.getDefaultDisplayHomeActivity().getTask().taskId);
6345 mContext.startActivityAsUser(intent, activityOptions.toBundle(),
6346 UserHandle.CURRENT);
6347 } finally {
6348 Binder.restoreCallingIdentity(ident);
6349 }
6350 }
6351 }
6352
6353 @Override
6354 public void writeActivitiesToProto(ProtoOutputStream proto) {
6355 synchronized (mGlobalLock) {
6356 // The output proto of "activity --proto activities"
6357 // is ActivityManagerServiceDumpActivitiesProto
6358 mStackSupervisor.writeToProto(proto,
6359 ActivityManagerServiceDumpActivitiesProto.ACTIVITY_STACK_SUPERVISOR);
6360 }
6361 }
6362
6363 @Override
6364 public void saveANRState(String reason) {
6365 synchronized (mGlobalLock) {
6366 final StringWriter sw = new StringWriter();
6367 final PrintWriter pw = new FastPrintWriter(sw, false, 1024);
6368 pw.println(" ANR time: " + DateFormat.getDateTimeInstance().format(new Date()));
6369 if (reason != null) {
6370 pw.println(" Reason: " + reason);
6371 }
6372 pw.println();
6373 getActivityStartController().dump(pw, " ", null);
6374 pw.println();
6375 pw.println("-------------------------------------------------------------------------------");
6376 dumpActivitiesLocked(null /* fd */, pw, null /* args */, 0 /* opti */,
6377 true /* dumpAll */, false /* dumpClient */, null /* dumpPackage */,
6378 "" /* header */);
6379 pw.println();
6380 pw.close();
6381
6382 mLastANRState = sw.toString();
6383 }
6384 }
6385
6386 @Override
6387 public void clearSavedANRState() {
6388 synchronized (mGlobalLock) {
6389 mLastANRState = null;
6390 }
6391 }
6392
6393 @Override
6394 public void dump(String cmd, FileDescriptor fd, PrintWriter pw, String[] args, int opti,
6395 boolean dumpAll, boolean dumpClient, String dumpPackage) {
6396 synchronized (mGlobalLock) {
6397 if (DUMP_ACTIVITIES_CMD.equals(cmd) || DUMP_ACTIVITIES_SHORT_CMD.equals(cmd)) {
6398 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage);
6399 } else if (DUMP_LASTANR_CMD.equals(cmd)) {
6400 dumpLastANRLocked(pw);
6401 } else if (DUMP_LASTANR_TRACES_CMD.equals(cmd)) {
6402 dumpLastANRTracesLocked(pw);
6403 } else if (DUMP_STARTER_CMD.equals(cmd)) {
6404 dumpActivityStarterLocked(pw, dumpPackage);
6405 } else if (DUMP_CONTAINERS_CMD.equals(cmd)) {
6406 dumpActivityContainersLocked(pw);
6407 } else if (DUMP_RECENTS_CMD.equals(cmd) || DUMP_RECENTS_SHORT_CMD.equals(cmd)) {
6408 if (getRecentTasks() != null) {
6409 getRecentTasks().dump(pw, dumpAll, dumpPackage);
6410 }
6411 }
6412 }
6413 }
6414
6415 @Override
6416 public boolean dumpForProcesses(FileDescriptor fd, PrintWriter pw, boolean dumpAll,
6417 String dumpPackage, int dumpAppId, boolean needSep, boolean testPssMode,
6418 int wakefulness) {
6419 synchronized (mGlobalLock) {
6420 if (mHomeProcess != null && (dumpPackage == null
6421 || mHomeProcess.mPkgList.contains(dumpPackage))) {
6422 if (needSep) {
6423 pw.println();
6424 needSep = false;
6425 }
6426 pw.println(" mHomeProcess: " + mHomeProcess);
6427 }
6428 if (mPreviousProcess != null && (dumpPackage == null
6429 || mPreviousProcess.mPkgList.contains(dumpPackage))) {
6430 if (needSep) {
6431 pw.println();
6432 needSep = false;
6433 }
6434 pw.println(" mPreviousProcess: " + mPreviousProcess);
6435 }
6436 if (dumpAll && (mPreviousProcess == null || dumpPackage == null
6437 || mPreviousProcess.mPkgList.contains(dumpPackage))) {
6438 StringBuilder sb = new StringBuilder(128);
6439 sb.append(" mPreviousProcessVisibleTime: ");
6440 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb);
6441 pw.println(sb);
6442 }
6443 if (mHeavyWeightProcess != null && (dumpPackage == null
6444 || mHeavyWeightProcess.mPkgList.contains(dumpPackage))) {
6445 if (needSep) {
6446 pw.println();
6447 needSep = false;
6448 }
6449 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess);
6450 }
6451 if (dumpPackage == null) {
6452 pw.println(" mGlobalConfiguration: " + getGlobalConfiguration());
6453 mStackSupervisor.dumpDisplayConfigs(pw, " ");
6454 }
6455 if (dumpAll) {
6456 if (dumpPackage == null) {
6457 pw.println(" mConfigWillChange: "
6458 + getTopDisplayFocusedStack().mConfigWillChange);
6459 }
6460 if (mCompatModePackages.getPackages().size() > 0) {
6461 boolean printed = false;
6462 for (Map.Entry<String, Integer> entry
6463 : mCompatModePackages.getPackages().entrySet()) {
6464 String pkg = entry.getKey();
6465 int mode = entry.getValue();
6466 if (dumpPackage != null && !dumpPackage.equals(pkg)) {
6467 continue;
6468 }
6469 if (!printed) {
6470 pw.println(" mScreenCompatPackages:");
6471 printed = true;
6472 }
6473 pw.println(" " + pkg + ": " + mode);
6474 }
6475 }
6476 }
6477
6478 if (dumpPackage == null) {
6479 pw.println(" mWakefulness="
6480 + PowerManagerInternal.wakefulnessToString(wakefulness));
6481 pw.println(" mSleepTokens=" + mStackSupervisor.mSleepTokens);
6482 if (mRunningVoice != null) {
6483 pw.println(" mRunningVoice=" + mRunningVoice);
6484 pw.println(" mVoiceWakeLock" + mVoiceWakeLock);
6485 }
6486 pw.println(" mSleeping=" + mSleeping);
6487 pw.println(" mShuttingDown=" + mShuttingDown + " mTestPssMode=" + testPssMode);
6488 pw.println(" mVrController=" + mVrController);
6489 }
6490 if (mCurAppTimeTracker != null) {
6491 mCurAppTimeTracker.dumpWithHeader(pw, " ", true);
6492 }
6493 if (mAllowAppSwitchUids.size() > 0) {
6494 boolean printed = false;
6495 for (int i = 0; i < mAllowAppSwitchUids.size(); i++) {
6496 ArrayMap<String, Integer> types = mAllowAppSwitchUids.valueAt(i);
6497 for (int j = 0; j < types.size(); j++) {
6498 if (dumpPackage == null ||
6499 UserHandle.getAppId(types.valueAt(j).intValue()) == dumpAppId) {
6500 if (needSep) {
6501 pw.println();
6502 needSep = false;
6503 }
6504 if (!printed) {
6505 pw.println(" mAllowAppSwitchUids:");
6506 printed = true;
6507 }
6508 pw.print(" User ");
6509 pw.print(mAllowAppSwitchUids.keyAt(i));
6510 pw.print(": Type ");
6511 pw.print(types.keyAt(j));
6512 pw.print(" = ");
6513 UserHandle.formatUid(pw, types.valueAt(j).intValue());
6514 pw.println();
6515 }
6516 }
6517 }
6518 }
6519 if (dumpPackage == null) {
6520 if (mController != null) {
6521 pw.println(" mController=" + mController
6522 + " mControllerIsAMonkey=" + mControllerIsAMonkey);
6523 }
6524 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep);
6525 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity);
6526 }
6527
6528 return needSep;
6529 }
6530 }
6531
6532 @Override
6533 public void writeProcessesToProto(ProtoOutputStream proto, String dumpPackage) {
6534 synchronized (mGlobalLock) {
6535 if (dumpPackage == null) {
6536 getGlobalConfiguration().writeToProto(proto, GLOBAL_CONFIGURATION);
6537 proto.write(CONFIG_WILL_CHANGE, getTopDisplayFocusedStack().mConfigWillChange);
6538 writeSleepStateToProto(proto);
6539 if (mController != null) {
6540 final long token = proto.start(CONTROLLER);
6541 proto.write(CONTROLLER, mController.toString());
6542 proto.write(IS_A_MONKEY, mControllerIsAMonkey);
6543 proto.end(token);
6544 }
6545 mStackSupervisor.mGoingToSleep.writeToProto(proto, GOING_TO_SLEEP);
6546 mStackSupervisor.mLaunchingActivity.writeToProto(proto, LAUNCHING_ACTIVITY);
6547 }
6548
6549 if (mHomeProcess != null && (dumpPackage == null
6550 || mHomeProcess.mPkgList.contains(dumpPackage))) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07006551 mHomeProcess.writeToProto(proto, HOME_PROC);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006552 }
6553
6554 if (mPreviousProcess != null && (dumpPackage == null
6555 || mPreviousProcess.mPkgList.contains(dumpPackage))) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07006556 mPreviousProcess.writeToProto(proto, PREVIOUS_PROC);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006557 proto.write(PREVIOUS_PROC_VISIBLE_TIME_MS, mPreviousProcessVisibleTime);
6558 }
6559
6560 if (mHeavyWeightProcess != null && (dumpPackage == null
6561 || mHeavyWeightProcess.mPkgList.contains(dumpPackage))) {
Wale Ogunwale51cc98a2018-10-15 10:41:05 -07006562 mHeavyWeightProcess.writeToProto(proto, HEAVY_WEIGHT_PROC);
Wale Ogunwale31913b52018-10-13 08:29:31 -07006563 }
6564
6565 for (Map.Entry<String, Integer> entry
6566 : mCompatModePackages.getPackages().entrySet()) {
6567 String pkg = entry.getKey();
6568 int mode = entry.getValue();
6569 if (dumpPackage == null || dumpPackage.equals(pkg)) {
6570 long compatToken = proto.start(SCREEN_COMPAT_PACKAGES);
6571 proto.write(PACKAGE, pkg);
6572 proto.write(MODE, mode);
6573 proto.end(compatToken);
6574 }
6575 }
6576
6577 if (mCurAppTimeTracker != null) {
6578 mCurAppTimeTracker.writeToProto(proto, CURRENT_TRACKER, true);
6579 }
6580
6581 }
6582 }
6583
6584 @Override
6585 public boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name,
6586 String[] args, int opti, boolean dumpAll, boolean dumpVisibleStacksOnly,
6587 boolean dumpFocusedStackOnly) {
6588 synchronized (mGlobalLock) {
6589 return ActivityTaskManagerService.this.dumpActivity(fd, pw, name, args, opti,
6590 dumpAll, dumpVisibleStacksOnly, dumpFocusedStackOnly);
6591 }
6592 }
6593
6594 @Override
6595 public boolean canGcNow() {
6596 synchronized (mGlobalLock) {
6597 return isSleeping() || mStackSupervisor.allResumedActivitiesIdle();
6598 }
6599 }
6600
6601 @Override
6602 public WindowProcessController getTopApp() {
6603 synchronized (mGlobalLock) {
6604 final ActivityRecord top = mStackSupervisor.getTopResumedActivity();
6605 return top != null ? top.app : null;
6606 }
6607 }
6608
6609 @Override
6610 public void rankTaskLayersIfNeeded() {
6611 synchronized (mGlobalLock) {
6612 if (mStackSupervisor != null) {
6613 mStackSupervisor.rankTaskLayersIfNeeded();
6614 }
6615 }
6616 }
6617
6618 @Override
6619 public void scheduleDestroyAllActivities(String reason) {
6620 synchronized (mGlobalLock) {
6621 mStackSupervisor.scheduleDestroyAllActivities(null, reason);
6622 }
6623 }
6624
6625 @Override
6626 public void removeUser(int userId) {
6627 synchronized (mGlobalLock) {
6628 mStackSupervisor.removeUserLocked(userId);
6629 }
6630 }
6631
6632 @Override
6633 public boolean switchUser(int userId, UserState userState) {
6634 synchronized (mGlobalLock) {
6635 return mStackSupervisor.switchUserLocked(userId, userState);
6636 }
6637 }
6638
6639 @Override
6640 public void onHandleAppCrash(WindowProcessController wpc) {
6641 synchronized (mGlobalLock) {
6642 mStackSupervisor.handleAppCrashLocked(wpc);
6643 }
6644 }
Wale Ogunwale6767eae2018-05-03 15:52:51 -07006645 }
Wale Ogunwale65ebd952018-04-25 15:41:44 -07006646}